Reputation: 564
I'm extracting a frame from a video using ffmpeg and golang. If I have a video in bytes instead of saved on disk as an .mp4, how do I tell ffmpeg to read from those bytes without having to write the file to disk, as that is much slower?
I have this working reading from a file, but I'm not sure how to read from bytes.
I've looked at the ffmpeg
documentation here but only see output examples instead of input examples.
func ExtractImage(fileBytes []byte){
// command line args, path, and command
command = "ffmpeg"
frameExtractionTime := "0:00:05.000"
vframes := "1"
qv := "2"
output := "/home/ubuntu/media/video-to-image/output-" + time.Now().Format(time.Kitchen) + ".jpg"
// TODO: use fileBytes instead of videoPath
// create the command
cmd := exec.Command(command,
"-ss", frameExtractionTime,
"-i", videoPath,
"-vframes", vframes,
"-q:v", qv,
output)
// run the command and don't wait for it to finish. waiting exec is run
// ignore errors for examples-sake
_ = cmd.Start()
_ = cmd.Wait()
}
Upvotes: 2
Views: 2817
Reputation: 772
You can make ffmpeg
to read data from stdin rather than reading file from disk, by specifying -
as the value of the option -i
. Then just pass your video bytes as stdin to the command.
func ExtractImage(fileBytes []byte){
// command line args, path, and command
command := "ffmpeg"
frameExtractionTime := "0:00:05.000"
vframes := "1"
qv := "2"
output := "/home/ubuntu/media/video-to-image/output-" + time.Now().Format(time.Kitchen) + ".jpg"
cmd := exec.Command(command,
"-ss", frameExtractionTime,
"-i", "-", // to read from stdin
"-vframes", vframes,
"-q:v", qv,
output)
cmd.Stdin = bytes.NewBuffer(fileBytes)
// run the command and don't wait for it to finish. waiting exec is run
// ignore errors for examples-sake
_ = cmd.Start()
_ = cmd.Wait()
}
You may need to run ffmpeg -protocols
to determine if the pipe
protocol (to read from stdin) is supported in your build of ffmpeg.
Upvotes: 6