Возможен ли асинхронный запуск linux приложения (ffmpeg) через shell_exec?

drkrol

Есть бот телеграме, которому отправляешь голосовое сообщение (формат oga), а он тебе в ответ отправляет mp3 файл. Я решил реализовать тоже самое: поставил на виртуалку ffmpeg, скормил боту голосовуху и получил mp3. Всё получилось, но меня смутила скорость выполнения скрипта. В моём случае скрипт выполнялся 3-4 секунды, а в случае с чужим ботом — меньше секунды (очень быстро, кажется, что где-то 300мс). Я связался с разработчиком того бота и он сказал, что бот написан на Python (у меня PHP) и самое главное, что выполнение конвертации сделано асинхронно, так как это была самая медленная часть скрипта. Я сделал замеры своего бота и получил такую картину:
(важный момент microtime был умножен на 1000, то есть 1860 — это 1.86 секунды)
Результат таймера
file_path — 312.7338886261
get link — 0.0030994415283203
ffmpeg — 1860.6932163239
send file — 916.67604446411
global — 3090.4860496521

у меня самый медленный момент — тоже конвертация файла.

Вопрос: возможно ли как-нибудь запустить ffmpeg асинхронно?

1. я не заморачивался с названием и просто брал текущую метку времени для его имени.
2. я закомментировал строки с замерами, чтобы не отвлекали

Код (PHP):
  1. $tga = json_decode(file_get_contents(‘php://input’), true);
  2. function tlgrm($method, $data, $client = ‘получатель’) {
  3.   $data[«parse_mode»] = «html»;
  4.   $data[«chat_id»] = $client;
  5.   $ch = curl_init(«https://api.telegram.org/апи бота/$method«);
  6.   curl_setopt_array($ch, [CURLOPT_RETURNTRANSFER => 1,CURLOPT_CUSTOMREQUEST => «POST»,CURLOPT_POSTFIELDS => $data]);
  7.   $r = curl_exec($ch);
  8.   curl_close($ch);
  9.   return json_decode($r, true);
  10. }
  11.  
  12. function tgfile($path) {
  13.   return «https://api.telegram.org/file/апи бота/$path«;
  14. }
  15. $time = time();
  16. $sec = «Результат таймераn«;
  17.  
  18.  
  19. // ПОЛУЧЕНИЕ #FILE_PATH
  20. # $t = microtime(1);
  21. $path = tlgrm(‘getFile’,[‘file_id’ => $tga[‘message’][‘voice’][‘file_id’]]);
  22. # $nt = (microtime(1) — $t)*1000;
  23. # $sec.= «file_path — $ntn»;
  24.  
  25. // ПОЛУЧЕНИЕ ССЫЛКИ НА ФАЙЛ #GET LINK
  26. # $t = microtime(1);
  27. $link = tgfile($path[‘result’][‘file_path’]);
  28. # $nt = (microtime(1) — $t)*1000;
  29. # $sec.= «get link — $ntn»;
  30.  
  31. // SHELL EXEC #FFMPEG
  32. # $t = microtime(1);
  33. shell_exec(«sudo ffmpeg -i $link tmp/$time.mp3″);
  34. # $nt = (microtime(1) — $t)*1000;
  35. # $sec.= «ffmpeg — $ntn»;
  36.  
  37. // ОТПРАВКА ФАЙЛА #SEND FILE
  38. # $t = microtime(1);
  39. $data[‘audio’] = «https://mywebsite.com/tmp/$time.mp3″; // telegram отказался принимать относительную ссылку
  40. tlgrm(‘sendAudio’, $data);
  41. # $nt = (microtime(1) — $t)*1000;
  42. # $sec.= «send file — $ntn»;
  43.  
  44. // ОТПРАВКА ОТЧЁТА
  45. $gt = (microtime(1) $gt)*1000;
  46. $sec.= «global — $gt«;
  47. tlgrm(‘sendMessage’, $sec);

p.s. меня, если честно, смутил ответ программиста, когда он сказал, что дело в асинхронности. Потому что данное действие является линейным: получение файла, конвертация, отправка. Нельзя конвертировать файл до того, как ты его получил. Но скорее всего здесь дело в инициализации ffmpeg. Если бы он был уже «заряжен», то возможно скорость была бы выше.
его слова:

 

musicman3

может просто железо разное?

 

drkrol

@musicman3 Я сейчас взял точно такую же машину как и у автора бота (4 ядра arm) и стало значительно быстрее, но я всё равно медленнее…
Сейчас мой скрипт выполняется в среднем 0,7 секунд, но у него вообще какие-то запредельные цифры. Я не преувеличиваю, когда говорю, что у него выполняется за 0,1-0,2 секунды (я говорю о голосовухе, которая длится 3 секунды). По факту у нас сейчас единственное отличие — это ЯП. Сервера у нас идентичные (я взял там же). Может ли php быть в 3 раза медленнее?

p.s. я убрал из скрипта все замеры времени, чтобы не тратить лишние ресурсы.

 

musicman3

Скорее всего алгоримы написания разные. Возможно это связано с ЯП, а возможно разные программеры по своему усмотрению писали как им это виделось, и в одном случае алгоритм более продуманный и малоресурсный, а в другом вышло по другому. Ну и скорость ЯП может тоже как то еще влиять.

 

artoodetoo

Асинхронно запустить конечно можно, но это не уменьшит скорость возврата готового mp3! Это может ускорить выдачу сообщения типа «заявка на конвертацию принята, скоро пришлем файл».
Python vs. PHP — говно вопрос. В данной задаче разницы не будет, если не косячить.

 

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *