В новых классах ресурсов Laravel вы можете удалять атрибуты на основе всего, что вам нравится.

Если вы хотите вернуть много предметов, вы можете использовать функцию

Resource::collection()

Но это не позволяет вам добавлять метаданные в одном месте. Введите коллекцию, отлично, это много элементов в красивом формате с возможностью добавления метаданных. Что вы не можете сделать, так это отфильтровать коллекцию, чтобы скрыть атрибуты, как вы можете с ресурсом. Единственный способ, которым я могу это сделать, - это

foreach ($this->collection as $item) {
        if ($notAdmin) {
            $temp = array_except($item->toArray(), ['secret']);
        }
        $temp['links'] = ['self' => route('restaurant.show', [$item])];
        $data[] = $temp;
    }

Что-то мне не хватает? Это похоже на огромную упущенную возможность для коллекции ресурсов.

3
Fireynis 14 Мар 2018 в 04:01

2 ответа

Лучший ответ

Судя по этой теме, при использовании класса ResourceCollection для настройки коллекции ( например BookCollection) Laravel ищет ресурс класс с тем же именем, но без суфиксного класса Collection (в этом примере класс с именем просто Book).

Таким образом, вам потребуется класс ресурсов с именем: Book, в котором вы настраиваете атрибуты, возвращаемые в ответ, и класс коллекции с именем: BookCollection, который будет использовать Book -для настройки данные, а также позволит вам настроить метаданные.

Приложение / HTTP / Ресурсы / Book.php

<?php

namespace App\Http\Resources;

use Illuminate\Http\Resources\Json\Resource;

class Book extends Resource
{
    /**
     * Transform the resource into an array.
     *
     * @param  \Illuminate\Http\Request
     * @return array
     */
    public function toArray($request)
    {
        return [
            'id' => $this->id,
            'title' => $this->title,
        ];
    }
}

Приложение / HTTP / Ресурсы / BookCollection.php

<?php

namespace App\Http\Resources\Users;

use Illuminate\Http\Resources\Json\ResourceCollection;

class BookCollection extends ResourceCollection
{
    /**
     * Transform the resource collection into an array.
     *
     * @param  \Illuminate\Http\Request
     * @return array
     */
    public function toArray($request)
    {
        return $this->collection;
    }

    public function with($request)    
    {
        return [
            'meta' => [
                'key' => 'value',
            ],
        ];
    }
}
6
Kenny Horna 18 Сен 2018 в 17:39

Хорошо, вот как это сделать:

  1. Создайте Resource для одного ресурса, где можно легко иметь условные атрибуты

  2. Создайте RCollection для коллекции, где вы можете добавить метаданные данные.

  3. Передайте Resource::collection(Model::all) в new RCollection().

Примерно так (из моего тестирования):

Route::get('users/all', function() {
    return new \App\Http\Resources\Users(
        \App\Http\Resources\UserResource::collection(\App\User::get())
    );
});

Работает как шарм!

0
DevK 14 Мар 2018 в 02:53