Jose Jimenez
Software Architect & Developer
> >

Using PHP 8.1 Enums in Laravel Models

Published in PHP, Laravel, Database on Jan 19, 2022

The release of PHP 8.1 brings proper built-in support for Enums, proper cast support was also added in a pull request for Laravel 8. In this tutorial we will go over how to add Enums in Laravel Models. A more detailed article on Enums can be found on

For this excercise we will have an Article model, with an Enum that will handle the article status (closed|open|draft).

Storing Enum as string/integer/enum

Storing the value of your Enum in the database will highly depend on what you want for readability and performance. For a highly utilized column I will often times use TinyInt, if I need to have readability I will use a Varchar. I typically avoid the Enum column due experience and a few articles I've read over the years like this one. However that is out of scope for this article, you should find the column type that best suits your needs.

For my example I will be using varchar for my column to more easily be able to see my results.


For application consistency I created an app\Enum\{Model} directory to more easily keep track of my Enums, I will also suffix my Enum file with Enum to more easily find it during autocomplete.



namespace App\Enum\Article;

enum StatusEnum: string
    case Closed = 'closed';
    case Open = 'open';
    case Draft = 'draft';


Schema::create('article', function (Blueprint $table) {
    $table->string('status', 6);




namespace App\Models;

use App\Enum\Article\StatusEnum;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class Article extends Model
    use HasFactory;

    protected $casts = [
        'status' => StatusEnum::class,

Real World Usage

$article1 = Article::create([
    'title' => 'My Draft Article',
    'status' => StatusEnum::Draft,

$article2 = Article::create([
    'title' => 'My Open Article',
    'status' => StatusEnum::Open,

// Returns true
echo $article1->status === StatusEnum::Draft;

// Returns false because it should be of StatusEnum::Open
echo $article2->status === StatusEnum::Closed;

If we took a look at the records in our database we would see this:

Generating HTML fields

One additional benefit is that you can use StatusEnum::cases() method to help generate a select dropdown to dynamically control your input fields moving forward.

<select name="status" id="status">
@foreach(\App\Enum\Article\StatusEnum::cases() as $status)
    <option value="{{ $status->value }}">{{ $status->name }}</option>

// Will generate

<select name="status" id="status">
    <option value="closed">Closed</option>
    <option value="open">Open</option>
    <option value="draft">Draft</option>