UsersResource があると想像してください:
<?php namespace App\Http\Resources; use Illuminate\Http\Resources\Json\Resource; class UsersResource extends Resource { /** * Transform the resource into an array. * * @param \Illuminate\Http\Request * @return array */ public function toArray($request) { return [ 'id' => $this->id, 'name' => $this->name, 'email' => $this->email ]; } }何らかの理由で、そのリソース クラスを別のエンドポイントで再利用したいが、
email フィールドを非表示にしたい場合があります。この記事では、これを達成する方法について説明します。
API リソース
が何かわからない場合は、これに関する私の以前の記事を参照してください。
- ネストされた関係を持つ API リソース
- 1- 初期化プロジェクト
composer create-project --prefer-dist laravel/laravel api-fields
cd api-fields
touch database/database.sqlite
ファイルを編集し、データベース設定を削除し、SQLite を使用してプロジェクトのセットアップを続行します<pre class="brush:php;toolbar:false">DB_CONNECTION=sqlite</pre>
php artisan migrate php artisan make:resource UsersResource php artisan make:resource --collection UsersResourceCollection php artisan make:controller UsersController php artisan tinker factory(App\User::class)->times(20)->create(); quit
2- ルーティング
api.php ファイルにルートを必ず作成してください。 <pre class="brush:php;toolbar:false">Route::apiResource('/users', 'UsersController');</pre>
3- コントローラー
コントローラーは、目的の目標を表します。この例では、ユーザー リストではすべてのユーザーの名前のみが必要で、ユーザー表示では電子メール アドレスのみが非表示になりたいと仮定します。
<?php namespace App\Http\Controllers; use App\Http\Resources\UsersResource; use App\User; class UsersController extends Controller { /** * Display a listing of the resource. * * @param User $user * @return \Illuminate\Http\Response */ public function index(User $user) { return UsersResource::collection($user->paginate())->hide(['id', 'email']); } /** * Display a user. * * @param User $user * @return \Illuminate\Http\Response */ public function show(User $user) { return UsersResource::make($user)->hide(['id']); } }
これを実現するには、
UsersResourceCollection と UsersResource
の両方が hide
呼び出しの処理方法を認識している必要があります。 4- UsersResource クラス
メソッドから始めましょう。UsersResource::make
は UsersResource
オブジェクトを返します。したがって、応答から削除したいキーを保存する hide
をわかりやすく説明する必要があります。<pre class="brush:php;toolbar:false"><?php
namespace App\Http\Resources;
use Illuminate\Http\Resources\Json\Resource;
class UsersResource extends Resource
{
/**
* @var array
*/
protected $withoutFields = [];
/**
* Transform the resource into an array.
*
* @param \Illuminate\Http\Request
* @return array
*/
public function toArray($request)
{
return $this->filterFields([
'id' => $this->id,
'name' => $this->name,
'email' => $this->email
]);
}
/**
* Set the keys that are supposed to be filtered out.
*
* @param array $fields
* @return $this
*/
public function hide(array $fields)
{
$this->withoutFields = $fields;
return $this;
}
/**
* Remove the filtered keys.
*
* @param $array
* @return array
*/
protected function filterFields($array)
{
return collect($array)->forget($this->withoutFields)->toArray();
}
}</pre>
Done! これで、
の場合、応答に id
フィールドがないことがわかります。 <pre class="brush:php;toolbar:false">{
"data": {
"name": "Mr. Frederik Morar",
"email": "darryl.wilkinson@example.org"
}
}</pre>
5- UsersResourceCollection クラス
プロジェクト コレクションで
index メソッドを実行します。次の変更を行う必要があります:
- UsersResource::collection
- が
UsersResourceCollection
インスタンス(2)
UsersResourceCollection# のパブリック - hide
メソッド
# を返すことを確認します。#(3) 隠しフィールドを
UsersResource -
に渡す (1) については、
UsersResource## の
# メソッド <pre class="brush:php;toolbar:false"><?php
namespace App\Http\Resources;
use Illuminate\Http\Resources\Json\Resource;
class UsersResource extends Resource
{
public static function collection($resource)
{
return tap(new UsersResourceCollection($resource), function ($collection) {
$collection->collects = __CLASS__;
});
}
/**
* @var array
*/
protected $withoutFields = [];
/**
* Transform the resource into an array.
* 将资源转换为一个数组
*
* @param \Illuminate\Http\Request
* @return array
*/
public function toArray($request)
{
return $this->filterFields([
'id' => $this->id,
'name' => $this->name,
'email' => $this->email
]);
}
/**
* Set the keys that are supposed to be filtered out.
* 设置需要隐藏过滤掉的键
*
* @param array $fields
* @return $this
*/
public function hide(array $fields)
{
$this->withoutFields = $fields;
return $this;
}
/**
* Remove the filtered keys.
* 删除隐藏的键
*
* @param $array
* @return array
*/
protected function filterFields($array)
{
return collect($array)->forget($this->withoutFields)->toArray();
}
}</pre>
(2) と (3) に関しては、UsersResourceCollection
ファイルを変更する必要があります。
メソッドを公開し、隠しフィールドを使用して、コレクションを扱います。 .<pre class="brush:php;toolbar:false"><?php
namespace App\Http\Resources;
use Illuminate\Http\Resources\Json\ResourceCollection;
class UsersResourceCollection extends ResourceCollection
{
/**
* @var array
*/
protected $withoutFields = [];
/**
* Transform the resource collection into an array.
*
* @param \Illuminate\Http\Request
* @return array
*/
public function toArray($request)
{
return $this->processCollection($request);
}
public function hide(array $fields)
{
$this->withoutFields = $fields;
return $this;
}
/**
* Send fields to hide to UsersResource while processing the collection.
* 将隐藏字段通过 UsersResource 处理集合
*
* @param $request
* @return array
*/
protected function processCollection($request)
{
return $this->collection->map(function (UsersResource $resource) use ($request) {
return $resource->hide($this->withoutFields)->toArray($request);
})->all();
}
}</pre>
それはとても簡単です! 次に、http://api.dev/api/users
にアクセスすると、
と が含まれていないことがわかります。 email
フィールドは、UsersController
.<pre class="brush:php;toolbar:false">{
"data": [{
"name": "Mr. Frederik Morar"
}, {
"name": "Angel Daniel"
}, {
"name": "Brianne Mueller"
}],
"links": {
"first": "http://lab.php71/api-fields-2/public/api/users?page=1",
"last": "http://lab.php71/api-fields-2/public/api/users?page=7",
"prev": null,
"next": "http://lab.php71/api-fields-2/public/api/users?page=2"
},
"meta": {
"current_page": 1,
"from": 1,
"last_page": 7,
"path": "http://api-fields.lab.php71/api/users",
"per_page": 3,
"to": 3,
"total": 20
}
}</pre>
6- Summaryのメソッドで指定されているとおりです。この記事の目標は、
クラスは非表示のフィールドを渡します。一部のフィールドは、より柔軟にするために他のインターフェイスで公開することが許可されています。たとえば、
/users インターフェイスをリクエストした場合、応答データには avatar
フィールドが含まれませんが、/users/99
をリクエストした場合、応答データには avatar
フィールドが含まれません。データには avatar
フィールドが含まれています。 API リソースに対するリクエストを過度に繰り返すことはお勧めしません。単純なことがより複雑になる可能性があるためです。そのため、リクエスト時に特定のフィールドを非表示にすることが、よりシンプルで合理的な解決策となります。