「Nginx, PHP-FPM」- NGINX 502 Bad Gateway

  CREATED BY JENKINSBOT

问题描述

浏览器访问 URL 地址,页面显示 502 Bad Gateway 信息。

问题原因

导致该问题可能有多种原因:

第一种、服务未启动

没有启动 PHP-FPM 服务导致 Nginx 无法访问,因此返回 502 错误。

第二种、配置错误

虽然启动 PHP-FPM 服务,但是 Nginx 配置错误。

比如 Nigix 连接 9000 端口,但是 PHP-FPM 监听 sock 文件。

第三种、进程提前退出

这些问题都是因为 PHP-FPM 工作进程退出,导致连接关闭。

在 Nginx 中将看见 104: Connection reset by peer 消息:

2020/05/28 16:30:58 [error] 915#0: *17358 recv() failed (104: Connection reset by peer) while reading
response header from upstream, client: 192.168.50.1, server: www.example.com, request: "HEAD /path/to
/somewhere HTTP/1.1", upstream: "fastcgi://127.0.0.1:9000", host: "www.example.com"

但是 PHP-FPM 的错误日志可能不同:

#1 child <PID> exited on signal 11 (SIGSEGV)

在 PHP-FPM 中,错误日志(对应时间点):

[28-May-2020 16:30:58] WARNING: [pool www] child 3359 exited on signal 11 (SIGSEGV) after 7066.544041 seconds from start
[28-May-2020 16:30:58] NOTICE: [pool www] child 21771 started

至于问题原因嘛,也是各种各样(php-fpm child process exited on signal 11

对于我们的场景,也没啥高级的排查思路:
1)从日志看,SIGSEGV,这是段错误的信号,那就是说 PHP-FPM 程序异常退出
2)那就看内核日志信息,dmesg | grep -F "php-fpm[<PID>]",在输出中显示 memcache.so 程序段错误
3)那我们能猜测的大概原因是:在程序中,使用的 Memcache 插件存在 BUG 导致段错误。

TODO !!! 通过 dmesg 排查进程错误。

#2 fastcgi_read_timeout > request_terminate_timeouts

在 Nginx 中,默认 CGI 超时由 fastcgi_read_timeout 指定,默认为 60 秒。

在 PHP-FPM 中,参数 request_terminate_timeout 指定工作进程处理单个请求的超时时间

如果 fastcgi_read_timeout > request_terminate_timeout 参数,PHP-FPM 进程提前退出,Nginx 返回 502 Bad Gateway 错误。

如果 fastcgi_read_timeout < request_terminate_timeout 参数,Nginx 等待超时,返回 504 Gateway Timeout 错误。

参考文献

NGINX 502 Bad Gateway: PHP-FPM
PHP/List of global php-fpm.conf directives
nginx errors readv() and recv() failed
PHP-FPM and continuos “exited on signal 11”
What causes a SIGSEGV