Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Data Fixtures Laravel Package

doctrine/data-fixtures

Doctrine Data Fixtures provides a simple way to define, manage, and run data fixture loaders for Doctrine ORM/ODM. Use it to seed databases with reusable sample data for development, testing, and demos via an organized fixture execution workflow.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Installation:

    composer require doctrine/data-fixtures-bundle
    

    For Laravel, use doctrine/doctrine-bundle (includes fixtures support).

  2. First Fixture: Create a fixture class in database/fixtures/ (or your preferred location):

    // database/fixtures/UserFixtures.php
    namespace Database\Fixtures;
    
    use Doctrine\Bundle\FixturesBundle\Fixture;
    use Doctrine\Persistence\ObjectManager;
    use App\Models\User;
    
    class UserFixtures extends Fixture
    {
        public function load(ObjectManager $manager)
        {
            $user = new User();
            $user->name = 'John Doe';
            $user->email = 'john@example.com';
            $manager->persist($user);
            $manager->flush();
    
            // Reference for later use
            $this->addReference('john_doe', $user);
        }
    }
    
  3. Run Fixtures:

    php artisan doctrine:fixtures:load
    

Key First Use Case

Populate a database with test data for development or testing. Example:

php artisan doctrine:fixtures:load --append  # Append to existing data
php artisan doctrine:fixtures:load --purge   # Clear and reload

Implementation Patterns

Common Workflows

1. Ordered Fixtures

Use dependsOn() to define execution order:

class RoleFixtures extends Fixture
{
    public function load(ObjectManager $manager)
    {
        $role = new Role();
        $role->name = 'Admin';
        $manager->persist($role);
        $manager->flush();
        $this->addReference('admin_role', $role);
    }
}

class UserFixtures extends Fixture
{
    public function getDependencies()
    {
        return [RoleFixtures::class]; // Runs RoleFixtures first
    }

    public function load(ObjectManager $manager)
    {
        $user = new User();
        $user->name = 'Admin User';
        $user->role = $this->getReference('admin_role'); // Uses referenced role
        $manager->persist($user);
        $manager->flush();
    }
}

2. Referencing Data

Reference entities for relationships:

$this->addReference('user_1', $user);
// Later in another fixture:
$user = $this->getReference('user_1');

3. Bulk Loading

Use ArrayCollection or loops for efficiency:

$users = [];
for ($i = 0; $i < 100; $i++) {
    $user = new User();
    $user->name = "User $i";
    $users[] = $user;
}
$manager->persist($users);
$manager->flush();

4. Custom Executors

Override default behavior (e.g., dry-run):

use Doctrine\Common\DataFixtures\Executor\ORMExecutor;
use Doctrine\Common\DataFixtures\Purger\ORMPurger;

$executor = new ORMExecutor($container->get('doctrine'), new ORMPurger());
$executor->execute($fixtures, true); // Dry-run mode

5. Laravel Integration

Leverage Laravel’s service container:

use Illuminate\Support\Facades\DB;

class DatabaseFixtures extends Fixture
{
    public function load(ObjectManager $manager)
    {
        DB::statement('SET FOREIGN_KEY_CHECKS=0;');
        // Fixture logic
        DB::statement('SET FOREIGN_KEY_CHECKS=1;');
    }
}

Integration Tips

With Laravel Migrations

Run fixtures after migrations:

php artisan migrate --seed

Or manually:

php artisan doctrine:fixtures:load

With Factories

Combine with Laravel factories for dynamic data:

use App\Models\User;
use Faker\Factory as Faker;

class UserFixtures extends Fixture
{
    public function load(ObjectManager $manager)
    {
        $faker = Faker::create();
        for ($i = 0; $i < 5; $i++) {
            $user = User::factory()->create([
                'email' => $faker->unique()->email
            ]);
            $manager->persist($user);
        }
        $manager->flush();
    }
}

Environment-Specific Fixtures

Use Laravel’s environment config:

if (app()->environment('testing')) {
    // Load test-specific fixtures
}

Parallel Loading

For large datasets, use doctrine/doctrine-fixtures-bundle's parallel loader:

# config/packages/doctrine_fixtures.yaml
doctrine_fixtures:
    parallel: true

Gotchas and Tips

