Laravel API返回JSON失败的主因是中间件配置错误、响应双重编码及模型序列化问题。需确保路由使用api中间件组、避免手动json_encode()、正确配置Eloquent模型的casts和appends。

API路由没加api中间件,返回HTML而不是JSON
Laravel默认的web中间件组会触发Session、CSRF等机制,导致API请求被重定向或返回视图页面——哪怕你写了return response()->json(...),也可能被包裹进HTML里。
- 确认路由定义在
routes/api.php中(自动加载api中间件组) - 如果硬要在
routes/web.php里写API,必须手动加->middleware('api') - 检查是否误用了
Route::get('/api/users', ...)->middleware('web')——这会让Accept: application/json失效
response()->json()和json_encode()混用导致双重编码
常见错误:手动json_encode()后再传给response()->json(),结果字符串被再套一层引号,前端解析成字符串而非对象。
- ✅ 正确:
return response()->json(['user' => $user]); - ❌ 错误:
return response()->json(json_encode(['user' => $user])); - 注意
$user如果是Eloquent模型,默认已转为数组;若手动调用$user->toJson(),也别再包一层response()->json()
模型序列化时字段缺失或格式错乱
Eloquent模型默认不会把所有属性都转成JSON,比如created_at是Carbon实例,password会被自动隐藏,appends字段可能没生效。
- 用
toArray()前先检查$model->getHidden()和$model->getVisible() - 时间字段要统一格式,推荐在模型里加
protected $casts = ['created_at' => 'datetime:Y-m-d H:i:s']; - 需要动态字段(如
is_subscribed),确保已声明在$appends并提供对应getIsSubscribedAttribute()方法
前端收到500但控制台只显示Failed to fetch
Laravel API在开发环境默认返回HTML错误页,前端fetch/fetch-like库无法解析,就静默失败。关键不是接口逻辑,而是响应内容类型不匹配。
- 确认
APP_DEBUG=true且Accept: application/json请求头已发送(Postman/axios默认带,浏览器地址栏直输不带) - 检查
App\Exceptions\Handler::render()是否重写了JSON异常响应逻辑;默认Laravel 9+对API请求会自动返回JSON错误,但若自定义了render却漏了$request->expectsJson()判断,就会退回到HTML - 临时验证:用
curl -H "Accept: application/json" http://localhost:8000/api/test看原始响应体
json(),而是中间件链、模型序列化边界、以及错误响应的内容协商机制——这三个地方一动,前端就收不到干净的JSON。










