← Back to Modules

Interactive Demo

🎯 Interactive Demo

Migration Builder Reference

Learn the syntax for creating well-structured database migrations.

📋 Column Types Reference

$$table->id()
Auto-increment primary key
$$table->string()
VARCHAR (default 255)
$$table->text()
TEXT column
$$table->integer()
INTEGER column
$$table->bigInteger()
BIGINT column
$$table->decimal()
DECIMAL column (for money)
$$table->boolean()
BOOLEAN column
$$table->date()
DATE column
$$table->datetime()
DATETIME column
$$table->timestamp()
TIMESTAMP column
$$table->json()
JSON column
$$table->foreignId()
Foreign key column

🔧 Column Modifiers

->nullable()
Allow NULL values
Example: $table->string('name')->nullable()
->default()
Set default value
Example: $table->string('name')->default()
->unique()
Add unique constraint
Example: $table->string('name')->unique()
->index()
Add index for performance
Example: $table->string('name')->index()
->unsigned()
Only positive numbers
Example: $table->string('name')->unsigned()

💡 Complete Migration Example

Schema::create('posts', function (Blueprint $table) {
    $table->id();
    $table->foreignId('user_id')->constrained()->onDelete('cascade');
    $table->string('title', 200);
    $table->text('content');
    $table->boolean('published')->default(false);
    $table->timestamp('published_at')->nullable();
    $table->timestamps();
    
    $table->index('published');
});

🔗 Foreign Keys & Relationships

Basic Foreign Key

$table->foreignId('user_id')
      ->constrained()
      ->onDelete('cascade');

Creates a foreign key to the 'users' table with cascade delete

Custom Foreign Key

$table->foreignId('author_id')
      ->constrained('users')  // References 'users' table
      ->onDelete('set null')
      ->nullable();

Foreign key to a different table with set null on delete

onDelete Actions

  • cascade - Delete related records
  • set null - Set foreign key to NULL
  • restrict - Prevent deletion if related records exist
  • no action - Do nothing (database default)

Indexes for Performance

Single Column Index

$table->index('email');

Speed up queries filtering by email

Composite Index

$table->index(['user_id', 'created_at']);

Optimize queries using both columns

Unique Index

$table->unique('email');

Ensure no duplicate emails

Index on Definition

$table->string('slug')->unique();

Add index while defining column

✨ Migration Best Practices

✅ Do:

  • Use descriptive migration names
  • Always provide a down() method
  • Add foreign keys for referential integrity
  • Index frequently queried columns
  • Use appropriate data types (decimal for money)
  • Keep migrations focused (one table/change)

❌ Don't:

  • Edit migrations after they've run in production
  • Forget to add indexes on foreign keys
  • Use string() without a length for large text
  • Hardcode IDs or data in migrations
  • Mix schema changes with data changes
  • Forget to handle nullable columns properly

⚙️ Artisan Commands

php artisan make:migration create_posts_table
php artisan make:migration add_status_to_posts_table --table=posts
php artisan migrate
php artisan migrate:rollback
php artisan migrate:fresh
php artisan migrate:fresh --seed
php artisan migrate:status