在PHP中使用长轮询时,例如
$start_time = time();
while ((time() - $start_time) < 30) {
if ($db->getNewStuff()->rows > 0) {
$response = "new stuff!";
break;
}
usleep(1000000);
}
echo $response;
你如何评价你“多长时间”“投票”?在这个例子中,我选择了30秒,因为......好吧,我甚至不知道为什么。
使用更长时间的民意调查,几分钟或类似情况会产生什么影响? Apache会崩溃吗?我的应用程序是否会出现滞后/卡住/降低性能?
此外:流程usleep
需要多长时间?
答案 0 :(得分:2)
您的PHP脚本可能无法存活那么久,具体取决于time limit。所以,一定要(重新)设定时间限制。否则我没有看到任何增加时间的问题。
至于usleep
应该有多长,这是你需要自己进行基准测试的东西。较短的微睡眠会增加服务器负载,但会更快地找到结果。什么是合适的取决于您的应用程序的其余部分和您的资源。您甚至可能希望根据服务器负载改变微睡眠时间(即在服务器负载较高时使其睡眠时间更长)。
答案 1 :(得分:2)
您可以轻松地使可用的apache进程/ workwer饱和。 例如,如果apache配置如下所示:
StartServers 2
MinSpareServers 4
MaxSpareServers 8
ServerLimit 11
MaxClients 11
MaxRequestsPerChild 4000
您只需投放11个请求广告即可在最后30秒内无法访问您的网站。 如果你只是寻找一个概念证明,可以使用apache和PHP,但在真正的服务器上,你真的避免使用PHP - > Apache长轮询。
您需要使用类似comet环境的内容来获得可扩展的解决方案
答案 2 :(得分:1)
当调用usleep()时,php会在睡眠过期之前不执行任何操作。
通常默认的最大脚本执行时间是30秒,但sleep()和usleep()会持续更长时间,因为技术上PHP在睡眠操作期间没有控制权。
从未尝试过几分钟 - 从未遇到任何问题。
如果它很忙并且让很多线程进入睡眠状态,那么可能会用完线程来处理其他请求......
答案 3 :(得分:1)
您提供的代码不是长时间轮询。长轮询是指允许客户端等待某些内容,并允许您的用户界面立即响应服务器上的事件。
客户端发出常规的ajax请求。您的服务器代码可能会等待,或者可能会立即响应。
如果没有什么可以返回(还),它只会使响应需要更长时间才能响应。如果发生某些等待事件,它会立即发送响应。
客户端轮询您的ajax请求,该请求在某些事件发生之前不会响应,但是当该事件发生时,它会立即响应。预计客户将立即转身并立即执行另一个长轮询请求。
因此,您通常在长轮询协议中使用序列号。为每个事件分配一个序列号,较新的事件具有比旧事件更高的序列号。如果你可以安排,那么你可以让长时间的民意调查成为自从id&#34;请求。如果有错过的事件,它会立即返回。如果他们给你最新的序列号,那么没有什么可以返回,所以不要回复任何回复,只需要花更长的时间。
如果多个事件在长轮询之间潜入,则您的民意调查将返回多个事件记录。
这需要某种方式让您的代码通知事件通知正在等待发送响应的代码。您可以将其实现为对键值存储的合理速率轮询,某种进程间通信,或适合重复使用的轻量级内容。
由于其流程模型,您在PHP中的选项有限。在nodejs或另一个单进程服务器体系结构中,您可以使用一组简单的响应等待结果,并将它们全部调用,尊重每一个&#34;因为&#34;参数,当发生新事件时。
聊天客户端就是典型的例子。聊天页面上的所有人都有一个长时间的民意调查,需要很长时间才能得到答复。页面工作正常,只是网络请求在后台花时间。
当有人键入消息时,他们会将消息发布到服务器,然后处理程序会插入带有下一个id的消息。所有长期民意调查都会注意到新记录大于&#34;因为&#34;他们正在寻找的价值,他们会立即发送一个响应,所有记录的ID都大于&#34;因为&#34;参数。基本上在短时间内通知所有其他聊天参与者,而不是让他们自己不断检查新消息。
答案 4 :(得分:0)
你应该考虑使用Node和Socket.io。 :)
答案 5 :(得分:0)
总响应间隔为20秒以上会使您的应用程序容易出现浏览器超时。保持在20秒或以下 - 只是为了安全起见。