web-dev-qa-db-ja.com

Laravel 5.6-追加のパラメーターをAPIリソースに渡しますか?

A Laravel APIリソース は、単一のリソースまたはコレクションのいずれかです。場合によっては、コントローラーからリソース/コレクションに追加のパラメーターを渡す必要があります。以下は、シングル/コレクションリソースとしてUserを使用し、出力用にリソースに渡すカスタム_$Apple_パラメーターを使用する問題を示す簡単な例です。問題は、最後のOutput (Collection)で確認できます。以下では、fruitの値について、正しいbananaの値(他のすべてのユーザーが取得する)ではなく、最初のユーザーのAppleの誤った値を取得します。

UserResourceを使用したコントローラー(シングル)

_    $user = User::first();
    return new UserResource($user, $Apple = true); // $Apple param passed
_

UserResource(コレクション)を持つコントローラー

_    $users = User::limit(3)->get();
    return UserResource::collection($users, $Apple = true); // $Apple param passed
_

UserResource

_    <?php

    namespace App\Http\Resources;
    use Illuminate\Http\Resources\Json\JsonResource;

    class UserResource extends JsonResource {
        private $Apple;

        public function __construct($resource, $Apple = false) {
            // Ensure we call the parent constructor
            parent::__construct($resource);
            $this->resource = $resource;
            $this->Apple = $Apple; // $Apple param passed
        }

        public function toArray($request) {
            return [
                'id'     => (int) $this->id, 
                'name'   => $this->name,
                'fruit'  => $this->Apple ? 'Apple' : 'banana',
            ];
        }
    }
_

出力(シングル)

_    {
        "data": {
            "id": 1,
            "name": "Peter",
            "fruit": "Apple" // correct param!
        }
    }

_

出力(コレクション)

_    {
        "data": [
            {
                "id": 1,
                "name": "Peter",
                "fruit": "banana" // INCORRECT param!
            },
            {
                "id": 2,
                "name": "Lois",
                "fruit": "Apple" // correct param!
            },
            {
                "id": 3,
                "name": "Brian",
                "fruit": "Apple" // correct param!
            }
        ]
    }
_

これは単なる例であり、任意のテーブルからの単一の値_read_at_タイムスタンプなど、任意の量のランダムパラメーター(Userコレクションとは無関係ですが、出力ロジックに渡す必要がある)であることに注意してください一度渡して、出力前にリソースコレクションで何らかのロジック(ユーザータイムスタンプとの比較など)を実行するか、追加のロジック_if/else_に渡されるその他のパラメーターを実行して、一般的にリソースファイルで実行し、コレクション。これをどのように行うことができますか?

7
Wonka

次のアプローチは私のために働いた:

serResource

class UserResource extends Resource{

    protected $foo;

    public function foo($value){
        $this->foo = $value;
        return $this;
    }

    public function toArray($request){
        return [
            'id' => $this->id,
            'name' => $this->name,
            'foo' => $this->foo,
         ];
    }

    public static function collection($resource){
        return new UserResourceCollection($resource);
    }
}

serCollection

class UserResourceCollection extends ResourceCollection{

    protected $foo;

    public function foo($value){
        $this->foo = $value;
        return $this;
    }

    public function toArray($request){
        return $this->collection->map(function(UserResource $resource) use($request){
            return $resource->foo($this->foo)->toArray($request);
    })->all();

        // or use HigherOrderCollectionProxy
        // return $this->collection->each->foo($this->foo)->map->toArray($request)->all()

        // or simple
        // $this->collection->each->foo($this->foo);
        // return parent::toArray($request);
    }
}

追加のパラメーターを渡す別の方法

(new UserResource($user))->foo('bar');
(new UserResourceCollection($user))->foo('bar');

UserResource::make($user)->foo('bar');
UserResourceCollection::make($users)->foo('bar');
UserResource::collection($users)->foo('bar');
15
Wonka

Laravel 5.7で動作するように、 ウォンカの答え

UserResource

    class UserResource extends Resource{

        protected $foo;

        public function foo($value){
            $this->foo = $value;
            return $this;
        }

        public function toArray($request){
            return [
                'id' => $this->id,
                'name' => $this->name,
                'foo' => $this->foo,
             ];
        }

        public static function collection($resource){
            return new UserResourceCollection($resource, get_called_class());
        }
    }

UserCollection

    class UserResourceCollection extends AnonymousResourceCollection {

        protected $foo;

        public function foo($value){
            $this->foo = $value;
            return $this;
        }

        public function toArray($request){
            return $this->collection->map(function(UserResource $resource) use($request){
                return $resource->foo($this->foo)->toArray($request);
        })->all();

        }
    }
3
Gabriel

APIエンドポイントへの呼び出しの一部として、追加のパラメーターを渡すことができます。その後、UserResourceの(たとえば)$ requestオブジェクトを使用してパラメーターにアクセスできます。

たとえば、Webブラウザやaxiosなどのクライアントから次のようなものを使用してエンドポイントを呼び出す場合:

http://localhost:3000/api/users?apple=true

これにより、パラメーターApple trueの値がコントローラーで使用可能になります。他のアクションがなければ、UserResourceのtoArray($ request)でもアクセスできます。次のようにアクセスできます。

public function toArray($request) {
      $isApple = $request->Apple;

        return [
            'id'     => (int) $this->id, 
            'name'   => $this->name,
            'fruit'  => $isApple ? 'Apple' : 'banana',
        ];
    }
1
SnapShot