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

React中使用Promise.all批量发起Apollo查询耗时随请求数增长问题

问题成因
  • 代码逻辑错误:你定义的async function getTimeSeriesQuery(i)没有返回apollo.query的执行结果,导致你推入promises数组的都是立即完成的空Promise,Promise.all(promises)的完成时机根本不绑定实际请求的返回状态,你实际统计的是所有请求串行排队/返回的总耗时,而非并行请求的耗时。
  • 浏览器同域名并发限制:HTTP/1.1协议下浏览器对同一个域名的并行请求数限制通常为6个,超过限制的请求会进入浏览器的待发送队列排队等待,若你的请求数量远大于6,总耗时会近似于Math.ceil(请求总数/6)*单请求耗时,呈现线性增长特征。
  • 客户端/服务端限制:Apollo Client如果配置了请求限流、批处理延迟规则,或者服务端对同一客户端的请求做了频率限制、串行处理逻辑,也会导致请求无法真正并行,总耗时线性增长。
  • HTTP协议队头阻塞:如果接口未启用HTTP/2,HTTP/1.1的TCP队头阻塞问题也会加剧高并发请求下的耗时增长。
优化方案
  • 修复基础代码错误:调整getTimeSeriesQuery的逻辑,返回请求对应的Promise,确保Promise.all能正确等待所有请求完成,修正后的代码如下:
// 去掉无用的async标识,直接返回query的Promise
function getTimeSeriesQuery(i) {
  return apollo.query(getChunkQueryOptions(i))
}

const promises = []
// 把var改为let避免循环变量共享问题
for(let i = 0; i < numberChunks; i++) {
  promises.push(getTimeSeriesQuery(i))
}

// 需要await或者加.then才能拿到实际返回数据
const data = await Promise.all(promises)
  • 控制请求并发数:不要一次性发起所有请求,手动实现并发控制器或者引入工具库限制同时发送的请求数(通常设为5~6适配HTTP/1.1的并发限制),避免请求在浏览器队列排队产生额外耗时。
  • 合并请求:如果服务端支持,开启Apollo Client的请求批处理能力,将多个分片的GQL查询合并为单个请求发送,直接将总耗时降低到接近单请求的水平。
  • 优化协议和服务端配置:接口启用HTTP/2,解除同域名并发数限制;协调服务端调整限流策略,允许合理范围内的并行请求。
  • 调整分片策略:适当调大单个请求的时序数据分片大小,降低总请求数,从根源上减少多请求带来的额外开销。

内容的提问来源于stack exchange,提问作者Mohamad Abdel Rida

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.27 04:06:04