2012-04-05 11 views
5

According to the documentation:max_execution_time real para PHP en Linux

max_execution_time only affect the execution time of the script itself. 
Any time spent on activity that happens outside the execution of the script 
such as system calls using system(), stream operations, database queries, etc. 
is not included when determining the maximum time that the script has been running. 
This is not true on Windows where the measured time is real. 

Esto es confirmado por las pruebas:

no superará el tiempo de

<?php 
set_time_limit(5); 
$sql = mysqli_connect('localhost','root','root','mysql'); 
$query = "SELECT SLEEP(10) FROM mysql.user;"; 
$sql->query($query) or die($query.'<br />'.$sql->error); 
echo "You got the page"; 

agotará el tiempo

<?php 
set_time_limit(5); 
while (true) { 
    // do nothing 
} 
echo "You got the page"; 

Nuestro problema es que realmente nos gustaría que PHP agote el tiempo de espera, independientemente de lo que esté haciendo, después de un período de tiempo dado (ya que no queremos mantener los recursos ocupados si sabemos que no hemos entregado una página en un tiempo aceptable, como 10 segundos). Sabemos que podemos jugar con configuraciones como MySQL wait_timeout para las consultas SQL, pero el tiempo de espera de la página dependerá del número de consultas que se ejecutan.

Algunas personas han intentado crear workarounds y no parece aplicable.

P: ¿Hay una forma fácil de obtener un PHP max_execution_time real en Linux, o es mejor que se agote el tiempo en otros lugares, como el nivel Apache?

Respuesta

5

Este es un consejo bastante complicado, pero definitivamente va a hacer lo que quieras, si estás dispuesto a modificar y recompilar PHP.

Eche un vistazo al código fuente de PHP en https://github.com/php/php-src/blob/master/Zend/zend_execute_API.c (el archivo es Zend/zend_execute_API.c), en la función zend_set_timeout. Esta es la función que implementa el límite de tiempo. He aquí cómo funciona en diferentes plataformas:

  • en Windows, crear un nuevo hilo, se inicia un temporizador en él, y cuando termina, establecer una variable global llamada timed_out a 1, la ejecución de PHP controles básicos de esta variable por cada instrucción, y después se salga (muy simplificado)

  • en Cygwin, utilice iTimer con ITIMER_REAL, que mide tiempo real, incluyendo el sueño, espera, lo que, a continuación, elevar una señalque interrumpirá cualquier procesamiento y detener el procesamiento

  • en otros sistemas Unix, use itimer con ITIMER_PROF, que solo mide el tiempo de CPU gastado por el proceso actual (pero tanto en modo de usuario como en modo kernel). Esto significa que esperar por otros procesos (como MySQL) no cuenta en esto.

Ahora lo que quiere hacer es cambiar el iTimer en su Linux desde ITIMER_PROF a ITIMER_REAL, que por supuesto que tiene que hacer manualmente, compilar, instalar, etc.La otra diferencia entre estos dos es que también usan una señal diferente cuando el temporizador se agota. Así que mi sugerencia es cambiar el ifdef:

# ifdef __CYGWIN__ 

en

# if 1 

de manera que se establece tanto ITIMER_REAL y la señal que PHP espera a SIGALRM.

De todos modos toda esta idea no se ha probado (lo uso para algún sistema muy específico, donde ITIMER_PROF se rompe, y parece al trabajo), sin soporte, etc. Utilice a su propio riesgo. Puede funcionar con PHP en sí mismo, pero podría romper otros módulos, en PHP y en Apache, si por alguna razón usan la señal SIGALRM u otro temporizador.

-2

De httpd.conf:

Tiempo de espera: El número de segundos antes de que recibe y envía el tiempo de espera

Tiempo de espera 300

+1

esto no afectará al procesamiento de PHP – kuba

+0

de hecho, he probado con Apache 'TimeOut' establecido en' 2' (segundos) y simplemente no tiene efecto alguno. ¿Hay algo más que 'mod_reqtimeout' que puedas recomendar a John? – Max

1

Esta es una pregunta antigua y respondida. Pero por el bien de ayudar a otros, quería señalar la opción request_terminate_timeout php-fpm. Si está utilizando PHP-FPM, es muy probable que sea lo que necesita.

Si se establece, esta opción le permite decirle a PHP-FPM que mate una solicitud después de N segundos, independientemente de lo que PHP haga.

Ver http://php.net/manual/en/install.fpm.configuration.php#request-terminate-timeout para más detalles.

Cuestiones relacionadas