在PHP中并行处理/分叉以加速检查大型数组

时间:2014-07-04 18:23:19

标签: php optimization fork

我的网站上有一个php脚本,旨在提供用户输入的域名的精彩概述。它做得很好,但速度很慢。这可能与它检查64个可能的域名数组的事实有关,然后继续检查名称服务器的A记录/ MX记录/ NS记录等。

我想知道的是,是否可以运行多个线程/子进程?这样它会一次检查数组的多个元素,并生成输出更快的丢失?

我已将我的代码示例放在一个pastebin中(所以为了避免在这里创建一个巨大的垃圾邮件帖子) http://pastebin.com/Qq9qKtP9

在perl我可以这样做:

  $fork = new Parallel::ForkManager($threads);
  foreach(Something here){
  $fork->start and next;
  $fork->finish;
  }

我可以根据需要在多个进程中运行循环。在PHP中可以用类似的东西或者你能想到的任何其他方式加快速度吗?主要问题是,cloudflare有一个超时,并且通常需要足够长的CF阻止响应发生。

由于

3 个答案:

答案 0 :(得分:3)

*从不介意支持!! *

从不想直接回复网络请求时创建线程(或其他相关流程)。

如果指示您的前端每次有人点击page.php时创建60个主题,并且有100个人同时请求page.php,那么您将要求您的硬件创建并执行6000个主题同时,更不用说操作系统服务和其他软件使用的线程。出于显而易见的原因,这不会,也永远不会扩展。

相反,您希望将需要其他线程或进程的应用程序部分分离出来,并通过某种理智的RPC与应用程序的这一部分进行通信。这意味着应用程序的后端可以通过pthreads或forking使用并发,使用固定数量的线程或进程,并在所有可用资源上尽可能均匀地分布工作。这允许流量大量涌入;它允许您的应用程序扩展。

我不会编写示例代码,但这似乎太琐碎了。

答案 1 :(得分:1)

您要做的第一件事是优化代码以尽可能缩短执行时间。 例如,而不是进行五个dns查询: $NS = dns_get_record($murl, DNS_NS); $MX = dns_get_record($murl,DNS_MX); $SRV = dns_get_record($murl,DNS_SRV); $A = dns_get_record($murl,DNS_A); $TXT = dns_get_record($murl,DNS_TXT);

您只能拨打 dns_get_record 一次: $DATA = dns_get_record($murl, DNS_NS + DNS_MX + DNS_SRV + DNS_A + DNS_TXT); 并从那里解析变量。

我没有直接分叉进程同时处理多个部分,而是实现了一个队列,所有请求都会被推入。查询处理器将限制它可以同时处理多少项,如果数百或数千个请求同时到达您的站点,则可以避免潜在的DoS。如果没有某种限制机制,您最终会得到许多服务器可能会挂起的进程 对于处理器,除了前面提到的项目之外,您还可以尝试使用pecl/Gearman作为队列处理器。我还没有使用它,但似乎做了你正在寻找的东西。

另一种优化方法是实现一个缓存系统,该系统可以保存一周(或其他)的结果。这会减少在一天内重复查找同一网站的人(或在您的网站上运行脚本)

答案 2 :(得分:0)

我怀疑用PHP分叉apache进程是个好主意。但是如果你真的想要PCNTL(apache模块中没有)。

pthread你可能会有更多乐趣。现在你甚至可以下载声称是线程安全的PHP。

最后你有可能使用经典的non blocking IO,我更喜欢PHP。