Day07-Response 最重要的是整整齐齐-API Resources

大家好~
延续昨天说的话题,
如果我们想修改 API 回传的格式,
还要在每个 function 中个别修改那岂不是很麻烦吗?
而今天要来实作的 API Resources 就能解决上述的问题罗~

建立 API Resources

首先先来建立我们 Message 的 Resource 吧!

php artisan make:resource Message
php artisan make:resource MessageCollection

输入上面两个指令後,
我们会得到两个 Resource ,
为什麽要有两个呢?
简单来说,
以上面建立的两个 Resource 为例:

  • app/Http/Resources/Message.php
    是转换单个 Model 的 Resource,extends 了 JsonResource。
  • app/Http/Resources/MessageCollection.php
    是转换 Collection 的 Resource,extends 了 ResourceCollection。

两个 Resource 负责的工作不太一样喔!

在建立 Resource 时带上 --collection 参数,
或是使用 Collection 当作名称结尾,
都能够建立 extends 了 ResourceCollection 的 Resource 喔~

实作 API Resources

app/Http/Resources/Message.php
public function toArray($request)
{
    return [
        'id' => $this->id,
        'title' => $this->title,
        'content' => $this->content,
        'updated_at' => $this->updated_at,
        'user' => User::make($this->whenLoaded('user')),
    ];
}

这样简单 Resource 就完成罗!
简单介绍一下,
基本格式大概是这样的规则:

return [
    '自定义 Key 值' => $this->Model属性名称,
];

那该如何用他转换我们想回传的资料呢?

首先先在要使用 Resource 的 Controller 内 use 他们吧。

use App\Http\Resources\Message as MessageResource;
use App\Http\Resources\MessageCollection;

以检索单一笔留言为例,
我们原本是:

public function show($messageId)
{
    $message = Message::with('user')->findOrFail($messageId);

    return response($message, Response::HTTP_OK);
}

现在改成:

public function show($messageId)
{
    $message = Message::with('user')->findOrFail($messageId);

    return response(MessageResource::make($message), Response::HTTP_OK);
}

上面的例子是用当资料型态为 Model 时为例子,
那如果资料型态是 Collection 呢?

这是我们原本的查询所有留言功能 return response 的方式:

public function index()
{
    $messages = Message::with('user')->get();

    return response($messages, Response::HTTP_OK);
}

只要改成:

public function index()
{
    $messages = Message::with('user')->get();

    // 方法 1.
    return response(MessageCollection::make($messages), Response::HTTP_OK);
    // 方法 2.
    return response(MessageResource::collection($messages), Response::HTTP_OK);
}

方法1与方法2都可以回传资料型态为 Collection 的资料喔!

成果预览:

show( )

index( )

Resource 提供许多有趣且实用的用法,
本次范例无法一一介绍到,
像上方用到的 whenLoaded() 会判断资料有没有加载关联,
若没有加载关联,
该 Key 就不会回传。
这样也可以避免查询时发生「N+1」问题喔~

下图就是没加载 user 关联时的回传结果,
可以看到回传格式中没有出现 user 的 key。

小结:

  1. 不一定要建立两种 Resource,使用 Resource::collection( ) 也可以处理 Collection 的资料。
  2. 在使用的时候要注意好我们的资料型态是 Model 还是 Collection,不然会报错喔。

那麽今天就先这样啦!
大家明天见~
若文章有任何问题,
还请大家不吝赐教!

参考资料:


<<:  [ 卡卡 DAY 7 ] - React Native style 必懂之 Flexbox弹性盒子(下)

>>:  Day 07 - Design System — 前端工程师也该知道的那些事

【Day 11】分类(Classification)(下)

昨天提到了生成模型(Generative Model),要去计算事前机率(Prior Probabi...

[Day13]-函数设计2

进阶函数 函数也可以当参数,下图result()函数把其他函数作为参数,也可称做高阶函数 嵌套函数...

Day 30 云端守门员

来到了最後一天,我们也剩下最後一片云要一起来探索。今天就来谈谈云端的资安,以此来总结我们这一趟经历两...

Day10-Kind部署环境与测试

在前一章我们介绍完kind常用的指令,既然已经知道指令了,接下来我们就来试看看部署 建立环境 首先,...

第06天 - 一些些的 MySQL(上)

今天来看看 MySQL 该怎麽用 第1部分 - 进到 MySQL 画面 1.先打开 XAMPP 2....