好的,请原谅我,如果这是另一个问题的重复,但在搜索后我没有找到一个明确的答案。我基本上想要做的是让我的php web应用程序触发一些事件(如电子邮件或报告生成器)可能需要几分钟才能完成并立即将控制权返回给页面。我来自.NET世界,可以通过线程轻松完成。
所以这是工作流程:
实现这一目标的最佳方法是什么?简短的回答很好。我不想为我编写代码,只是一些指导。我查看了shell_exec,但我不确定这是否是最佳方式,或者是否,如何使用它来处理Web应用程序中的功能。 (如果这有任何区别,我正在使用Yii框架)。感谢。
-Jason
答案 0 :(得分:2)
在PHP中启动新的线程线程的最佳(也是唯一的AFAIK)方法是使用curl之类的东西创建一个新的PHP请求。
$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'http://www.yoursite.com/background-script.php');
curl_setopt($ch, CURLOPT_FRESH_CONNECT, true);
curl_setopt($ch, CURLOPT_TIMEOUT_MS, 1);
curl_exec($ch);
curl_close($ch);
这将运行脚本,并立即返回页面。当然没有回调,所以最好的办法是将background-script.php的输出放入数据库,然后经常从客户端ping数据库,直到看到结果为止。
答案 1 :(得分:2)
我们在这里创建了一个函数,它返回浏览器的答案并继续执行。我们使用它发送电子邮件而不让用户等待它。
public function redirectAndContinue( $url )
{
ignore_user_abort(true);
header("Location: $url");
header("Connection: close");
header("Content-Length: 0");
flush();
}
您可以像这样使用它
// do quick basic stuff to validate your report
$this->redirectAndContinue( $url )
// send your email or do other slow stuff
问题是:它不适用于AJAX,它必须是常规页面请求(可能带有POST)。但是你仍然可以创建进度条:在数据库或会话中保存一些东西,然后继续调用一些URL来通过AJAX获得进度。
答案 2 :(得分:1)
据我记忆,shell_exec或exec将阻止PHP脚本的执行,直到进程终止。 解决方案是添加“&”在命令结束时,您的脚本/程序将被后台化。
"/usr/report.sh &"
我使用类似的东西从PHP运行外部工具,但通过中间脚本来控制PID,实例数... 不能说它是否在Windows主机下运行。
答案 3 :(得分:0)
我可以建议Gearman吗?您可以将作业提交给齿轮箱服务器并请求状态。
Gearman提供了一个分布式应用程序框架,用于处理多台机器或进程。它允许应用程序并行完成任务,负载平衡处理和语言之间的函数调用。该框架可用于各种应用程序。 Gearman是多线程的,已知能够每秒执行5万个工作。
快速教程在这里:http://www.sitepoint.com/introduction-gearman-multi-tasking-php/
它也很容易上手,所有代码都将使用PHP。