Laravel for Beginners: Laravel Seeders and Factories

Arlind Musliu cofounder at Lucky Media
Arlind Musliu

January 6, 2024 · 4 min read

Laravel for Beginners: Laravel Seeders and Factories

2026 UPDATE - LARAVEL 13

We’re excited to announce that we have updated all of our blog post examples to reflect the new Laravel 13 version! Our previous examples were based on Laravel 10, but with the release of Laravel 13, we wanted to ensure that our readers have access to the most up-to-date information and examples.

Note: Make sure you’ve already run the commands on our previous post when we set the models of our application. The following information assumes you’ve already followed that article successfully.

Populating Your App with Dynamic Data

After creating the database schema for our blog with Laravel migrations, it’s time to populate our tables with sample data. When building an application in Laravel, it’s important to have a rich dataset for testing and development. Laravel’s Seeders and Factories work hand in hand to create this data. Factories define how default data for models should be generated, and Seeders use those factories to populate the database. Let’s combine Seeders and Factories to fill our blog with dynamic, realistic data.

Why Use Seeders in your Laravel app?

Seeders are PHP classes that feed data into our database tables. They help us:

  • Test Features: With seeders, we can create enough data to test our application.

  • Develop Consistently: Seeders ensure every developer on the team has a consistent set of data.

  • Demo Purposes: Seeders provide a full demo for clients without manually entering data.

Setting Up Factories

Factories in Laravel are classes that define how to generate fake data for your models. They use the Faker library to create realistic data values. Let’s modify the factories for our blog’s Users, Profiles, Posts, Tags, and Images.

Note: If you followed the article where we set the models then you already have the following files below and are ready to code. Otherwise, you won’t be able to find these files in your app.

User Factory

namespace Database\Factories;

use Illuminate\Database\Eloquent\Factories\Factory;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Str;

/**
 * @extends \Illuminate\Database\Eloquent\Factories\Factory<\App\Models\User>
 */
class UserFactory extends Factory
{
    /**
     * The current password being used by the factory.
     */
    protected static ?string $password;

    /**
     * Define the model's default state.
     *
     * @return array<string, mixed>
     */
    public function definition(): array
    {
        return [
            'name' => fake()->name(),
            'email' => fake()->unique()->safeEmail(),
            'email_verified_at' => now(),
            'password' => static::$password ??= Hash::make('password'),
            'remember_token' => Str::random(10),
        ];
    }

    /**
     * Indicate that the model's email address should be unverified.
     */
    public function unverified(): static
    {
        return $this->state(fn (array $attributes) => [
            'email_verified_at' => null,
        ]);
    }
}

Profile Factory

You can create a Profile factory, but in this example, we’ll handle profile creation directly in the User Seeder to ensure each user has one profile.

Post Factory

namespace Database\Factories;

use App\Models\User;
use Illuminate\Database\Eloquent\Factories\Factory;

/**
 * @extends \Illuminate\Database\Eloquent\Factories\Factory<\App\Models\Post>
 */
class PostFactory extends Factory
{
    /**
     * Define the model's default state.
     *
     * @return array<string, mixed>
     */
    public function definition(): array
    {
        return [
            'user_id' => User::inRandomOrder()->first()->id,
            'title' => fake()->sentence,
            'content' => fake()->paragraph,
        ];
    }
}

Tag Factory

Tags may not necessarily need a factory if you’re using a predefined set of tags, but you can create one if you want dynamic tag names.

Image Factory

namespace Database\Factories;

use Illuminate\Database\Eloquent\Factories\Factory;

/**
 * @extends \Illuminate\Database\Eloquent\Factories\Factory<\App\Models\Image>
 */
class ImageFactory extends Factory
{
    /**
     * Define the model's default state.
     *
     * @return array<string, mixed>
     */
    public function definition(): array
    {
        return [
            'path' => fake()->imageUrl(),
        ];
    }
}
laravel best framework php

Planting the Seeds

Let’s create seeders for our blog’s users, profiles, posts, tags, and images to see how these seeds blossom into a rich database ready for development.

User Table Seeder

