ffprobe / ffmpeg сообщает о разной продолжительности видео, когда файл передается через стандартный ввод - PullRequest
1 голос
/ 19 июня 2019

Я пытаюсь определить продолжительность видео MP4 с помощью ffmpeg, что, конечно, возможно, за исключением того, что когда данные передаются через stdin (требование в моем случае), сообщается, что продолжительность меньше, чем она есть на самом деле является. У меня такая же проблема с ffprobe.

Фактическая продолжительность видео составляет ~ 13 секунд.

Примеры ниже вывода, который я получаю с помощью ffprobe.

Чтение файла с диска (правильная продолжительность):

$ ffprobe video.mp4
...
Duration: 00:00:13.05, start: 0.000000, bitrate: 736 kb/s
...

Потоковая передача в файле (неверная продолжительность):

$ cat video.mp4 | ffprobe -i -
...
Duration: 00:00:08.40, start: 0.080000, bitrate: N/A
...

Как я могу заставить ffprobe сообщать правильную длительность при потоковой передаче в файл через стандартный ввод?

Ответы [ 2 ]

1 голос
/ 19 июня 2019

Ваши входные MP4 выглядят фрагментированными, в этом случае ffmpeg прекратит зондирование после первого фрагмента блока moof и сообщит о его продолжительности. Это не проблема с обычными MP4.

Вы можете запустить cat fragmented.mp4 | ffmpeg -i - -c copy -f null - 2>&1 | grep -oP "(?<=time=)[\d:\.]+" для таких файлов.

1 голос
/ 19 июня 2019

Вы можете использовать опцию ffprobe -show_packets, которая будет «Показывать информацию о каждом пакете, содержащемся во входном мультимедийном потоке».( Прочтите об этом в ffprobe docs .)

С этой опцией ffprobe выведет запись для каждого пакета в потоке следующим образом:

dts_time=13.008000

Итак, мыможет grep вывод для dts_time:

$ cat video.mp4 | ffprobe -i - -show_packets | grep dts_time
...
dts_time=13.008000
dts_time=13.029333

Последняя строка вывода будет содержать метку времени последнего пакета, которая может быть взята в качестве продолжительности видео, чтобы получить, что мы можемсделать что-то вроде:

$ catvideo.mp4 \
    | ffprobe -i - -show_packets -v quiet \
    | grep dts_time \
    | tail -n 1 \
    | awk -F"=" '{print $2}'
13.029333
...