You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

GuzzleHttp 6.3.2异步请求性能疑问:100个GET请求耗时50秒是否正常?

关于Guzzle 6.3.2异步请求耗时的问题解答

嘿,这个情况我太熟悉了——先给你明确结论:这个表现肯定不是正常的异步并发效果,正常来说100个各耗时5秒的异步请求,总耗时应该接近5秒(忽略连接建立这类微小开销)。你现在用了50秒,说明你的请求其实是分批串行执行的,核心问题出在并发数的配置上。

咱们来拆解一下:

  • 50秒总耗时 ÷ 单个请求5秒耗时 = 10,这意味着你的Guzzle实际上是同时跑10个请求,100个请求分成10批,每批5秒,加起来就是50秒。这明显是并发数被限制了,没有真正把异步的威力发挥出来。

为什么会出现这种情况?

Guzzle 6.x的Pool组件(用来管理批量异步请求的核心工具)默认会限制并发数——它不会无限制地同时发起所有请求,而是会根据默认配置或者系统资源情况控制并发量。如果你没有显式设置concurrency参数,它可能会默认使用一个保守的值(比如10),这就导致了请求分批执行。

怎么解决?

很简单,在创建Pool的时候显式设置足够大的concurrency参数(比如直接设为100,当然要考虑你的系统和目标服务端的承受能力——服务端得能扛住100个并发请求才行)。

给你个示例代码参考:

use GuzzleHttp\Client;
use GuzzleHttp\Pool;
use GuzzleHttp\Psr7\Request;

// 初始化客户端
$client = new Client();

// 生成100个GET请求
$requestsGenerator = function ($totalRequests) {
    $targetUrl = 'http://your-server.com/your-sleep-endpoint';
    for ($i = 0; $i < $totalRequests; $i++) {
        yield new Request('GET', $targetUrl);
    }
};

// 创建请求池,显式设置并发数为100
$pool = new Pool($client, $requestsGenerator(100), [
    'concurrency' => 100,
    'fulfilled' => function ($response, $index) {
        // 处理成功的响应,比如记录日志或解析数据
        echo "请求{$index}完成,状态码:{$response->getStatusCode()}\n";
    },
    'rejected' => function ($reason, $index) {
        // 处理失败的请求,比如记录错误
        echo "请求{$index}失败:{$reason->getMessage()}\n";
    },
]);

// 启动池并等待所有请求完成
$pool->promise()->wait();

额外注意事项

  1. 系统文件描述符限制:每个HTTP请求都会占用一个套接字(对应系统的文件描述符),如果你的系统ulimit设置过低(比如默认可能是1024,100个并发完全没问题,但如果更高的话需要调整),可能会导致请求失败。
  2. 服务端承受能力:虽然你用sleep(5)模拟响应,但服务端得能同时处理100个并发请求才行,如果服务端本身有连接数限制,那即使Guzzle并发拉满,服务端也会排队,总耗时还是会增加。

调整完并发数后,你应该能看到总耗时接近5秒,这才是异步请求该有的表现~

内容的提问来源于stack exchange,提问作者bijiDango

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.25 07:57:37