We’ll start by creating a seeder for the User table. Laravel uses the Faker library to generate fake data that looks real.

&lt;?php

namespace Database\Seeders;

use App\Models\Profile;
use App\Models\User;
use Illuminate\Database\Seeder;

class UserSeeder extends Seeder
{
    /**
     * Run the database seeds.
     */
    public function run(): void
    {
        User::factory()->count(10)
					   ->create()->each(
							fn($user) => $user->profile()->save(
												Profile::factory()->make()
						));
    }
}

Profile Table Seeder

Next, we’ll seed profiles for each user. Since each user should only have one profile, we’ll handle this within the User factory itself.

Post Table Seeder

For the Post table, we’ll create a seeder that generates 1000 blog posts for our users. We will need a greater number of posts when we show the difference between lazy loading and eager loading. We explain that in the post Laravel 13 for Beginners: Query Performance Issues and Debugbar.

use Illuminate\Database\Seeder;
use App\Models\Post;
use App\Models\Tag;

class PostSeeder extends Seeder
{
    public function run()
    {
        // Create 1000 posts
        $posts = Post::factory()->count(1000)->create();
        
        // Get all tags
        $tags = Tag::all();
        
        // Attach random tags to each post
        $posts->each(function ($post) use ($tags) {
            $randomTags = $tags->random(rand(1, 3)); // Random number of tags between 1 and 3 per post
            $post->tags()->attach($randomTags->pluck('id'));
        });
    }
}

Tag Table Seeder

Tags are the keywords for categorizing posts. We can seed a few common tags.

use Illuminate\Database\Seeder;
use App\Models\Tag;

class TagSeeder extends Seeder
{
    public function run()
    {
        $tags = ['Laravel', 'PHP', 'JavaScript', 'CSS', 'HTML'];

        foreach ($tags as $tag) {
            Tag::create(['name' => $tag]);
        }
    }
}

Image Table Seeder

Finally, we’ll seed some images for our posts. We’ll assume each post has at least one image.

use Illuminate\Database\Seeder;
use App\Models\Image;
use App\Models\Post;

class ImageSeeder extends Seeder
{
    public function run()
    {
        // Assume each post needs at least one image
        Post::all()->each(function ($post)
		{
            Image::factory()->create(
					[
						'imageable_id' => $post->id,
		                'imageable_type' => get_class($post),
					]
				);
        });
    }
}

Running the Seeders

To run all our seeders, we can call them from the DatabaseSeeder class. This class is executed when you run the db:seed Artisan command.

use Illuminate\Database\Seeder;

class DatabaseSeeder extends Seeder
{
    public function run()
    {
        $this->call([
            UserSeeder::class,
            TagSeeder::class,
            PostSeeder::class,
            ImageSeeder::class,
        ]);
    }
}

With our seeders ready, we can fill our database with the sample data using the following command:

php artisan migrate:fresh --seed

NOTE: This will remove all previous data and start fresh.

Conclusion

By using Laravel seeders and factories to generate user profiles, blog posts, tags, and images, we can simulate a blog application. This data not only aids in development and testing but also provides a visual demo for presenting our project to others.

Upcoming Articles in the Series

  1. Laravel for Beginners: Routing Your Application

  2. Laravel for Beginners: Middleware

  3. Laravel for Beginners: Authentication and Authorization

This article is part of our series Laravel for Beginners: A Step-by-Step Guide to Learn the Concepts.


Bring Your Ideas to Life 🚀

If you need help with a Laravel project let’s get in touch.

Lucky Media is proud to be recognized as a leading Laravel Development Agency

Technologies

Laravel
Arlind Musliu cofounder at Lucky Media
Arlind Musliu

Cofounder and CFO of Lucky Media

Stay up-to-date

Be updated with all news, products and tips we share!

Let’s chat

We partner with a limited number of brands each quarter to ensure senior-level attention on every project.

lokman and arlind headshots
Teamwork

Related posts

April 30, 2021

Laravel Breeze with Inertia and React
Laravel
Inertia
React

November 9, 2023

How to scope a Laravel project
Laravel
Business