JS动态Import失败重试代码中.then(resolve,reject)的作用及必要性疑问
关于Promise重试函数中
.then(resolve, reject)的解析 先看你提供的重试函数代码:
function retry(fn, retriesLeft = 5, interval = 1000) { return new Promise((resolve, reject) => { fn() .then(resolve) .catch((error) => { setTimeout(() => { if (retriesLeft === 1) { reject(error); return; } retry(fn, retriesLeft - 1, interval).then(resolve, reject); }, interval); }); }); }
一、.then(resolve, reject) 是怎么工作的?
每次递归调用retry()都会返回一个全新的Promise对象。.then(resolve, reject)的作用是把当前外层Promise的状态控制权,完全转交给递归返回的新Promise:
- 若递归的Promise最终成功(比如后续重试
fn()执行成功),就调用外层Promise的resolve,让外层Promise同步变为成功状态,并把成功结果传递出去; - 若递归的Promise最终失败(比如最后一次重试仍失败),就调用外层Promise的
reject,让外层Promise同步变为失败状态,并把错误传递出去。
简单来说:递归Promise的最终结果是什么,当前外层Promise的结果就会跟它保持一致。
二、为什么需要这个结构?
因为每次retry()调用都会生成独立的Promise实例。如果没有.then(resolve, reject),递归调用只是执行了重试逻辑,但外层的Promise会一直处于pending状态——它的resolve和reject从未被触发,外部调用这个函数的地方永远拿不到任何结果。
举个反例,如果只写递归调用:
// 错误写法:仅执行重试,但未关联外层Promise状态 retry(fn, retriesLeft - 1, interval);
此时外层Promise的状态永远不会改变,调用retry()的代码会一直等待,永远收不到成功或失败的通知。
三、是否必须更新Promise的状态才能对外生效?
是的。Promise的核心特性就是状态一旦变更就不可修改,且只有当状态从pending变为fulfilled(成功)或rejected(失败)时,外部通过.then()/.catch()注册的回调才会执行。
外层Promise是当前retry()调用返回给外部的对象,必须通过调用它的resolve或reject来改变状态,外部才能感知到重试的最终结果。.then(resolve, reject)本质是一种简洁写法,等价于手动编写:
retry(fn, retriesLeft - 1, interval) .then(result => resolve(result)) .catch(err => reject(err));
因为resolve本身就是接收成功结果的回调,reject本身就是接收错误的回调,直接传入.then()可以省去冗余的包装函数。
内容的提问来源于stack exchange,提问作者user469485
相关产品推荐
相关产品推荐

