PHP CURL超时但CLI CURL起作用

我正在看到我正在构build的一个PHP应用程序的一个非常奇怪的问题。

我在我的开发服务器(Windows 7 64位) sometestsite.comendpoint.sometestsite.com上有2个虚拟主机。

在我的hosts文件中,我将sometestsite.comendpoint.sometestsite.comconfiguration为指向127.0.0.1

当服务器以PHP 5.4.9作为fcgi模块运行Apache 2.4.2时,一切正常。

然后我删除了Apache并安装了nginx-1.2.5(windows build)。 我得到了php-cgi.exe作为服务运行,似乎一切正常。

问题是从以前的sometestsite.comendpoint.sometestsite.com的CURL调用会超时

然后,我把这段代码本身移动到一个小的PHP文件进行testing:

 $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, 'http://endpoint.sometestsite.com/test'); curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POSTFIELDS, array('provider' => urlencode('provider'), 'key' => urlencode('asdf'))); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); //Execute and get the data back $result = curl_exec($ch); var_dump($result); 

这是我在PHP日志中收到的内容:

 PHP Fatal error: Maximum execution time of 30 seconds exceeded in D:\www\test5.php on line 22 PHP Stack trace: PHP 1. {main}() D:\www\test5.php:0 

但是,如果我使用CLI CURL(通过Git Bash)运行相同的请求,它工作正常:

 $ curl -X POST 'http://endpoint.sometestsite.com/test' -d'provider=provider&key=asdf' {"test": "OK"} 

这是非常奇怪的,因为PHP是完全相同的版本,并具有与使用Apache时相同的configuration。

我不确定这是一个Web服务器configuration问题还是PHP的CURL问题。

任何人都可以提供一些见解/过去的经验,为什么发生这种情况?

Nginx不会为你产生你的php-cgi.exe进程。 如果你来自像我这样的Apache,并使用mod_fcgid,你会发现在系统中有许多php-cgi.exe进程。

由于Nginx并没有为您产生PHP进程,您将需要自己启动进程。 在我的情况下,我有php-cgi.exe -b 127.0.0.1:9000自动作为服务运行。 然后Nginx将PHP的所有请求推送到PHP处理程序并接收响应。

问题: PHP-FPM不适用于Windows (从5.4.9开始)。 FPM是一个整洁的小程序管理器,它在后台进行处理,并在处理请求时管理PHP进程的产卵和查杀。

因为这是不可能的,在Windows上,我们一次只能处理一个请求,类似于这里遇到的问题 。

在我的情况下,发生以下情况:在sometestsite.com上的应用程序中调用一个页面,调用127.0.0.1:9000上的php-cgi.exe sometestsite.com 。 在里面,一个CURL请求在endpoint.sometestsite.com上调用一个页面。 但是,我们无法产生任何新的PHP进程来处理第二个请求。 通过提供运行CURL请求的请求来阻止原始的php-cgi.exe。 所以,我们陷入僵局,一切都超时了。

我使用的解决方案(这几乎是一个黑客)是使用这个python脚本来产生10个PHP进程。

然后在nginx中使用上游模块(根据脚本的文档)告诉nginx有10个进程可用。

事情然后完美地工作。

话虽如此,请不要在生产环境中使用它(您可能更适合在Linux上运行nginx和php-fpm)。 如果你有一个繁忙的网站,10个进程可能是不够的。 但是,很难知道你需要多少个进程。

但是,如果你坚持在Windows上运行php的nginx,考虑在本教程中运行Cygwin中的PHP-FPM。

请确保您在用于运行cgi进程的同一用户的控制台上运行脚本。 如果他们不一样 – 他们可能有不同的权限。 对我来说问题是在防火墙规则,不允许开放的外部连接的所有者的CGI进程。