
本文深入解析在 async-await 模式下,return await 与直接 return promise 的本质区别,阐明为何省略 async/await 反而更高效,并提供可立即落地的函数设计规范。
本文深入解析在 async-await 模式下,`return await` 与直接 `return promise` 的本质区别,阐明为何省略 `async`/`await` 反而更高效,并提供可立即落地的函数设计规范。
在 JavaScript 的异步编程中,async 函数本质上是语法糖——它自动将返回值包装为 Promise,并隐式捕获异常。因此,一个 async 函数内部若已返回一个 Promise(如 response.json()),再用 await 等待它、然后 return,不仅多余,还会引入不必要的微任务延迟和额外的 Promise 包装层。
以问题中的两个案例为例:
-
Case A(不推荐) 中,
getFolders()和getUserProfile()被声明为async,且内部使用return await fetchData(...)。这导致:-
fetchData()已返回 Promise(response.json()是 Promise); -
await强制等待该 Promise 解析,得到实际数据后,async函数再将其重新包装为新 Promise 返回; - 结果:多一次 Promise 构造 + 多一次微任务调度,纯属冗余。
-
Case B(推荐) 中,
getFolders()和getUserProfile()是普通函数,直接return fetchData('folder')。由于fetchData()本身是async函数,其返回值天然就是 Promise,因此调用方拿到的仍是可await的 Promise,语义与 Case A 完全一致,但执行路径更短、性能更优。
✅ 正确写法(优化后的 Case B)如下:
const BASE_URL = "https://bootcamp-api.codeit.kr/api";
export async function fetchData(endpoint) {
const response = await fetch(`${BASE_URL}/sample/${endpoint}`);
if (!response.ok) {
throw new Error(`HTTP ${response.status}: ${response.statusText}`);
}
return response.json(); // ✅ 直接返回 Promise,无需 await
}
// ✅ 普通函数即可 —— 因为 fetchData 已返回 Promise
export function getFolders() {
return fetchData('folder');
}
export function getUserProfile() {
return fetchData('user');
}
⚠️ 关键注意事项:
-
永远避免
return await expression:除非你需要在返回前同步处理解析后的值(如日志、转换、条件抛错),否则它只会拖慢执行、增加内存开销。 -
函数是否需声明
async,取决于你是否在函数体内await或throw异步错误:若仅作 Promise 透传,普通函数更轻量。 -
调用方体验完全一致:无论
getFolders()是async还是普通函数,调用者均可await getFolders()或.then(),因为二者都返回 Promise。
总结:异步函数的设计应遵循“最小封装原则”——只在必要时 await,只在必要时声明 async。精简 return await 不仅提升性能,更让代码意图更清晰、调试链路更直接。










