@thiagoinnfo No since the database should empty when you start the test and empty when you finish the test.
In a test you need to know exactly what is inside the database, thus the creation of the author.
You should use a trait to make sure that you refresh your database between every test, and you should either use an in memory SQLite database or a dedicated test database. The complete test class for the Author show action in my case looks like this
class ShowTest extends TestCase
{
use RefreshDatabase;
/**
* @test
*/
public function it_shows_an_author(): void
{
$author = Author::factory()->create([
'first_name' => 'Robert',
'last_name' => 'Jordan'
]);
$this->get(action([AuthorsController::class, 'show'], $author->id))
->assertStatus(200)
->assertSee('Jordan, Robert');
}
/**
* @test
*/
public function it_shows_the_books_written_by_the_author(): void
{
$author = Author::factory(['first_name' => 'Robert', 'last_name' => 'Jordan'])
->has(Book::factory(['title' => 'The Eye Of The World']))
->create();
$this->get(action([AuthorsController::class, 'show'], $author->id))
->assertStatus(200)
->assertSee('Jordan, Robert')
->assertSee('The Eye Of The World');
}
}
The refreshDatabase tells phpunit that it should refresh the database between each test.
You use the phpunit.xml file to tell phpunit which database it should use.
In my case I tell it to use one called mysql_test
Depending on your version of Laravel the phpunit.vml uses different syntax, In my projects it uses the
<server name> tag to define the laravel settings from the env file, in later versions of Laravel it uses the <env> tag, so change the examples below accordingly.
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="./vendor/phpunit/phpunit/phpunit.xsd"
bootstrap="vendor/autoload.php"
colors="true"
>
<testsuites>
<testsuite name="Unit">
<directory suffix="Test.php">./tests/Unit</directory>
</testsuite>
<testsuite name="Feature">
<directory suffix="Test.php">./tests/Feature</directory>
</testsuite>
</testsuites>
<coverage processUncoveredFiles="true">
<include>
<directory suffix=".php">./app</directory>
</include>
</coverage>
<php>
<server name="APP_ENV" value="testing"/>
<server name="BCRYPT_ROUNDS" value="4"/>
<server name="CACHE_DRIVER" value="array"/>
<server name="DB_CONNECTION" value="mysql_test"/>
<server name="MAIL_MAILER" value="array"/>
<server name="QUEUE_CONNECTION" value="sync"/>
<server name="SESSION_DRIVER" value="array"/>
<server name="TELESCOPE_ENABLED" value="false"/>
</php>
</phpunit>
that one is also defined in my .env file
DB_CONNECTION_TEST=mysql
DB_DATABASE_TEST=mb2_test
If you want to use an in memory database your phpunit file might look something like this
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/9.3/phpunit.xsd" bootstrap="vendor/autoload.php" colors="true" stopOnFailure="true">
<coverage processUncoveredFiles="true">
<include>
<directory suffix=".php">./app</directory>
</include>
</coverage>
<testsuites>
<testsuite name="Unit">
<directory suffix="Test.php">./tests/Unit</directory>
</testsuite>
<testsuite name="Feature">
<directory suffix="Test.php">./tests/Feature</directory>
</testsuite>
</testsuites>
<php>
<server name="APP_ENV" value="testing"/>
<server name="BCRYPT_ROUNDS" value="4"/>
<server name="CACHE_DRIVER" value="array"/>
<server name="DB_CONNECTION" value="sqlite"/>
<server name="DB_DATABASE" value=":memory:"/>
<server name="MAIL_MAILER" value="array"/>
<server name="QUEUE_CONNECTION" value="sync"/>
<server name="SESSION_DRIVER" value="array"/>
</php>
</phpunit>