0
0

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 1 year has passed since last update.

【Laravel】enumで管理する場合引数に渡すIDをオブジェクトで渡そう【リファクタリング】

Posted at

環境

Laravel v9.5.1 (PHP v8.1.3)

前提

  • User -> Bookは1対多
  • Bookのプロパティ:user_id title content genre
  • genreはenumで定義されている
app/Enums/Genre.php
namespace App\Enums;

enum Genre: int
{
  case Fantasy = 1;
  case DetectiveAndMystery = 2;
  case Horror = 3;
  case Romance = 4;
}

Bad

genreIdをenumで定義している場合、createPostメソッドのgenreIdの型宣言をintにしてしまうと、enumに存在しない値が入る可能性がある。
例えばenumには定義されていない5が入ってしまうとか。
DB上は問題ない値なのでもし5が入っても保存されてしまうが、一度DBに保存されてしまうとまず気づかないし変更するとしてもかなり大変なことになる。
バグの温床になりかねない。

BookController.php
class BookController extends Controller
{
  ...
  public function store(Request $request): JsonResponse
  {
    $post = $request->user()->createBook(
       $request->title, $request->content, $request->genre_id
    );

    return response()->json(Response::HTTP_OK);
  }
}
User.php
class User extends Model
{
  ...
  public static function createBook(string $title, string $content, int $genreId): void
  {
     Book::create([
        'user_id' => $this->id,
        'title' => $title,
        'content' => $content,
        'genre_id' => $genreId,
     ]);
  }
}

Better

createPostメソッドのgenreIdの型宣言をGenreオブジェクトで定義すると、間違って1~4以外の数字が入ることはない。
DBに間違った値が入る前にアプリケーション側で防ぐことが大切!

User.php
use App\Enums\Genre;

class User extends Model
{
  ...
  public static function createBook(string $title, string $content, Genre $genreId): void
  {
     Book::create([
        'user_id' => $this->id,
        'title' => $title,
        'content' => $content,
        'genre_id' => $genreId,
     ]);
  }
}
0
0
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
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?