响应 Responsable 接口(Laravel 5.5 新功能早知道)

file
Laravel 5.5 路由支持新的返回类型:Responsable 接口。 这个契约(contract)允许将对象从控制器或路由闭包返回时转换为 HTTP 响应实例。 Responsable 对象需要实现一个 toResponse() 方法来将该对象作为 HTTP 响应表示。

<?php

use Illuminate\Contracts\Support\Responsable;

class ExampleObject implements Responsable
{
    public function __construct($name = null)
    {
        $this->name = $name ?? 'Teapot'; 
    }

    public function status()
    {
        switch(strtolower($this->name)) {
            case 'teapot':
                return 418;
            default:
                return 200;
        }
    }

    public function toResponse()
    {
        return response(
            "Hello {$this->name}",
            $this->status(),
            ['X-Person' => $this->name]
        );
    }
}

在路由中使用上面这个 ExampleObject,就可以执行以下操作:

Route::get('/hello', function () {
    return new ExampleObject(request('name'));
});

现在,在框架中,路由 类会在准备响应时检查此类型:

if ($response instanceof Responsable) {
    $response = $response->toResponse();
}

假设你在 App\Http\Responses 的命名空间中有各种响应类型来组织你的响应。 支持一个 Posts 模型的例子可能是这样子的:

<?php

namespace App\Http\Responses;

class PostIndexResponse extends Response
{
    public function __construct($posts)
    {
        $this->posts = $posts;
    }

    public function toResponse()
    {
        return response()->json($this->transformPosts());
    }

    protected function transformPosts()
    {
        return $this->posts->map(function ($post) {
            return [
                'title' => $post->title,
                'description' => $post->description,
                'body' => $post->body,
                'published_date' => $post->published_at->toIso8601String(),
                'created' => $post->created_at->toIso8601String(),
            ];
        });
    }
}

上面是一个简单用例的基本例子。 它返回 JSON 响应,但你可能希望响应层包含其他功能,如内容协商。 上面的例子还假设了继承的 App\Http\Responses\Response 类可以提供一些基本功能。 响应层也可以包含像 Fractal 这样的转换代码,这样就不必直接在控制器中使用它。

这个 PostIndexResponse 的控制器可以这样写:

<?php

namespace App\Http\Controllers;

use App\Http\Responses;

class PostsController extends Controller
{
    public function index()
    {
        $posts = \App\Post::all();

        return new Responses\PostIndexResponse($posts);
    }
}

查看实现这个契约代码库的 提交, 可以详细了解如何在 Laravel 5.5 中使用 Responsable。

参考链接:https://laravel-news.com/laravel-5-5-respo...

本作品采用《CC 协议》,转载必须注明作者和本文链接
Stay Hungry, Stay Foolish.
本帖由 Summer 于 6年前 加精
《L02 从零构建论坛系统》
以构建论坛项目 LaraBBS 为线索,展开对 Laravel 框架的全面学习。应用程序架构思路贴近 Laravel 框架的设计哲学。
《G01 Go 实战入门》
从零开始带你一步步开发一个 Go 博客项目,让你在最短的时间内学会使用 Go 进行编码。项目结构很大程度上参考了 Laravel。
讨论数量: 13
Summer

这么晚还在写文章哈

6年前 评论

还是很期待5.5的,很多新的特性迫不及待的想用上啊~

6年前 评论

5.5会在这个月发布吗?

6年前 评论

ExampleObject 类中的 toResponse() 方法是不是少了个参数,Responsable 接口中有的

interface Responsable
{
    /**
     * Create an HTTP response that represents the object.
     *
     * @param  \Illuminate\Http\Request  $request
     * @return \Illuminate\Http\Response
     */
    public function toResponse($request);
}
public function toResponse()
{
    return response(
        "Hello {$this->name}",
        $this->status(),
        ['X-Person' => $this->name]
    );
6年前 评论

@duc 并不是,我不知道你看的哪个版本的,我看的最新版的并不带参数,也就是即将发行的 5.5 版。

6年前 评论

@duc 我找到了,Taylor 后来修改了这个 commit,是我没注意。:kissing_closed_eyes:

6年前 评论

真是勤奋的人! 赞一个

6年前 评论

很棒!赞一个

6年前 评论

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!