done回调中JSON.parse失败需用xhr.responseText获取原始响应,trim后手动解析并try/catch捕获错误;Unexpected token u多因传入undefined,Unexpected end多因空字符串。

layui.upload.render 的 done 回调里 JSON.parse 失败怎么办
layui 本身不替你解析响应体,done 回调拿到的 res 是 layui 尝试 JSON.parse() 后的结果——如果失败,它会直接跳过 done,走 error 回调,但不会告诉你原始响应是什么。所以真要排查,得绕过 layui 的自动解析,自己抓原始字符串。
关键点:必须用 xhr.responseText,它是最原始、未被篡改的响应体字符串,比 res 可靠得多。
- 始终先
trim()再判断是否为空:if (!xhr.responseText?.trim()) - 不要依赖
res是否为 object 来判断成功;它可能是{}或undefined,毫无意义 - 在
try/catch里手动JSON.parse(xhr.responseText),捕获具体错误类型 -
response配置项(如statusName)只影响解析成功后的字段提取,对SyntaxError完全无效
Unexpected token u / Unexpected end of JSON input 怎么快速定位
这两个报错不是后端问题,而是你传给 JSON.parse() 的东西根本不是字符串。
Unexpected token u 几乎等于你传了 undefined;Unexpected end of JSON input 基本是空字符串、全是空白或 null 字符串化后的结果。
- 检查来源:是
xhr.responseText?还是localStorage.getItem('key')?或是fetch().then(r => r.json())?不同来源的“空”表现不同 - 打印
typeof raw和raw本身,别只看console.log(raw)——浏览器控制台对undefined和空字符串显示太相似 - 后端返回 HTTP 200 但 body 为空,前端无脑
res.json()就会触发Unexpected end - Node.js 里读文件没加
encoding: 'utf8',fs.readFileSync()返回 Buffer,toString() 前没处理好也容易出token u
fetch + response.json() 报 Unexpected token < 怎么办
这个 < 不是 JSON 错误,是 HTML。说明你请求的 URL 实际返回了一个 HTML 页面(比如 404 页面、登录跳转页、Nginx 默认页),而不是 JSON。
典型场景:API 路径写错、代理没配好、后端路由未匹配,或者静态资源路径和 API 路径冲突(例如请求 /api/user 却返回了 index.html)。
- 先在浏览器地址栏直接访问那个 URL,看返回的是 JSON 还是 HTML
- 检查 Network 面板里该请求的 Response Headers,确认
Content-Type是application/json,不是text/html - 避免在
fetch().then(r => r.json())前不做r.ok或r.status判断 - 更稳妥的做法:先
r.text(),再手动JSON.parse(),这样你能看到原始 HTML 内容,立刻知道哪错了
封装一个防崩的 JSON 解析工具函数
别每次都在业务里写重复的 try/catch,抽成函数更可控。
function safeJsonParse(str, fallback = null) {
if (typeof str !== 'string' || !str.trim()) return fallback;
try {
return JSON.parse(str);
} catch (e) {
console.warn('safeJsonParse failed:', { raw: str, error: e.message });
return fallback;
}
}
用法示例:
- Layui upload:
const data = safeJsonParse(xhr.responseText, {}); - fetch 场景:
const json = safeJsonParse(await res.text(), { code: -1 }); - localStorage:
const cfg = safeJsonParse(localStorage.getItem('config'), {});
注意 fallback 值类型要和业务预期一致;传 null 比 {} 更能暴露逻辑分支问题。真正难缠的从来不是语法错误,而是你以为它是个字符串,其实它早就不是了。


















