Я пытаюсь использовать FFMPEG для работы с видео на сервере, и мне нужно кое-что сделать, это получить ход процесса.
Я немного поискал и нашел это решение, которое говорит написать войти в файл, а затем прочитать и проанализировать его.
Проблема
Что сводит меня с ума, так это то, что я говорю FFMPEG - с exec
- (процесс A) записать журнал в файл, но когда я пытаюсь его прочитать - с file_get_contents()
- (процесс B ) он не показывает содержимое до тех пор, пока процесс A не завершится (или не будет прерван PHP-скрипт).
Таким образом, когда процесс A завершается или появляется сообщение "Тайм-аут сценария PHP", я могу читать файл столько раз, сколько захочу, обновляя страницу (процесс B) и показывая содержание в то время.
Что я пробовал
Я пытался использовать fopen()
для создания файла с параметрами w
, w+
и a
, используя и не используя fclose()
. Я пытался также использовать flock()
на тот случай, если процесс B будет быстрее читать, если он знает, что он уже заблокирован и ему не нужно ждать, но тогда FFMPEG не может записать в файл .
Я также искал многопоточность, но я думаю, что должен быть более легкий и простой способ.
Я также использовал контекст CURL и HTTP, как ссылка предлагает, но не повезло.
Я тоже пытался использовать PHP-FFMPEG, но он не поддерживает последнюю версию FFMPEG, поэтому я не могу его использовать.
Когда я сказал раньше "(или прервал PHP-скрипт)", это потому, что я пытался подождать и, когда PHP получил тайм-аут, процесс B работал нормально, и файл все еще обновлялся. эм>
Код
Процесс А (файл A.php)
exec('ffmpeg -y -i input_file.mp4 output_file.avi 2> C:\Full\Path\To\File\log.txt 1>&2');
Процесс B (файл B.php)
$content = file_get_contents($file);
if($content){
//get duration of source
preg_match("/Duration: (.*?), start:/", $content, $matches);
$rawDuration = $matches[1];
//rawDuration is in 00:00:00.00 format. This converts it to seconds.
$ar = array_reverse(explode(":", $rawDuration));
$duration = floatval($ar[0]);
if (!empty($ar[1])) $duration += intval($ar[1]) * 60;
if (!empty($ar[2])) $duration += intval($ar[2]) * 60 * 60;
//get the time in the file that is already encoded
preg_match_all("/time=(.*?) bitrate/", $content, $matches);
$rawTime = array_pop($matches);
//this is needed if there is more than one match
if (is_array($rawTime)){$rawTime = array_pop($rawTime);}
//rawTime is in 00:00:00.00 format. This converts it to seconds.
$ar = array_reverse(explode(":", $rawTime));
$time = floatval($ar[0]);
if (!empty($ar[1])) $time += intval($ar[1]) * 60;
if (!empty($ar[2])) $time += intval($ar[2]) * 60 * 60;
//calculate the progress
$progress = round(($time/$duration) * 100);
echo "Duration: " . $duration . "<br>";
echo "Current Time: " . $time . "<br>";
echo "Progress: " . $progress . "%";
}
Процесс
Я просто открываю fileA.php
на вкладке Chrome, а через несколько секунд открываю fileB.php
на другой вкладке Chrome (и он продолжает загружаться).
Что мне нужно
Мне нужно иметь возможность загрузить файл и показать информацию, которую я хочу показать, пока файл записывается (с помощью exec
и FFMPEG
или других PHP-скриптов), поэтому я могу обновить процент выполнения с помощью некоторых вызовов AJAX.
Дополнительная информация
На данный момент я использую PHP 5.4 на IIS 7.5 с Windows 7 Professional.
Спасибо всем за ваше время, помощь и терпение!
С наилучшими пожеланиями.
Log.txt
записывается и заполняется содержимым до завершения процесса A? - person maxhb   schedule 01.02.2016