35

I am trying to recreate the database before each test in some PHPUnit test cases. I am using Laravel 5.3. Here is TestCase:

class CourseTypesTest extends TestCase
{
    public function setUp()
    {
        parent::setUp();
        Artisan::call('migrate');
        Artisan::call('db:seed', ['--class' => 'TestDatabaseSeeder ', '--database' => 'testing']);
    }

    /**
     * A basic functional test example.
     *
     * @return void
     */
    public function test_list_course_types()
    {
        $httpRequest = $this->json('GET', '/api/course-types');
        $httpRequest->assertResponseOk();
        $httpRequest->seeJson();

    }

    public function tearDown()
    {
        Artisan::call('migrate:reset');
        parent::tearDown();
    }
}

Running phpunit fails with error:

$ phpunit PHPUnit 5.7.5 by Sebastian Bergmann and contributors.

E 1 / 1 (100%)

Time: 2.19 seconds, Memory: 12.00MB

There was 1 error:

1) CourseTypesTest::test_list_course_types ReflectionException: Class TestDatabaseSeeder does not exist

D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Container\Container.php:749 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Container\Container.php:644 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Foundation\Application.php:709 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Database\Console\Seeds\SeedCommand.php:74 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Database\Console\Seeds\SeedCommand.php:63 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Database\Eloquent\Model.php:2292 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Database\Console\Seeds\SeedCommand.php:64 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Container\Container.php:508 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Console\Command.php:169 D:\www\learn-laravel\my-folder-api\vendor\symfony\console\Command\Command.php:254 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Console\Command.php:155 D:\www\learn-laravel\my-folder-api\vendor\symfony\console\Application.php:821 D:\www\learn-laravel\my-folder-api\vendor\symfony\console\Application.php:187 D:\www\learn-laravel\my-folder-api\vendor\symfony\console\Application.php:118 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Console\Application.php:107 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Foundation\Console\Kernel.php:218 D:\www\learn-laravel\my-folder-api\vendor\laravel\framework\src\Illuminate\Support\Facades\Facade.php:237 D:\www\learn-laravel\my-folder-api\tests\rest\CourseTypesTest.php:17

ERRORS! Tests: 1, Assertions: 0, Errors: 1.

but this class exists:
TestDatabaseSeeder inside database/seeds

0

6 Answers 6

41

Since version 5.8 you can do:

// Run the DatabaseSeeder...
$this->seed();

// Run a single seeder...
$this->seed(OrderStatusesTableSeeder::class);

Take a look at the documentation

Sign up to request clarification or add additional context in comments.

2 Comments

How to run multiple seeder? Just multiple single call or I can pass an array to $this->seed()?
Since version 8, you can pass in an array of seeder classes to $this->seed([...]);
22

The DatabaseSeeder can be instantiated on its own, and its call method is public.

All you need to do in your CourseTypesTest class would be

(new DatabaseSeeder())->call(TestDatabaseSeeder::class);

Or you can make use of Laravel's app helper as follow

app(DatabaseSeeder::class)->call(TestDatabaseSeeder::class);

Comments

13

The problem is empty space in your --class argument. If you take close look at array '--class' => 'TestDatabaseSeeder ' there is space in the end ... this is the problem. Change it to '--class' => 'TestDatabaseSeeder' and it should work fine.

2 Comments

Congrat! Empty space .. great :)
If you like migrate only one time your data, check this stackoverflow.com/questions/21893698/…
2

For those stumbling on this question recently and are using a newer version of Laravel, ever since Laravel 8.0 there is a simpler way to do this.

If you use the Framework's provided base test case Illuminate\Foundation\Testing\TestCase and you use any of the db traits, such as Illuminate\Foundation\Testing\RefreshDatabase, you can just add a protected $seed = true; property to your tests and it will seed the db when doing the migrations.

Example from the documentation:

<?php
 
namespace Tests;
 
use Illuminate\Foundation\Testing\TestCase as BaseTestCase;
use Illuminate\Foundation\Testing\RefreshDatabase;
 
abstract class TestCase extends BaseTestCase
{
    use RefreshDatabase;

    /**
     * Indicates whether the default seeder should run before each test.
     *
     * @var bool
     */
    protected $seed = true;
}

Comments

0

Refresh your database with Artisan:

Artisan::call('migrate:fresh --seed');

This command removes your tables, creates the tables again (runs the migrations) and then seeds the tables with clean data.

Comments

-4

enter image description here

You can try this way. You can execute this command when you run your test.

1 Comment

Please include the source code in the answer body instead of using an image.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.