Pitfalls

1. Reference Scope

  • References are fixture-specific. A reference in UserFixtures won’t be available in ProductFixtures unless explicitly passed via dependencies.
  • Fix: Use dependsOn() to chain fixtures or pass references through constructor injection.

2. Transaction Isolation

  • Fixtures run in a single transaction by default. Large datasets may hit transaction limits.
  • Fix: Use --append or chunk data:
    $manager->flush(); // Flush after every N entities
    

3. Circular Dependencies

  • Avoid A depends on B and B depends on A.
  • Fix: Restructure fixtures or use a base fixture.

4. Purger Behavior

  • The ORMPurger deletes all entities of loaded fixtures. Be explicit with purgeMode.
  • Fix: Use Purger::PURGE_MODE_DELETE (default) or Purger::PURGE_MODE_TRUNCATE for faster clears.

5. Doctrine Events

  • Fixtures bypass Doctrine lifecycle events (e.g., prePersist). Use EventManager if needed:
    $eventManager = $manager->getEventManager();
    $eventManager->dispatchEvent(...);
    

6. Laravel Caching

  • Fixtures may conflict with Laravel’s query cache. Disable during fixture load:
    DB::connection()->disableQueryLog();
    // Fixture logic
    DB::connection()->enableQueryLog();
    

Debugging Tips

1. Dry-Run Mode

Test without writing to the database:

php artisan doctrine:fixtures:load --dry-run

2. Logging

Enable verbose output:

php artisan doctrine:fixtures:load -v

Or configure a custom logger:

use Psr\Log\LoggerInterface;

class CustomFixtures extends Fixture
{
    public function __construct(private LoggerInterface $logger) {}

    public function load(ObjectManager $manager)
    {
        $this->logger->info('Loading fixtures...');
    }
}

3. Fixture Order Debugging

Check execution order with:

public function load(ObjectManager $manager)
{
    dump('Executing: ' . static::class);
}

4. Reference Issues

Verify references exist:

if (!$this->hasReference('user_1')) {
    throw new \RuntimeException('Reference "user_1" not found!');
}

Extension Points

1. Custom Fixture Loader

Extend Loader\LoaderInterface for custom logic:

use Doctrine\Common\DataFixtures\Loader\LoaderInterface;

class CustomLoader implements LoaderInterface
{
    public function load(ObjectManager $manager)
    {
        // Custom logic
    }
}

2. Event Subscribers

Listen to fixture events:

use Doctrine\Common\DataFixtures\Event\FixturesLoadedEvent;

class FixtureSubscriber implements SubscriberInterface
{
    public function getSubscribedEvents()
    {
        return [
            FixturesLoadedEvent::class => 'onFixturesLoaded',
        ];
    }

    public function onFixturesLoaded(FixturesLoadedEvent $event)
    {
        // Post-load logic
    }
}

3. Custom Executor

Override ExecutorInterface for custom behavior (e.g., parallel loading):

use Doctrine\Common\DataFixtures\Executor\ExecutorInterface;

class ParallelExecutor implements ExecutorInterface
{
    public function execute(LoaderInterface $loader, bool $purgeMode)
    {
        // Parallel logic
    }
}

4. Laravel Service Provider

Bind custom fixtures in register():

$this->app->bind(
    \Doctrine\Common\DataFixtures\Loader\LoaderInterface::class,
    \App\Fixtures\CustomLoader::class
);

5. Fixtures as Migrations

Use doctrine/doctrine-migrations-bundle to version-control fixtures:

php artisan doctrine:migrations:execute --fixtures

Laravel-Specific Quirks

1. Eloquent vs. Doctrine

  • Prefer Eloquent for Laravel-specific features (e.g., hasManyThrough):
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
codraw/entity-migrator
codraw/doctrine-extra
codraw/aws-tool-kit
codraw/validator
codraw/workflow
codraw/open-api
codraw/cron-job
codraw/process
codraw/log
nexmo/api-specification
capell-app/block-library
axium/identity
cetria/laravel-dummy-models
cetria/reflection-helper
agropredict/sso-auth-bundle
evolvestudio/spam-protection
datacore/hub-sdk
develia/commons
cuci/prototurk-sdk
cuci/prototurk-sdk-symfony