Nginx下,请求本机另外Host很慢

栏目: 服务器 · Nginx · 发布时间: 6年前

现象

在本机安装了一个 Discuz!X3.4 的论坛,其使用 UCenter 作为统一用户登录,在其应用管理页面,通信情况一直提示为“正在连接”:

Nginx下,请求本机另外Host很慢

原因

关于这个问题,网上绝大多数的说法是 nginx 服务器在 Windows 上有问题,建议更换为 Apache ,我更换到 Apache 下,也确实是问题解决了,但是我还是觉得 nginx 不至于有这种问题,一定有解决的办法。

再继续查找,发现 nginx 日志里有报告 499 错误,网上说 499 错误的原因是客户端主动断开了与服务器的连接,可是看 ucenter 的代码,貌似并没有断开连接的操作,倒是看日志报告的时间,发现一点端倪:

127.0.0.1 - - [18/Jul/2018:22:35:48   +0800] "GET /uc_server/admin.php?m=app&a=ls&…

127.0.0.1 - - [18/Jul/2018:22:36:19   +0800] "GET   /api/uc.php?code=434eRMR%2FD%2FtjZ357V3sA9RLPqp0rpGfi7ryntpyVEEYay3xgen8Oqk9ETjgEXNbyEbKItHYPZqs   HTTP/1.0" 499

127.0.0.1 - - [18/Jul/2018:22:36:19   +0800] "GET /uc_server/admin.php?m=app&a=ping&inajax=1&url=…

1 行日志,是 ucenter 应用管理中心页面的链接,在这个页面里, ucenter 向本机的 Discuz 服务器发出通信验证请求(第 3 行日志),而第 2 行日志,就是 Discuz 服务器收到的通信验证请求, 499 错误就是出现在此行。

仔细查看这 3 条日志的时间,发现第 2 3 条与第 1 条间隔差不多 29 秒,我们知道, PHP 默认的超时时间为 30 秒,算上点误差, 29 秒也差不多。因此可以认为这个 499 错误是因为 ucenter 服务器发起了 ping 请求(第 3 行日志),一直没有接收到返回值,结果超时断开连接,从而导致 discuz 服务器出现 499 错误。

整个流程如下图:

Nginx下,请求本机另外Host很慢

知道是 499 错误,于是又查找如何解决 499 问题,结果大多数提出要在 nginx 服务器中添加如下配置:

proxy_ignore_client_abort  on;

fastcgi_ignore_client_abort on;

Discuz 的配置项中添加了上述配置:

location ~ \.php$ {

root         C:/PHPackage/workspace/github/DiscuzX/bbs;

fastcgi_pass   127.0.0.1:9090;

fastcgi_index  index.php;

fastcgi_param  SCRIPT_FILENAME  $document_root$fastcgi_script_name;

include        fastcgi_params;

proxy_ignore_client_abort  on;

fastcgi_ignore_client_abort on;

}

再运行服务器,发现 499 问题果然没了,但是通信问题依然没有解决,只是日志变为如下了:

127.0.0.1 - - [18/Jul/2018:22:35:48   +0800] "GET /uc_server/admin.php?m=app&a=ls&…

127.0.0.1 - - [18/Jul/2018:22:36:19   +0800] "GET   /api/uc.php?code=434eRMR%2FD%2FtjZ357V3sA9RLPqp0rpGfi7ryntpyVEEYay3xgen8Oqk9ETjgEXNbyEbKItHYPZqs   HTTP/1.0" 200

127.0.0.1 - - [18/Jul/2018:22:36:19   +0800] "GET /uc_server/admin.php?m=app&a=ping&inajax=1&url=…

配置生效了,但是有个毛用啊,通信还是不成功。第 1 条日志和下面两条日志还是差了差不多 30 秒左右。回过头来仔细分析上面的两个配置项,应该是让 nginx 服务器忽略客户端断开的错误,注意,仅仅是让服务器忽略这个错误,也就是说,当 ucenter 请求超时,断开连接的时候, discuz 服务器忽略了这个错误,从而返回 200 ,可是 ucenter 实际上已经断开了,也收不到 discuz 的返回值,所以实际上还是通信失败。

不过再进一步分析上面的流程,从 nginx php 的关系来看,发现整个请求处理如下图:

Nginx下,请求本机另外Host很慢

nginx 收到请求后,发现是需要执行 PHP 代码,于是将请求就转给了 PHP-CGI 进程,由该进程找到 PHP 代码并执行,但是在 PHP 代码中,又再次向本机的另一个服务器发出 HTTP 请求, nginx 收到后,发现同样要执行 PHP 代码,于是将请求又转回给 PHP-CGI 进程,但是系统中 PHP-CGI 进程只开了一个,后面的 PHP 代码要等到上面的执行完毕才能执行,而后面的 PHP 代码却又是上面的代码请求产生的,于是就阻塞了。

1.1.3   解决

分析至此,解决的思路就已经很清晰了,既然一个 PHP-CGI 线程处理不过来,那么就增加一个线程好了,修改启动 nginx 服务器的批处理代码如下,仅修改一个数字,见红色字体部分:

@echo off

REM Windows 下无效

REM set PHP_FCGI_CHILDREN=5

REM 每个进程处理的最大请求数,或设置为 Windows 环境变量

set PHP_FCGI_MAX_REQUESTS=1000

echo Starting PHP FastCGI...

rem RunHiddenConsole   C:/PHPackage/PHP/php-cgi.exe -b 127.0.0.1:9090 -c C:/PHPackage/PHP/php.ini

RunHiddenConsole xxfpm   "C:/PHPackage/PHP/php-cgi.exe -c C:/PHPackage/PHP/php.ini" -n 2 -i 127.0.0.1 -p 9090

echo Starting nginx...

RunHiddenConsole   C:/PHPackage/nginx-1.15.1/nginx.exe -p C:/PHPackage/nginx-1.15.1

该数字原来是 1 ,现在改为 2 ,重新启动服务器,看任务管理器,果然有两个 PHP-CGI 进程:

Nginx下,请求本机另外Host很慢

再回到 ucenter 的应用管理页面,刷新,结果如下:

Nginx下,请求本机另外Host很慢

啥情况?我们上面折腾了半天,只是从“正在连接”变成了“通信失败”,问题还是没有解决啊!

不过呢,跟踪代码可以验证, 499 的问题的确是彻底解决了,至于为什么还是“通信失败”,那是另外一个问题了,请参见《 Unable to find the socket transport "http" 》。


以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

A Project Guide to UX Design

A Project Guide to UX Design

Russ Unger、Carolyn Chandler / New Riders Press / 2009-3-23 / USD 39.99

"If you are a young designer entering or contemplating entering the UX field this is a canonical book. If you are an organization that really needs to start grokking UX this book is also for you. " -......一起来看看 《A Project Guide to UX Design》 这本书的介绍吧!

HTML 压缩/解压工具
HTML 压缩/解压工具

在线压缩/解压 HTML 代码

MD5 加密
MD5 加密

MD5 加密工具

XML、JSON 在线转换
XML、JSON 在线转换

在线XML、JSON转换工具