Laravel 响应:永远返回 JSON 响应 0 个改进

当你在编写完全为 API 服务的 Laravel 应用时,你希望所有响应都是 JSON 格式的,而不是例如说授权错误会重定向到 /home 或 /login,最终重定向会变成 InvalidArgumentException: Route [login] is not defined. 的视图。

下面这个简单的方案,可以让你的 Laravel 应用优先响应为 JSON 格式。

第一步、编写 BaseRequest

首先我们需要构建一个 BaseRequest 来重写 Illuminate\Http\Request ,修改为默认优先使用 JSON 响应:

app/Http/Requests/BaseRequest.php

<?php
namespace App\Http\Requests;

use Illuminate\Http\Request;
class BaseRequest extends Request
{
    public function expectsJson()
    {
        return true;
    }
    public function wantsJson()
    {
        return true;
    }
}

第二步、替换 BaseRequest

public/index.php 文件中,将 \Illumiate\Http\Request 替换为我们的 BaseRequest,如下:

$response = $kernel->handle(
    $request = \App\Http\Requests\BaseRequest::capture()
);

搞定!

现在所有的响应都是 application/json ,包括错误和异常。

本文为 Wiki 文章,邀您参与纠错、纰漏和优化
讨论数量: 28

我來貢獻一下我自己的做法

新增 middleware

namespace App\Http\Middleware;

use Closure;

class ForceJson
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request $request
     * @param  \Closure $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        $request->headers->set('accept', 'application/json');

        return $next($request);
    }
}

Kernel.php 加入

'force-json' => \App\Http\Middleware\ForceJson::class,

routes/api.php

Route::group(['middleware' => ['force-json', 'auth:api']], function () {
    // put your router
});

打完收功

這樣的做法可以任意指定 router 的行為
還可以不用更動到 Laravel 原生的程式碼

10个月前 评论

黑科技

11个月前 评论

黑科技

11个月前 评论

66666, 又学到了

11个月前 评论

果然黑科技。

11个月前 评论

操作好骚

11个月前 评论

果然是骚操作

11个月前 评论
aen233

黑科技,学到了

10个月前 评论
GhostCoder

666666666

10个月前 评论
GalaxyNo_1

:gem: 黑科技

10个月前 评论

反手就是一个赞

10个月前 评论
sushengbuhuo

666

10个月前 评论

喜欢黑科技,666

10个月前 评论

我來貢獻一下我自己的做法

新增 middleware

namespace App\Http\Middleware;

use Closure;

class ForceJson
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request $request
     * @param  \Closure $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        $request->headers->set('accept', 'application/json');

        return $next($request);
    }
}

Kernel.php 加入

'force-json' => \App\Http\Middleware\ForceJson::class,

routes/api.php

Route::group(['middleware' => ['force-json', 'auth:api']], function () {
    // put your router
});

打完收功

這樣的做法可以任意指定 router 的行為
還可以不用更動到 Laravel 原生的程式碼

10个月前 评论
ThinkCsly

厉害

10个月前 评论
largezhou

牛逼啊,省的总是要在headers中加一个xhr....

10个月前 评论

哈哈哈,为什么我想笑啊,哈哈哈哈

10个月前 评论

不错

10个月前 评论

黑色武器吧

10个月前 评论
sureyee

这个在请求头中加入Accept:application/json就可以了吧

10个月前 评论
GalaxyNo_1

牛叉

9个月前 评论
Timgle

可以的,666

9个月前 评论
Shuyi

如果这样,不如直接用Lumen。。。

8个月前 评论
wanghan

@recca0120 我觉得你的方法更好

8个月前 评论
黑将军

@recca0120 我也是用这种方法

8个月前 评论

@recca0120 同样是九年义务教育,niTM 怎么这么优秀

8个月前 评论

@recca0120 其实~你的做法好,但这个 accept 的设置应该在前端或请求段,不应该服务器自己手动设置;

7个月前 评论

@Moting 這個是單純的思路,可以快速的解決這個需求,但如你所說的不該我們設置,所以應該再多一行判斷式才對,判斷 request header accept 有無值,有值就不做任何動作,空值就補 header ,這樣就把控制權還給 client 了

4个月前 评论

好骚的操作啊,可是为啥呢,大神能不能讲讲原因啊

3个月前 评论

楼主这个太暴力啦,假设项目同时提供web和api两种服务,更通用的做法应该根据不同的路由前缀进行不同的返回。

2个月前 评论

请勿发布不友善或者负能量的内容。与人为善,比聪明更重要!