我一直在进行负载测试(通过 blitz.io),尝试调整运行 php 5.5、wordpress 3.9.1 和 nginx 1.6.2 的服务器池上的服务器性能。
当我用过多的流量使单个服务器超载时,我就会感到困惑。我完全意识到服务器上的资源是有限的,在某种程度上,它将不得不开始拒绝连接和/或返回 502(或类似)响应。但让我感到困惑的是,为什么我的服务器在负载测试中这么早就返回了 502。
我尝试调整 nginx 来接受多个连接:
nginx.conf
worker_processes auto;
worker_rlimit_nofile 100000;
events {
worker_connections 1024;
use epoll;
multi_accept on;
}
站点配置文件
location ~ \.php$ {
try_files $uri =404;
include /etc/nginx/fastcgi_params;
fastcgi_pass unix:/var/run/php5-fpm.sock;
fastcgi_index index.php;
fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
fastcgi_read_timeout 60s;
fastcgi_send_timeout 60s;
fastcgi_next_upstream_timeout 0;
fastcgi_connect_timeout 60s;
}
php www.conf
pm = static
pm.max_children = 8
我预计负载测试会很快使 PHP 工作进程饱和。但我还预计 nginx 会继续接受连接,并且在达到 fast_cgi 超时后开始返回某种 HTTP 错误代码。
我实际看到的是,nginx 在测试启动后几乎立即返回 502。
nginx 错误日志
2014/11/01 20:35:24 [error] 16688#0: *25837 connect() to unix:/var/run/php5-fpm.sock failed
(11: Resource temporarily unavailable) while connecting to upstream, client: OBFUSCATED,
server: OBFUSCATED, request: "GET /?bust=1 HTTP/1.1", upstream:
"fastcgi://unix:/var/run/php5-fpm.sock:", host: "OBFUSCATED"
我遗漏了什么?为什么待处理的请求没有排队,然后在流程的稍后阶段完成或超时?
答案1
这意味着 php 部分崩溃并且不再在 unix 套接字上监听。
因此 nginx 不会对任何内容进行排队,因为它无法联系代理服务器来发送请求,此时,您可以轻松想象请求在 nginx 端得到非常快的处理。
如果您的 php 服务器没有崩溃,请求确实会就fastcgi_connect_timeout
和fastcgi_read_timeout
值待机,等待某个事件出现。如果达到这些超时,您应该会看到504
错误代码。
worker_connections
顺便说一句,与 rlimit 相比,你的似乎有点低。
也许是时候开始使用upstream
块来决定当目标服务器似乎出现故障时 nginx 必须如何表现,使用健康检查。通过这种方式,您可以管理延迟时间,一旦达到该时间,就会将服务器标记为故障。一旦被视为故障,请求将不会到达该服务器,直到健康检查条件通过以将其再次标记为正常。
答案2
您的问题很可能出在您的 PHP-FPM 配置上,因为您使用的静态进程管理器只有 8 个子进程。几乎任何负载测试都会立即用完这 8 个子进程,并要求更多子进程 - 当没有空闲子进程来处理 PHP 代码时,您将收到您看到的 502 错误。
您应该切换到动态的,或者甚至更好(在我看来),按需的。
此外,根据您正在运行的负载测试类型,将 max_children 设置为相当高的值。如果不知道您正在运行的测试的详细信息,我无法为 max_children 建议任何值。就我而言,我有几个网站,它们每天总共获得约 2,500 名独立访问者和约 15,000 次页面浏览量,我的 max_children 设置为 64,而且从未接近该数字。我将其设置为高于我需要的值,因为负载测试表明我的服务器可以处理比当前更多的流量。
一旦负载测试运行良好,您就会更好地了解如何调整 PHP-FPM 配置。我会建议像我一样将 max_children 设置为 64;只需检查 PHP-FPM 日志以查看您是否超出该限制并根据需要向上调整。