Promise构造函数必须传入执行器函数,它立即执行并接收resolve和reject参数;.then()可处理成功与失败,但推荐用.catch()统一捕获异常;async/await是Promise语法糖,需在async函数中使用;Promise.all全成功才resolve,Promise.race以最先settled者为准。

Promise 构造函数里必须传执行器函数
Promise 不是直接调用就能跑起来的,它需要一个「执行器函数」(executor),也就是 new Promise(fn) 中那个 fn。这个函数会立即执行,且接收两个参数:resolve 和 reject —— 它们是 Promise 内部提供的回调,不是你随便定义的变量。
常见错误是漏写执行器、或把异步逻辑写在 new Promise 外面:
const p = new Promise(); // ❌ 报错:executor is required
const p = new Promise(() => {
setTimeout(() => resolve('done'), 100); // ❌ resolve is not defined
});
正确写法:
const p = new Promise((resolve, reject) => {
setTimeout(() => resolve('done'), 100);
});
-
resolve触发 fulfilled 状态,值会传给后续.then() -
reject触发 rejected 状态,等价于抛出异常,会被.catch()或.then(null, fn)捕获 - 执行器中若抛出未捕获错误,Promise 自动进入 rejected 状态
.then() 的两个参数分别处理成功和失败
.then() 接收两个可选函数:第一个处理 fulfilled 值,第二个处理 rejected 原因。很多人只写第一个,结果错误被吞掉:
立即学习“Java免费学习笔记(深入)”;
p.then( value => console.log(value), reason => console.error(reason) // ✅ 显式处理错误 );
但更推荐统一用 .catch(),因为:
-
.catch(fn)等价于.then(null, fn),语义更清晰 - 它能捕获前面任意
.then()中抛出的错误(链式调用中的异常冒泡) - 避免在每个
.then()都重复写错误处理逻辑
注意:.catch() 只捕获 Promise rejection,不捕获同步 throw(除非 throw 发生在 Promise 执行器或 .then() 回调里)。
async/await 是 Promise 语法糖,不是替代品
async 函数返回的是 Promise 对象,await 后面的表达式必须是 Promise(或可转为 Promise 的值)。它只是让 Promise 链写起来像同步代码,底层没变。
常见误区:
-
await不能用在普通函数里,必须包裹在async函数中 -
await后面如果是普通值(如await 42),会自动包装成Promise.resolve(42) - 想并发执行多个 Promise,别写成
await p1; await p2;(串行),改用await Promise.all([p1, p2])
错误示例:
function fetchUser() {
return await fetch('/user'); // ❌ SyntaxError:await only valid in async function
}
正确写法:
async function fetchUser() {
const res = await fetch('/user');
return res.json();
}
Promise.all 和 Promise.race 的行为差异很关键
两者都接受 Promise 数组,但失败策略完全不同:
-
Promise.all([p1, p2, p3]):全部 fulfilled 才 resolve;只要一个 rejected,就立刻 reject(带第一个失败的 reason) -
Promise.race([p1, p2, p3]):哪个 Promise 先 settle(fulfill 或 reject),就以它的结果为准
典型误用场景:用 Promise.race 做超时控制时,忘了它也会把先发生的 rejection 当作 race 结果。如果请求本身很快失败,超时逻辑就失效了。
安全的超时写法要确保 timeout Promise 只可能 fulfill,不能 reject:
const timeout = (ms, promise) =>
Promise.race([
promise,
new Promise((_, reject) =>
setTimeout(() => reject(new Error('timeout')), ms)
)
]);
真正容易被忽略的是:Promise 链一旦进入 rejected 状态,又没被 .catch() 拦住,就会变成 unhandled rejection —— 浏览器控制台报黄警告,Node.js 可能直接退出进程。别依赖全局 unhandledrejection 事件兜底,该 catch 的地方必须显式处理。











