从PHP安全地分叉

时间:2010-12-11 20:31:50

标签: php bash fork

从开始,让我说我试图避免使用pcntl_fork()

对于这个例子,让我们想象一下,我正在尝试分叉'dig'命令行应用程序的许多实例。实际上,相同的脚本将用于不同的命令行应用程序。

现在我正在使用php exec 并将& 附加到命令中,以便bash在后台运行它。

E.g

exec("dig google.com &");
exec("dig yahoo.com &"); 

依旧......

这成功创建了多个挖掘并行运行的流程。

我遇到的问题是进程数量稳步上升,直到系统崩溃。基本上它是一个叉炸弹。

我试图通过使用ps ax | wc -l来检查正在运行的进程数来解决这个问题 如果它低于X,则仅启动更多。

例如(在循环中运行)

if 80 processes are running, i'll launch another 20. 
if 70 processes are running, i'll launch another 30.

问题是,即使进行了此检查,流程数量也会持续增加,直到系统崩溃或遇到操作系统最大用户进程

任何人都可以给我一些提示,告诉我如何在不强奸所有系统资源的情况下有效地分叉(大规模)吗?我不明白为什么这个当前的方法不起作用。

2 个答案:

答案 0 :(得分:1)

由于您有管理流程,我建议您查看已创建的子流程。保存你开始的每个下标的PID:

$running[] = exec("process www.google.com &  echo $!");

其中$!将返回后台进程的PID,将其添加到PHP中的列表中。然后在管理循环中,只需重新检查进程是否仍处于活动状态:

do {
    foreach ($running as $i=>$pid) {
        if (!posix_getpgid($pid)) {
             unset($running[$i]);
             // restart
        }
}   }

我不认为它非常优雅或可靠。 pcntl_fork通常是更好的方法,但你不能详细说明你的实际脚本。但也许这适用于你的情况。

答案 1 :(得分:0)

您可能还想使用uptime来检查系统负载。