What is `protected $fillable` in a Laravel model?

In Laravel, the `protected $fillable` property is used to define an array of attributes that are mass assignable. This means these attributes can be assigned using mass-assignment techniques, such as when creating a new model instance or updating an existing one using the `create` or `update` methods.

Mass Assignment

Mass assignment is a way to assign multiple attributes to a model instance in a single step, typically using an array. For example, you might have a form where a user can submit several pieces of information at once. Instead of assigning each piece of information individually, you can pass the entire array to the `create` or `update` method.

Here’s an example of how you might use the `$fillable` property in a Laravel model:

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Post extends Model
{
    // Define the attributes that are mass assignable
    protected $fillable = [
        'title', 
        'content', 
        'author_id'
    ];
}

In this example, the `Post` model has three attributes (`title`, `content`, and `author_id`) that are mass assignable.

Using Mass Assignment

With the `$fillable` property defined, you can now safely use mass assignment:

// Creating a new post
$post = Post::create([
    'title' => 'My First Post',
    'content' => 'This is the content of my first post.',
    'author_id' => 1
]);

// Updating an existing post
$post->update([
    'title' => 'Updated Title',
    'content' => 'This is the updated content.'
]);

The primary purpose of the `$fillable` property is to prevent mass-assignment vulnerabilities. Without `$fillable` (or its counterpart `$guarded`), any attribute in the model can be mass assigned, which could potentially allow malicious users to update sensitive fields that they shouldn’t have access to.

Mass Assignment Vulnerability

So what is this mass assignment vulnerability? Consider a scenario where a user can submit their profile information. If the user model has an attribute like `is_admin`, and this attribute is not protected, a malicious user could submit a form with an `is_admin` field and set its value to `true`, giving themselves admin privileges.

By defining the `$fillable` property, you explicitly specify which attributes are safe to be mass assigned, thus mitigating this risk.

So, using the `$fillable` property is a best practice in Laravel to ensure that only the intended attributes can be mass assigned, enhancing the security of your application.