增加 PHP-FPM 的空闲超时设置

13

我们最近迁移到了PHP-FPM。然而,我们遇到了一些长时间运行脚本的问题。代码大致如下:

foreach ($items as $item) {
     set_time_limit(30);
     proccessThatTakesAround2secs(); 
}

正常的PHP脚本时间限制也是30秒。以前,我们将剩余的时间限制重置为每个项目的30秒,这在运行良好。由于有大约1000个项目,因此脚本总共通常需要大约30分钟才能完成。但是我们后来遇到了以下问题:

FastCGI: 与服务器“/usr/local/php-5.6.24/sbin/php5-fpm”的通信中止:空闲超时(30秒)

现在我的问题是,将空闲超时增加到一个小时左右是否明智,但仍确保PHP脚本不会运行超过30秒,除非我们使用 set_time_limit?是否有一种方法可以针对每个脚本设置空闲超时(类似于 set_time_limit)?

以下是我们的池配置:

[www]
user = www-data
group = www-data
listen = /var/run/php5-fpm.sock
listen.owner = www-data
listen.group = www-data
pm = static
pm.max_children = 55
pm.max_requests = 10000

php_value[memory_limit] = 128M
php_value[max_execution_time] = 30
php_value[upload_max_filesize] = 20M
php_value[post_max_size] = 20M
php_value[max_input_vars] = 9999

这里是我们的fastcgi.conf文件

<IfModule mod_fastcgi.c>
    AddType application/x-httpd-fastphp5 .php
    Action application/x-httpd-fastphp5 /php5-fcgi
    Alias /php5-fcgi /usr/local/php-5.6.24/sbin/php5-fpm
    FastCgiExternalServer /usr/local/php-5.6.24/sbin/php5-fpm -socket /var/run/php5-fpm.sock -idle-timeout 30 -pass-header Authorization
    <Directory /usr/local/php-5.6.24/sbin/>
        Require all granted
   </Directory>
</IfModule>
2个回答

27

在从 mod_php 迁移到 php-fpm 和 fastcgi 时,我也遇到了长时间运行进程的类似情况。

你看到的错误来自于 apache 的 fastcgi 代理,它会在你的脚本没有输出任何内容 30 秒后终止与 php-fpm 池的连接。

你可以在 Apache 配置中更改空闲超时时间来延长它(不能为 0):

FastCgiExternalServer /usr/lib/cgi-bin/php7-fcgi -socket /run/php/php7.0-fpm.sock -idle-timeout 1800 -pass-header Authorization

链条如下:Apache -> FastCgiExternalServer代理 -> php-fpm池服务器 -> php进程

Apache代理会断开与php的连接,因此从php代码或者.user.ini文件或者通过apache (.htaccess)设置max_execution_time或 set_time_limit没有任何作用。

据我所知,如果php是通过mod_fastcgi在Apache上运行的,则无法从php代码或.user.ini文件或apache (.htaccess)中设置每个脚本的时间限制。这意味着通过一个地方扩展它,例如,你正在为前端和后端用户同时延长超时时间。或者您可以通过2个虚拟主机进行分隔,并在那里定义不同的超时值。


关于您在mod_fastcgi上的评论,您能否在所有地方将时间限制设置得更长一些,然后在应用程序中使用set_time_limit()将时间限制设置为较短的时间,这样应用程序就可以更好地控制时间了? - Frank Forte
@FrankForte 据我所知 - 不,服务器设置在这种情况下优先于应用程序设置。服务器将会直接断开连接。 - seven
1
服务器设置为600秒超时,应用程序设置为30秒或300秒超时 - 只要应用程序超时时间比服务器短,我想应用程序超时就会首先触发(在这种情况下,关闭函数可以在PHP退出之前进行一些最终清理)。 - Frank Forte
请注意,这是针对 httpd 2.2 解决方案的翻译内容。如果使用 2.4 解决方案,则应改用 ProxyPassMatch,并且必须以不同的方式实现超时。 - blamb

11

虽然这可能不适用于OP的配置,但是大多数人将在代理设置下运行PHP-FPM。因此,您可以像这样为代理设置设置超时时间(这是我的php.conf)。

<Proxy "fcgi://127.0.0.1:9000">
   ProxySet timeout=300
</Proxy>

<FilesMatch \.php$>
    SetHandler application/x-httpd-php
    SetHandler "proxy:fcgi://127.0.0.1:9000"
</FilesMatch>

如果您使用的是 .sock 文件,只需将两个实例中的 fcgi://127.0.0.1:9000 替换为使用 sock 文件的命令即可。


我很好奇使用代理与禁用代理的套接字相比有哪些优缺点。 - gunnerman

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接