データーベース上で特定のフラグで判別を基本毎回実行したい処理があった。
イメージとしては、アカウントとか一時的に停止させたいみたいな状況。
要件上、削除とは区別したいんだけど、動き的にはSoftDeleteと同じ動きにしたい。
これをscopeHogeみたいにモデルにスコープ定義して、呼び出し側で毎回スコープを呼ぶ。
めんどくさい&絶対呼び出しもれが発生するリスクがあるでイケテナイ。
そこで登場。グローバルスコープ。
グローバルスコープを定義したトレイトを必要なモデル側で読み込む事で、特定のモデルだけに対応させる事ができる。
例えば、各テーブルのsuspend
カラムで「0」のレコードのみにしたい場合は、
app/Models/Suspend.php
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Builder;
/**
* 一時停止処理トレイト
*/
trait Suspend
{
/**
* 初期起動(bootプレフィックスでトレイト名をメソッド名にする事で勝手に呼んでくれる)
* @return void
*/
protected static function bootSuspend(): void
{
static::addGlobalScope('suspend', function(Builder $builder) {
$builder->where('suspend', 0);
});
}
}
てな感じでトレイト作成。モデルでuseしてしまえばいい。
app/Models/Hoge.php
<?php
namespace App\Models;
use Illuminate\Database\Eloquent\Model;
class Hoge extends Model
{
use Suspend;
}
フラグ判定させたいモデルに、このトレイトを読み込ませるだけで勝手にSQLに追加してくれる。便利!
動きとしても SodtDelete と同等の動きが可能。
管理画面などで、フラグ判定させたくない場合は
$hoges = Hoge::withoutGlobalScope('suspend')->all();
とすれば取得可能。もちろん、whereメソッド等で組み合わせられる。