Hi,
I'm using Vinyl File to represents a file stream in my application. I use clones to pipe the same content to multiple ffmpeg commands (using stream-transcoder or fluent-ffmpeg (same behaviour happening)).
It works great for the first original Vinyl file, but not for the clones.
I've isolated the error in the example below, if I run it multiple times, sometimes I got the 3 finish events, sometimes I just have the one for the original stream. But the files are really copied in the example.
const cloneable = require('cloneable-readable');
const path = require('path');
const fs = require('fs');
let stream = cloneable(fs.createReadStream(path.join(__dirname, 'sample.wav')));
function pipe(stream, num) {
stream.on('end', () => {
console.log(`Reaching end of stream : ${num}`);
});
stream.pipe(fs.createWriteStream(path.join(__dirname, `sample-${num}.wav`))).on('finish', () => {
console.log(`Stop writing to file for stream : ${num}`);
});
}
setImmediate(pipe.bind(null, stream, 1)); // Pipe in another event loop tick <-- this one finished only, it's the original cloneable.
pipe(stream.clone(), 0); // Pipe in the same event loop tick
setTimeout(pipe.bind(null, stream.clone(), 2), 1000); // Pipe a long time after
setTimeout(() => { }, 2000); // here to maintain a ref in the event loop longer.
Here is an example of what I can see during my tests :
Environment
I'm using Node v6.10.3 on mac.
I use a sample wav file of 450kb.
Full example
I think it's not an ffmpeg issue, but for your interest, here is an example of code using ffmpeg which is not working :
const path = require('path');
const fs = require('fs');
const cloneable = require('cloneable-readable');
const ffmpeg = require('fluent-ffmpeg');
let stream = cloneable(fs.createReadStream(path.join(__dirname, 'sample.wav')));
function pipe(stream, num) {
stream.on('end', () => {
console.log(`End writing the stream : ${num}`);
});
ffmpeg(stream)
.audioFrequency(8000)
.format('s16le')
.output(path.join(__dirname, 'copy', `sample-${num}.wav`))
.on('end', () => {
console.log(`finished for the stream: ${num}`);
})
.run();
}
setImmediate(pipe.bind(null, stream, 1)); // Pipe in another event loop tick <-- it's the original cloneable.
pipe(stream.clone(), 0); // Pipe in the same event loop tick
setTimeout(pipe.bind(null, stream.clone(), 2), 1000); // Pipe a long time after
setTimeout(() => { }, 2000); // here to maintain a ref in the event loop longer.
If you run the process above, it will never exit. Events are still attached in the event loop ? Are they lost somewhere ?
Thank you for the time and the response,
Pierre.