除了Promise.all和Promise.race,还有哪些处理多个异步操作的方法?

简介: 除了Promise.all和Promise.race,还有哪些处理多个异步操作的方法?

除了 Promise.all()Promise.race(),JavaScript 还提供了其他专门处理多个异步操作的 Promise 静态方法,以及一些基于 Promise 链式调用的模式,适用于不同的业务场景。以下是主要方法及使用场景:

一、Promise.allSettled():等待所有操作完成(无论成败)

Promise.allSettled() 会等待传入的所有异步操作全部完成(无论成功或失败),最终返回一个包含每个操作结果的数组。每个结果对象包含:

  • status"fulfilled"(成功)或 "rejected"(失败)
  • value:成功时的结果(仅 statusfulfilled 时存在)
  • reason:失败时的原因(仅 statusrejected 时存在)

适用场景:

  • 需要完整获取所有异步操作的结果(成功和失败都要处理),例如批量任务状态汇总(如批量上传文件后统计成功/失败数量)。

示例:

// 模拟多个异步操作(成功和失败混合)
const tasks = [
  Promise.resolve("任务1成功"),
  Promise.reject(new Error("任务2失败")),
  new Promise(resolve => setTimeout(() => resolve("任务3成功"), 1000))
];

Promise.allSettled(tasks).then(results => {
   
  results.forEach((result, index) => {
   
    if (result.status === "fulfilled") {
   
      console.log(`任务${
     index + 1}成功:`, result.value);
    } else {
   
      console.error(`任务${
     index + 1}失败:`, result.reason.message);
    }
  });
});

二、Promise.any():等待第一个成功的操作

Promise.any() 接收多个 Promise,等待第一个成功的操作并返回其结果;如果所有操作都失败,则返回一个包含所有失败原因的 AggregateError 错误。

适用场景:

  • 从多个备选资源中优先使用第一个可用的结果(如多 CDN 资源加载,取第一个成功返回的资源)。
  • 容错场景:允许部分操作失败,只要有一个成功即可继续执行。

示例:

// 模拟多个异步操作(1个成功,2个失败)
const apis = [
  new Promise((_, reject) => setTimeout(() => reject("接口1超时"), 1000)),
  new Promise(resolve => setTimeout(() => resolve("接口2返回数据"), 1500)),
  new Promise((_, reject) => setTimeout(() => reject("接口3错误"), 2000))
];

Promise.any(apis)
  .then(data => {
   
    console.log("成功获取数据:", data); // 输出:接口2返回数据(1.5秒后)
  })
  .catch(errors => {
   
    console.error("所有接口失败:", errors.errors); // 仅当所有操作失败时触发
  });

三、串行执行多个异步操作(基于链式调用)

如果多个异步操作存在依赖关系(后一个操作需要前一个的结果),则需要按顺序执行,可通过 then() 链式调用或 async/await 实现(本质是 Promise 的链式特性)。

适用场景:

  • 流程化异步任务(如先登录获取 token,再用 token 获取用户信息,最后用用户信息获取权限列表)。

示例(基于 then() 链式调用):

// 模拟依赖关系的异步操作
const fetchToken = () => Promise.resolve("user_token_123");
const fetchUser = (token) => Promise.resolve({
    id: 1, name: "Alice", token });
const fetchPermissions = (userId) => Promise.resolve(["read", "write"]);

// 按顺序执行:先获取token → 再获取用户 → 最后获取权限
fetchToken()
  .then(token => fetchUser(token))
  .then(user => fetchPermissions(user.id))
  .then(permissions => {
   
    console.log("最终权限:", permissions); // 输出:["read", "write"]
  });

示例(基于 async/await,更直观):

async function getPermissions() {
   
  const token = await fetchToken();
  const user = await fetchUser(token);
  const permissions = await fetchPermissions(user.id);
  console.log("最终权限:", permissions);
}
getPermissions();

总结:方法对比与选择

方法 核心特性 适用场景
Promise.all() 所有成功则返回结果数组,一个失败则整体失败 依赖所有异步操作成功的场景(如数据汇总)
Promise.race() 第一个完成(无论成败)则返回其结果 超时控制、资源竞速(如接口超时处理)
Promise.allSettled() 等待所有完成,返回每个操作的状态和结果 需完整统计成功/失败的场景(如批量任务)
Promise.any() 第一个成功则返回其结果,全失败则报错 容错场景(如多资源备选加载)
链式调用/async/await 按顺序执行,后一个依赖前一个的结果 有依赖关系的异步流程(如分步操作)

根据具体业务需求选择合适的方法,可以高效处理多异步场景,同时保证代码的可读性和健壮性。

目录
相关文章
|
7天前
|
弹性计算 关系型数据库 微服务
基于 Docker 与 Kubernetes(K3s)的微服务:阿里云生产环境扩容实践
在微服务架构中,如何实现“稳定扩容”与“成本可控”是企业面临的核心挑战。本文结合 Python FastAPI 微服务实战,详解如何基于阿里云基础设施,利用 Docker 封装服务、K3s 实现容器编排,构建生产级微服务架构。内容涵盖容器构建、集群部署、自动扩缩容、可观测性等关键环节,适配阿里云资源特性与服务生态,助力企业打造低成本、高可靠、易扩展的微服务解决方案。
1165 3
|
6天前
|
机器学习/深度学习 人工智能 前端开发
通义DeepResearch全面开源!同步分享可落地的高阶Agent构建方法论
通义研究团队开源发布通义 DeepResearch —— 首个在性能上可与 OpenAI DeepResearch 相媲美、并在多项权威基准测试中取得领先表现的全开源 Web Agent。
843 12
|
16天前
|
人工智能 运维 安全
|
5天前
|
机器学习/深度学习 物联网
Wan2.2再次开源数字人:Animate-14B!一键实现电影角色替换和动作驱动
今天,通义万相的视频生成模型又又又开源了!Wan2.2系列模型家族新增数字人成员Wan2.2-Animate-14B。
430 10
|
7天前
|
弹性计算 Kubernetes jenkins
如何在 ECS/EKS 集群中有效使用 Jenkins
本文探讨了如何将 Jenkins 与 AWS ECS 和 EKS 集群集成,以构建高效、灵活且具备自动扩缩容能力的 CI/CD 流水线,提升软件交付效率并优化资源成本。
329 0
|
14天前
|
人工智能 异构计算
敬请锁定《C位面对面》,洞察通用计算如何在AI时代持续赋能企业创新,助力业务发展!
敬请锁定《C位面对面》,洞察通用计算如何在AI时代持续赋能企业创新,助力业务发展!