2013-04-19 1 views
1

У меня есть рабочий php-скрипт, использующий shell_exec для выполнения внешней программы, для завершения которой требуется около 30 секунд. Проблема заключается в том, что если пользователь закрывает браузер или соединение закрывается по какой-либо причине, программа, запущенная с shell_exec, продолжает работать впустую, так как ее вывод больше не может быть отправлен пользователю.PHP shell_exec - как завершить процесс, если соединение закрыто?

Есть ли способ убить этот процесс, как только соединение будет закрыто?

Благодарим за помощь.

+0

Просто, чтобы подтвердить, я получил это прямо: имеет ли пользователь в настоящее время приходится ждать около 30 секунд для загрузки страницы? – Jon

+0

shell_exec вызывает программу для выполнения 3D-рендеринга, и результатом является URL-адрес рендеринга, который затем устанавливается как src тега img. PHP-код, который использует shell_exec, выполняется через вызов ajax, поэтому пользователю не нужно ждать 30 секунд для полной загрузки страницы, ему нужно дождаться результата 3D-рендеринга, который, как он знает, займет некоторое время. –

ответ

2

Наконец Я решил!

Я использовал функцию PHP connection_aborted(), чтобы проверить, отключен ли клиент. http://us2.php.net/manual/en/function.connection-aborted.php

Алгоритм следующий (псевдокод)

shell_exec("script");//script is a shell script that launch the program in another thread thus this return immediately 
$task_completed=false; 
while(!$task_completed){ 
    if(connection_aborted()==1){ 
     kill_the_process();//this will kill the running process launched by script 
     die(); 
    } 
    $task_completed=...;//true if the task completed 
    sleep(1); 
} 
0

Вы можете создать менеджер, который запускает/выполняет/останавливает запущенные скрипты php. Этот скрипт будет работать постоянно - может быть как демон - и проверить статус скрипта/процесса, статус пользователя и закрыть скрипт, если пользователь ушел. Я думаю, вы могли бы сделать это хорошо с Sockets.
How to Use Sockets in JavaScript\HTML?
http://php.net/manual/en/book.sockets.php

0

вы можете использовать, чтобы получить список всех запущенных процессов

$res = shell_exec('ps -x'); 
$res = explode("\n",$res); 
print_r($res); 

и использовать это, чтобы убить процесс с заданным ProcessId

shell_exec('kill -KILL ProcessID'); 
+0

Что это значит, если он хочет, чтобы сценарий остановился? 'shell_exec' сначала не является асинхронным (не считая nohup), и, во-вторых, он все равно не знает, покинет ли пользователь страницу или нет. – h2ooooooo

+0

он может использовать этот код, чтобы убить запущенный процесс, когда пользователь закрывает свой браузер, выполняя функцию обратного вызова, которая будет делать запрос ajax всякий раз, когда пользователь закрывает вкладку/браузер на http://www.w3schools.com/jsref/event_onunload.asp – Shushant

+0

Вы не может ожидать, что событие onunload вызовет вызов ajax до того, как пользователь закроет браузер. Это очень ненадежно. – h2ooooooo