Promise的catch能捕获网络错误、HTTP状态码错误(需手动检查response.ok后throw)、JSON解析异常及then中主动throw的错误;它本质是.then(undefined, onRejected)的语法糖,仅监听rejection状态。

Promise 的 catch 方法专门用于捕获异步操作中抛出的错误,包括网络请求失败、JSON 解析异常、手动 throw 的错误等。它本质是 .then(undefined, onRejected) 的语法糖,只监听 rejection 状态。
catch 能捕获哪些错误
只要 Promise 链中任意一环发生 reject(无论是 fetch 失败、await 抛错,还是手动调用 reject() 或 throw),后续的 catch 都能捕获到:
- HTTP 状态码非 2xx(如 404、500),但注意:fetch 默认不会因状态码 reject,需手动检查
response.ok - 网络中断、跨域拒绝、DNS 失败等底层错误
-
response.json()解析非法 JSON 时抛出的 SyntaxError - 在
then回调里主动throw new Error('...')
正确写法:链式 catch 和 async/await 中的 try-catch
两种主流写法都可靠,关键是位置和作用域:
-
链式写法:把
catch放在 Promise 链末尾,它会捕获前面所有then中的同步错误和异步 reject -
async/await 写法:用
try/catch包裹 await 表达式,catch 捕获被 await 的 Promise 的 rejection
示例(链式):
立即学习“Java免费学习笔记(深入)”;
fetch('/api/data').then(res => {
if (!res.ok) throw new Error(`HTTP ${res.status}`);
return res.json();
})
.then(data => console.log(data))
.catch(err => console.error('请求出错了:', err.message));
示例(async/await):
async function loadData() {try {
const res = await fetch('/api/data');
if (!res.ok) throw new Error(`HTTP ${res.status}`);
const data = await res.json();
console.log(data);
} catch (err) {
console.error('请求出错了:', err.message);
}
}
容易忽略的坑
-
fetch 不会自动 reject 错误状态码:404、500 等仍算“成功响应”,必须手动判断
res.ok或res.status >= 400后throw - 多个 catch 只触发一次:Promise 一旦被 catch,后续链会恢复为 fulfilled 状态,除非 catch 里再次 throw
-
不要漏掉 finally:需要统一收尾(如关闭 loading)时,配合
finally()更清晰
如何让错误更易排查
仅打印 err.message 往往信息不足。建议:
- 打印完整 error 对象:
console.error(err)(现代浏览器可展开查看堆栈) - 对 fetch 错误补充 URL 和 method:
console.error('API 请求失败', url, err) - 业务错误可自定义 Error 类或添加 code 字段,便于分类处理


















