Skip to content

PHP Attributes in Laravel 13: A Comprehensive Guide

Explore the new PHP Attributes in Laravel 13, transforming Eloquent models, queue jobs, and more. Learn how to leverage these declarative features with practical examples.

Published · Updated · 3 min read

PHP Attributes in Laravel 13: A Comprehensive Guide

Laravel 13 marks a significant shift towards embracing PHP's attribute feature, offering a more declarative and cleaner way to configure various aspects of your application. This guide dives deep into the new attributes introduced, alongside existing ones, providing practical examples for Laravel and PHP developers.

It's important to note that these attributes are entirely optional. The traditional property-based syntax remains fully supported, ensuring backward compatibility and a smooth transition for existing projects.

New Eloquent Model Attributes

Laravel 13 introduces a suite of attributes that directly replace common Eloquent model properties, streamlining model definitions.

Mass Assignment Control

  • #[Fillable] Previously defined using protected $fillable, this attribute specifies which model attributes are mass assignable.

    use Illuminate\Database\Eloquent\Attributes\Fillable;
    
    #[Fillable(['title', 'body', 'status'])]
    class Post extends Model
    {
    }
    
  • #[Guarded] Replaces protected $guarded, defining attributes that are not mass assignable.

    use Illuminate\Database\Eloquent\Attributes\Guarded;
    
    #[Guarded(['id', 'is_admin'])]
    class User extends Model
    {
    }
    
  • #[Unguarded] A simple marker attribute that disables mass-assignment protection entirely, equivalent to protected $guarded = [];.

    use Illuminate\Database\Eloquent\Attributes\Unguarded;
    
    #[Unguarded]
    class Setting extends Model
    {
    }
    

Serialization Control

  • #[Hidden] Replaces protected $hidden, specifying attributes to exclude from JSON serialization.

    use Illuminate\Database\Eloquent\Attributes\Hidden;
    
    #[Hidden(['password', 'remember_token'])]
    class User extends Model
    {
    }
    
  • #[Visible] The inverse of #[Hidden], explicitly defining attributes to include in JSON serialization, replacing protected $visible.

    use Illuminate\Database\Eloquent\Attributes\Visible;
    
    #[Visible(['id', 'name', 'email'])]
    class User extends Model
    {
    }
    

Relationship and Appending Configuration

  • #[Appends] Replaces protected $appends, automatically appending accessor results to JSON output.

    use Illuminate\Database\Eloquent\Attributes\Appends;
    
    #[Appends(['full_name', 'is_active'])]
    class User extends Model
    {
        public function getFullNameAttribute(): string
        {
            return $this->first_name . ' ' . $this->last_name;
        }
    }
    
  • #[Touches] Replaces protected $touches, specifying parent models whose timestamps should be updated when the current model is saved.

    use Illuminate\Database\Eloquent\Attributes\Touches;
    
    #[Touches(['post'])]
    class Comment extends Model
    {
        public function post(): BelongsTo
        {
            return $this->belongsTo(Post::class);
        }
    }
    

Table and Connection Configuration

  • #[Table] A versatile attribute that consolidates configuration for $table, $primaryKey, $keyType, $incrementing, $timestamps, and $dateFormat.

    use Illuminate\Database\Eloquent\Attributes\Table;
    
    #[Table('blog_posts', key: 'post_id')]
    class Post extends Model
    {
    }
    
    #[Table(
        name: 'external_orders',
        key: 'uuid',
        keyType: 'string',
        incrementing: false,
        timestamps: false,
    )]
    class ExternalOrder extends Model
    {
    }
    
  • #[Connection] Replaces protected $connection, specifying the database connection to use for the model.

    use Illuminate\Database\Eloquent\Attributes\Connection;
    
    #[Connection('analytics')]
    class PageView extends Model
    {
    }
    

Queue / Job Attributes

Configure job behavior declaratively using attributes.

  • #[Tries] Sets the maximum number of times a job should be attempted, replacing $tries.

    use Illuminate\Queue\Attributes\Tries;
    
    #[Tries(3)]
    class ProcessPayment implements ShouldQueue
    {
        use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    }
    
  • #[Timeout] Defines the job timeout in seconds, replacing $timeout.

    use Illuminate\Queue\Attributes\Timeout;
    
    #[Timeout(120)]
    class GenerateReport implements ShouldQueue
    {
        use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    }
    
  • #[Backoff] Configures the delay between retries, supporting both fixed and exponential backoff strategies, replacing $backoff.

    use Illuminate\Queue\Attributes\Backoff;
    
    // Fixed backoff
    #[Backoff(30)]
    class SyncInventory implements ShouldQueue
    {
        // ...
    }
    
    // Exponential backoff
    #[Backoff([10, 30, 60])]
    class AnotherJob implements ShouldQueue
    {
        // ...
    }
    

This is just a glimpse of the new attribute-driven features in Laravel 13. As the framework evolves, expect more components to adopt this modern, declarative approach.


Frequently asked questions

Are PHP Attributes in Laravel 13 breaking changes?

No, the new PHP Attributes in Laravel 13 are optional. The traditional property-based syntax for Eloquent models and queue jobs remains fully supported.

What Eloquent model properties can be replaced by attributes in Laravel 13?

In Laravel 13, attributes can replace properties like `$fillable`, `$guarded`, `$hidden`, `$visible`, `$appends`, `$table`, `$primaryKey`, `$keyType`, `$incrementing`, `$timestamps`, `$dateFormat`, `$connection`, and `$touches`.

How do PHP Attributes improve Queue Job configuration in Laravel 13?

Laravel 13 allows configuring Queue Jobs using attributes like `#[Tries]`, `#[Timeout]`, and `#[Backoff]`, providing a more declarative and readable way to manage job retry logic and execution parameters.

Mohamed Said

About the author

Senior Backend Engineer specializing in Laravel, scalable SaaS platforms, APIs, and cloud infrastructure. I build secure, high-performance web applications that help businesses grow.

About GitHub LinkedIn WhatsApp Email Address My CV

Have a technical challenge?

Tell me what you’re building. I reply within two working days.

Discuss your project