JavaScript 教程:深入理解 Promise API 的 6 个静态方法
前言
在现代 JavaScript 开发中,Promise 已经成为处理异步操作的核心工具。Promise API 提供了 6 个非常实用的静态方法,它们可以帮助我们优雅地处理各种异步场景。本文将深入讲解这些方法的使用场景和区别。
1. Promise.all:并行执行多个 Promise
Promise.all 是最常用的方法之一,它允许我们并行执行多个 Promise,并等待所有 Promise 都完成。
基本用法
let promise = Promise.all([promise1, promise2, promise3]);
特点
- 当所有 Promise 都成功解决时,返回一个包含所有结果的数组
- 结果的顺序与传入的 Promise 顺序一致
- 如果任何一个 Promise 被拒绝,整个
Promise.all会立即被拒绝
实际应用示例
假设我们需要同时获取多个用户的信息:
let userIds = [1, 2, 3];
let userPromises = userIds.map(id => fetch(`/api/users/${id}`));
Promise.all(userPromises)
.then(responses => Promise.all(responses.map(r => r.json())))
.then(users => {
// 处理所有用户数据
})
.catch(error => {
// 处理错误
});
2. Promise.allSettled:获取所有 Promise 的最终状态
Promise.allSettled 是 ES2020 新增的方法,它不会因为某个 Promise 被拒绝而中断。
基本用法
let promise = Promise.allSettled([promise1, promise2]);
特点
- 等待所有 Promise 完成(无论成功或失败)
- 返回一个对象数组,每个对象包含:
status: "fulfilled" 或 "rejected"value(如果成功)或reason(如果失败)
实际应用示例
Promise.allSettled([
fetch('/api/user'),
fetch('/api/products'),
fetch('/invalid-url')
]).then(results => {
results.forEach(result => {
if (result.status === 'fulfilled') {
console.log('成功:', result.value);
} else {
console.log('失败:', result.reason);
}
});
});
3. Promise.race:竞速模式
Promise.race 返回第一个完成的 Promise(无论成功或失败)。
基本用法
let promise = Promise.race([promise1, promise2]);
特点
- 返回第一个完成的 Promise 的结果
- 其他 Promise 的结果会被忽略
- 常用于设置超时机制
实际应用示例
// 设置请求超时
let fetchPromise = fetch('/api/data');
let timeoutPromise = new Promise((_, reject) =>
setTimeout(() => reject(new Error('请求超时')), 5000)
);
Promise.race([fetchPromise, timeoutPromise])
.then(data => console.log(data))
.catch(error => console.error(error));
4. Promise.any:获取第一个成功的 Promise
Promise.any 是 ES2021 新增的方法,它返回第一个成功解决的 Promise。
基本用法
let promise = Promise.any([promise1, promise2]);
特点
- 忽略所有被拒绝的 Promise,直到第一个成功的 Promise
- 如果所有 Promise 都被拒绝,返回一个 AggregateError
- 适用于需要从多个备用源获取数据的场景
实际应用示例
Promise.any([
fetch('https://source1.com/data'),
fetch('https://source2.com/data'),
fetch('https://source3.com/data')
]).then(data => {
// 使用第一个成功的响应
}).catch(error => {
// 所有请求都失败了
console.error(error.errors); // 查看所有错误
});
5. Promise.resolve 和 Promise.reject
这两个方法用于创建已解决或已拒绝的 Promise。
Promise.resolve
// 创建一个已解决的 Promise
let resolvedPromise = Promise.resolve('成功值');
// 等同于
let resolvedPromise = new Promise(resolve => resolve('成功值'));
Promise.reject
// 创建一个已拒绝的 Promise
let rejectedPromise = Promise.reject(new Error('失败原因'));
// 等同于
let rejectedPromise = new Promise((_, reject) => reject(new Error('失败原因')));
使用场景
- 确保函数总是返回 Promise
- 在测试中创建模拟的 Promise
- 将同步值转换为 Promise
方法对比总结
| 方法 | 描述 | 成功条件 | 失败条件 |
|---|---|---|---|
Promise.all | 所有 Promise 都成功 | 返回结果数组 | 任一失败立即拒绝 |
Promise.allSettled | 所有 Promise 都完成(无论成功或失败) | 返回状态对象数组 | 不会拒绝 |
Promise.race | 第一个完成的 Promise(无论成功或失败) | 返回第一个结果 | 返回第一个错误 |
Promise.any | 第一个成功的 Promise | 返回第一个成功结果 | 所有都失败才拒绝 |
Promise.resolve | 创建一个已解决的 Promise | 总是成功 | 不适用 |
Promise.reject | 创建一个已拒绝的 Promise | 不适用 | 总是失败 |
最佳实践建议
- 数据并行获取:使用
Promise.all同时获取多个不相关的数据 - 容错处理:使用
Promise.allSettled当需要知道每个 Promise 的最终状态 - 超时控制:使用
Promise.race实现请求超时机制 - 备用数据源:使用
Promise.any从多个备用源获取数据 - API 兼容:使用
Promise.resolve确保函数总是返回 Promise
理解这些 Promise 静态方法的区别和适用场景,将帮助你编写更健壮、更高效的异步 JavaScript 代码。
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考



