0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

Laravelのmodelでphp-enumをいい感じに使う

Posted at

はじめに

Laravelでenumを扱おうとすると、よく出てくるのがこの三つのライブラリです。

このうち、下二つはLaravel用のライブラリなので、親和性は高いと思うのですが、他PHPフレームワークを使う時に応用が効かないかなと思って、個人的にはphp-enumを推しています。(そもそもphp-enum以外は使ったことがないので、こっちのがいいぜ!という時は教えていただけるとありがたいです)

そういう訳で、laravelでphp-enumを使う時の個人的なベストプラクティスを紹介します。

ライブラリ バージョン
laravel 6.18
php-enum 1.7

やり方

enumの定義

php-enumでは、MyCLabs\Enum\Enumクラスを継承したクラスに、定数を定義することで、num値を定義します。このような感じです。

<?php

declare(strict_types=1);

namespace App\Enums;

use MyCLabs\Enum\Enum;

class RoleType extends Enum
{
    public const SUPER_ADMIN = 'SUPER_ADMIN';

    public const ADMIN = 'ADMIN';

    public const USER = 'USER';
}

マイグレーションの作成

マイグレーションファイルを作る時は、Blueprintenum()メソッドを使います。第二引数にはenumとして許可する値の配列を渡します。php-enumでは、values()メソッドでそのenum内で定義されている値の配列を得ることができるので、この値を渡します。

class CreateUsersTable extends Migration
{
    /**
     * Run the migrations.
     */
    public function up(): void
    {
        Schema::create('users', function (Blueprint $table): void {
            $table->enum('role', RoleType::values());
        });
    }

    /**
     * Reverse the migrations.
     */
    public function down(): void
    {
        Schema::dropIfExists('users');
    }
}

モデルの定義

UserモデルにRoleTypeを持たせる時、今の状態では$user->roleとしてもRoleTypeのインスタンスは取れず、DB上にあるスカラー値しか取れません。また、$user->roleRoleTypeをそのままセットすることもできず、スカラー値に変換してからセットする必要があります。


$role = RoleType::ADMIN();
$user = new User();

$user->role = $role->getValue();
$role = new Role($user->role);

// NG
// $user->role = $role;

プロパティの値を使う度に変換を行うのは手間なので、Laravelのミューテタ1を使います。
以下のようにgetRoleAttribute〇〇(), setRoleAttribute〇〇()メソッドを定義しておくことで、laravelがよしなに変換をしてくれます。


<?php

declare(strict_types=1);

namespace App\Models;

use App\Enums\AnaUserRole;
use Illuminate\Foundation\Auth\User as Authenticatable;

class User extends Authenticatable
{
    /**
     * The attributes that are mass assignable.
     *
     * @var array
     */
    protected $fillable = ['role'];

    public function getRoleAttribute(string $value): RoleType
    {
        return new Role($value);
    }

    public function setRoleAttribute(RoleType $role): void
    {
        $this->attributes['role'] = $role->getValue();
    }

}

このようにかけます。


$role = RoleType::ADMIN();
$user = new User();

$user->role = $role;
// $roleはRoleTypeのインスタンス
$role = $user->role;

以上!

参考文献

  1. https://readouble.com/laravel/6.x/ja/eloquent-mutators.html

0
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?