PHP:非阻塞shell_exec WITH命令输出

时间:2014-08-06 02:58:34

标签: php linux apache bash nginx

我正在使用php的shell_exec来调用bash文件,系统程序和Ksh文件。

shell_exec的一个问题是,如果您需要输出,您的Web服务器将锁定(即,不会提供新请求),直到该过程完成。一个常见的技巧是将进程设置为在后台运行(> / dev / null 2> / dev / null&),但这当然会丢弃任何输出。

我尝试从apache切换到nginx,认为这可以解决我的问题,但潜在的问题似乎是php的shell_exec阻止i / o。即使使用nginx,shell_exec也会完全阻止任何新的http请求。

有没有人知道如何在不锁定服务器的情况下使用php进行系统调用,同时还能捕获输出?

我正在考虑建立一个管理异步系统调用的库,以便稍后使用Ajax检索输出。

但我不想走那条路。有什么建议吗?

5 个答案:

答案 0 :(得分:1)

这是常见的会话问题。

默认情况下,当会话启动时,php锁定会话文件,直到会话关闭。所有其他请求等待解锁会话文件以继续。

尝试将session_write_close放在shell_exec

之前

答案 1 :(得分:1)

如何在后台运行它,但将输出重定向到文件?
您可以使用>>| tee

答案 2 :(得分:0)

可能会离开这里但是如何创建新线程? http://php.net/manual/en/class.thread.php。没有太多的PHP和Linux经验,但像这样的问题的一般解决方案是多线程您的Web应用程序

答案 3 :(得分:0)

尝试将shell执行放在带有typescript的屏幕会话中,即

shell_exec("screen -dmS scriptname /bin/bash -c /path/to/script | typescript");

然后当你想要阅读输出时:

shell_exec("sed -e 's/$/<br>/' typescript; rm typescript");

不完全确定这是否是您想要的,但我希望它有所帮助!

编辑:在sed表达式中忘了/:P

答案 4 :(得分:0)

如果您希望在外部程序运行时继续执行PHP脚本,可以使用proc_open()

如果您希望PHP脚本不阻止其他请求,则必须确保您的PHP脚本没有任何阻止其他请求被提供的锁。最常见的是会话锁定,您可以按照sectus的建议使用session_write_close()