async函数中try...catch可捕获await的promise拒绝错误,需确保所有异步操作都await且不遗漏末端错误;未await的promise错误会触发unhandledrejection事件。

在 async 函数中直接用 try...catch 就能捕获 await 表达式抛出的异常,关键在于确保所有异步操作都经过 await,且不漏掉 Promise 链末端的错误。
正确写法:await 放在 try 块里
async 函数内部的 try...catch 可以捕获被 await 的 Promise 被 reject 时的错误,等价于 .catch():
- ✅ 正确:对每个可能失败的 await 调用做包裹
- ❌ 错误:把整个 async 函数体包进 try(语法不允许)
- ❌ 错误:忘记 await,导致 catch 捕不到(返回的是 pending Promise,不是值或错误)
示例:
async function fetchUserData() {
try {
const res = await fetch('/api/user');
if (!res.ok) throw new Error(`HTTP ${res.status}`);
const user = await res.json();
return user;
} catch (err) {
console.error('获取用户失败:', err.message);
throw err; // 或返回默认值、重试、上报等
}
}
处理多个异步操作:按需 await,避免竞态
多个请求之间有依赖时,逐个 await 是最清晰安全的方式;若无依赖,可并行发起再统一 await,但要小心错误传播:
- ✅ 并行 + 全部 await:用
Promise.all([p1, p2]),任一失败则整体 reject - ✅ 并行 + 容错:用
Promise.allSettled([p1, p2]),始终 resolve,检查每个结果的status - ⚠️ 避免:只 await 第一个,其余丢给后台执行(可能漏错、内存泄漏、状态不一致)
封装通用错误处理逻辑
重复的 try/catch 可抽象为高阶函数或自定义 Hook(React):
- 写一个
safeAwait(fn),返回[data, error]元组(类似 Go) - 在框架中(如 Express),用中间件统一捕获路由层 async 错误
- 对特定错误类型(如网络超时、401)做差异化响应
简单封装示例:
function safeAwait(promise) {
return promise
.then(data => [data, null])
.catch(err => [null, err]);
}
// 使用
const [user, err] = await safeAwait(fetchUser());
if (err) handleUserFetchError(err);
注意边界情况
有些错误不会被 try/catch 捕获,需额外防范:
- 未 await 的 Promise 内部错误 → 成为 unhandled rejection,触发
unhandledrejection事件 - async 函数外抛出同步错误(如参数校验失败)→ 会立即 throw,仍可被外层 try/catch 捕获
- 定时器、事件监听器里的异步错误 → 不在当前 async 上下文,需各自处理
建议加全局兜底:
window.addEventListener('unhandledrejection', event => {
console.error('未捕获的 Promise 错误:', event.reason);
// 上报、提示用户、降级等
});
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











