Modifier la fonction createVideoWithList pour utiliser spawn au lieu de execSync pour l'exécution de ffmpeg en arrière-plan
This commit is contained in:
@@ -1,6 +1,6 @@
|
|||||||
const fs = require('fs');
|
const fs = require('fs');
|
||||||
const path = require('path');
|
const path = require('path');
|
||||||
const { execSync } = require('child_process');
|
const { spawn } = require('child_process');
|
||||||
|
|
||||||
const serverError = require('../../utils/serverError');
|
const serverError = require('../../utils/serverError');
|
||||||
const db = require('../../db');
|
const db = require('../../db');
|
||||||
@@ -28,13 +28,9 @@ async function deleteVideoProject(videoId) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async function createVideoWithList(projectId, pathList, duration) {
|
async function createVideoWithList(projectId, pathList, duration) {
|
||||||
//pathList étant la liste des chemins déjà triés
|
|
||||||
const tempFile = path.join('temp.txt');
|
const tempFile = path.join('temp.txt');
|
||||||
try {
|
try {
|
||||||
// Trouver tous les fichiers image pour le projet donné
|
|
||||||
const workdir = path.join(PROJECTS_DIR, 'storage', `${projectId}`);
|
const workdir = path.join(PROJECTS_DIR, 'storage', `${projectId}`);
|
||||||
const dir = path.join(PROJECTS_DIR, 'storage', `${projectId}`, 'images');
|
|
||||||
console.log('dir:', dir);
|
|
||||||
const images = pathList;
|
const images = pathList;
|
||||||
console.log('images:', images);
|
console.log('images:', images);
|
||||||
|
|
||||||
@@ -45,38 +41,50 @@ async function createVideoWithList(projectId, pathList, duration) {
|
|||||||
return numA - numB;
|
return numA - numB;
|
||||||
});
|
});
|
||||||
|
|
||||||
// En déduire l'id de la première et dernière image utilisée
|
// Déterminer l'id de la première et la dernière image utilisée
|
||||||
const firstImageId = parseInt(path.basename(sortedImages[0]).match(/\d+/)[0], 10);
|
const firstImageId = parseInt(path.basename(sortedImages[0]).match(/\d+/)[0], 10);
|
||||||
const lastImageId = parseInt(path.basename(sortedImages[sortedImages.length - 1]).match(/\d+/)[0], 10);
|
const lastImageId = parseInt(path.basename(sortedImages[sortedImages.length - 1]).match(/\d+/)[0], 10);
|
||||||
|
|
||||||
console.log('firstImageId:', firstImageId);
|
console.log('firstImageId:', firstImageId);
|
||||||
console.log('lastImageId:', lastImageId);
|
console.log('lastImageId:', lastImageId);
|
||||||
|
|
||||||
// Créer un fichier temporaire pour la liste des images
|
// Créer le fichier temporaire pour la liste des images
|
||||||
fs.writeFileSync(tempFile, sortedImages.map(image => `file '${image}'`).join('\n'));
|
fs.writeFileSync(tempFile, sortedImages.map(image => `file '${image}'`).join('\n'));
|
||||||
|
|
||||||
const frameRate = Math.ceil(sortedImages.length / parseInt(duration));
|
const frameRate = Math.ceil(sortedImages.length / parseInt(duration));
|
||||||
|
|
||||||
// le fichier final prend cette forme : {projectId}_{firstImageId}_{lastImageId}-{timestamp}.mp4
|
|
||||||
const timestamp = new Date().getTime();
|
const timestamp = new Date().getTime();
|
||||||
const outputVideo = path.join(workdir, `${projectId}_${firstImageId}_${lastImageId}-${timestamp}.mp4`);
|
const outputVideo = path.join(workdir, `${projectId}_${firstImageId}_${lastImageId}-${timestamp}.mp4`);
|
||||||
|
|
||||||
// Commande ffmpeg pour créer la vidéo
|
// Préparer les arguments pour ffmpeg
|
||||||
const ffmpegCommand = `ffmpeg -r ${frameRate} -f concat -safe 0 -i ${tempFile} -vsync vfr -pix_fmt yuv420p ${outputVideo}`;
|
const ffmpegArgs = [
|
||||||
console.log('Running ffmpeg command:', ffmpegCommand);
|
'-r', frameRate.toString(),
|
||||||
try {
|
'-f', 'concat',
|
||||||
execSync(ffmpegCommand, { stdio: 'ignore', detached: true });
|
'-safe', '0',
|
||||||
|
'-i', tempFile,
|
||||||
|
'-vsync', 'vfr',
|
||||||
|
'-pix_fmt', 'yuv420p',
|
||||||
|
outputVideo
|
||||||
|
];
|
||||||
|
|
||||||
|
console.log('Lancement de ffmpeg en arrière-plan avec les arguments:', ffmpegArgs);
|
||||||
|
|
||||||
|
// Lancer ffmpeg en mode détaché
|
||||||
|
const child = spawn('ffmpeg', ffmpegArgs, {
|
||||||
|
detached: true,
|
||||||
|
stdio: 'ignore'
|
||||||
|
});
|
||||||
|
|
||||||
|
// Permettre au processus ffmpeg de continuer même si le parent se termine
|
||||||
|
child.unref();
|
||||||
console.log('Video creation started in background:', outputVideo);
|
console.log('Video creation started in background:', outputVideo);
|
||||||
} catch (error) {
|
|
||||||
console.error('ffmpeg command failed:', error);
|
|
||||||
serverError.sendError(error);
|
|
||||||
}
|
|
||||||
return outputVideo;
|
return outputVideo;
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('Error creating video:', error);
|
console.error('Error creating video:', error);
|
||||||
serverError.sendError(error);
|
serverError.sendError(error);
|
||||||
} finally {
|
} finally {
|
||||||
// Supprimer le fichier temporaire
|
// Attention : supprimer le fichier temporaire immédiatement pourrait poser problème
|
||||||
|
// si ffmpeg n'a pas encore fini de le lire. Envisagez un délai ou un mécanisme de nettoyage
|
||||||
if (fs.existsSync(tempFile)) {
|
if (fs.existsSync(tempFile)) {
|
||||||
fs.unlinkSync(tempFile);
|
fs.unlinkSync(tempFile);
|
||||||
console.log('Temporary file deleted:', tempFile);
|
console.log('Temporary file deleted:', tempFile);
|
||||||
@@ -117,7 +125,7 @@ async function createVideo(projectId) {
|
|||||||
// Commande ffmpeg pour créer la vidéo
|
// Commande ffmpeg pour créer la vidéo
|
||||||
const ffmpegCommand = `ffmpeg -r ${frameRate} -f concat -safe 0 -i ${tempFile} -vsync vfr -pix_fmt yuv420p ${outputVideo}`;
|
const ffmpegCommand = `ffmpeg -r ${frameRate} -f concat -safe 0 -i ${tempFile} -vsync vfr -pix_fmt yuv420p ${outputVideo}`;
|
||||||
console.log('Running ffmpeg command:', ffmpegCommand);
|
console.log('Running ffmpeg command:', ffmpegCommand);
|
||||||
execSync(ffmpegCommand);
|
spawn(ffmpegCommand);
|
||||||
console.log('Video created successfully:', outputVideo);
|
console.log('Video created successfully:', outputVideo);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('Error creating video:', error);
|
console.error('Error creating video:', error);
|
||||||
|
|||||||
Reference in New Issue
Block a user