Laravel 9.x データベーステスト

イントロダクション

データベース駆動型アプリケーションのテストを容易にするため、Laravelはさまざまな便利なツールとアサートを提供しています。それに加えて、Laravelモデルのファクトリ(テスト用インスタンスの生成)とシーダ(初期データ設定)により、アプリケーションのEloquentモデルとリレーションを使用し、テストデータベースレコードを簡単に作成できます。これらの強力な機能のすべてについて、以降のドキュメントで説明します。

各テスト後のデータベースリセット

先へ進む前に、以前のテストデータが後続のテストに干渉しないように、各テストの後にデータベースをリセットする方法について説明しましょう。Laravelに含まれているIlluminate\Foundation\Testing\RefreshDatabaseトレイトがこれを処理します。テストクラスでトレイトを使用するだけです。

<?php

namespace Tests\Feature;

use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Foundation\Testing\WithoutMiddleware;
use Tests\TestCase;

class ExampleTest extends TestCase
{
    use RefreshDatabase;

    /**
     * 基本的な機能テスト例
     *
     * @return void
     */
    public function test_basic_example()
    {
        $response = $this->get('/');

        // ...
    }
}

Illuminate\Foundation\Testing\RefreshDatabaseトレイトは、スキーマが最新であれば、データベースをマイグレートしません。その代わりに、データベーストランザクション内でテストを実行するだけです。したがって、このトレイトを使用しないテストケースによってデータベースに追加されたレコードは、まだデータベースに残っている可能性があります。

マイグレーションを使用してデータベースを完全にリセットしたい場合は、代わりにIlluminate\Foundation\Testing\DatabaseMigrationsトレイトを使用します。しかし、DatabaseMigrationsRefreshDatabaseよりかなり低速です。

モデルファクトリ

テスト時、テストを実行する前にデータベースへレコードを挿入する必要がある場合があると思います。このようなテストデータ作成時、各カラムの値を手作業で指定する代わりに、Laravelではモデルファクトリを使用し、デフォルトの属性セットを各Eloquentモデルに対して定義できます。

モデルを生成するモデルファクトリの作成と利用の詳細は、完全なモデルファクトリドキュメントを参照してください。モデルファクトリを定義したら、テスト内でそのファクトリを利用してモデルを作成できます。

use App\Models\User;

public function test_models_can_be_instantiated()
{
    $user = User::factory()->create();

    // ...
}

シーダの実行

機能テスト中にデータベースシーダ(初期値設定)を使用してデータベースへデータを入力する場合は、seedメソッドを呼び出してください。seedメソッドはデフォルトで、DatabaseSeederを実行します。これにより、他のすべてのシーダが実行されます。または、特定のシーダクラス名をseedメソッドに渡します。

<?php

namespace Tests\Feature;

use Database\Seeders\OrderStatusSeeder;
use Database\Seeders\TransactionStatusSeeder;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Foundation\Testing\WithoutMiddleware;
use Tests\TestCase;

class ExampleTest extends TestCase
{
    use RefreshDatabase;

    /**
     * 新しい注文の作成をテスト
     *
     * @return void
     */
    public function test_orders_can_be_created()
    {
        // DatabaseSeederを実行
        $this->seed();

        // 特定のシーダを実行
        $this->seed(OrderStatusSeeder::class);

        // ...

        // 配列中に指定してあるシーダを実行
        $this->seed([
            OrderStatusSeeder::class,
            TransactionStatusSeeder::class,
            // ...
        ]);
    }
}

あるいは、RefreshDatabaseトレイトを使用する各テストの前に、自動的にデータベースをシードするようにLaravelに指示することもできます。これを実現するには、テストの基本クラスに$seedプロパティを定義します。

<?php

namespace Tests;

use Illuminate\Foundation\Testing\TestCase as BaseTestCase;

abstract class TestCase extends BaseTestCase
{
    use CreatesApplication;

    /**
     * デフォルトのシーダーが各テストの前に実行するかを示す
     *
     * @var bool
     */
    protected $seed = true;
}

$seedプロパティが true の場合、RefreshDatabaseトレイトを使用する各テストの前にDatabase\Seeders\DatabaseSeederクラスを実行します。ただし,テストクラスに$seederプロパティを定義し,実行したい特定のシーダーを指定できます。

use Database\Seeders\OrderStatusSeeder;

/**
 * 各テストの前に特定のシーダーを実行
 *
 * @var string
 */
protected $seeder = OrderStatusSeeder::class;

利用可能なアサート

Laravelは、PHPUnit機能テスト用にいくつかのデータベースアサートを提供しています。以下にこのようなアサートについて説明します。

assertDatabaseCount

データベース内のテーブルに指定した数のレコードが含まれていることをアサートします。

$this->assertDatabaseCount('users', 5);

assertDatabaseHas

データベース内のテーブルに、指定したキー/値クエリの制約に一致するレコードが含まれていることをアサートします。

$this->assertDatabaseHas('users', [
    'email' => 'sally@example.com',
]);

assertDatabaseMissing

データベース内のテーブルに、指定したキー/値クエリの制約に一致するレコードが含まれていないことをアサートします。

$this->assertDatabaseMissing('users', [
    'email' => 'sally@example.com',
]);

assertSoftDeleted

assertSoftDeletedメソッドは、指定したEloquentモデルが「ソフト削除」されたことをアサートします。

$this->assertSoftDeleted($user);

assertNotSoftDeleted

assertNotSoftDeletedメソッドは、指定Eloquentモデルが、「ソフトデリート」されていないことをアサートします。

$this->assertNotSoftDeleted($user);

assertModelExists

指定モデルがデータベースに存在することをアサートします。

use App\Models\User;

$user = User::factory()->create();

$this->assertModelExists($user);

assertModelMissing

指定モデルがデータベースに存在しないことをアサートします。

use App\Models\User;

$user = User::factory()->create();

$user->delete();

$this->assertModelMissing($user);

ドキュメント章別ページ

ヘッダー項目移動

注目:アイコン:ページ内リンク設置(リンクがないヘッダーへの移動では、リンクがある以前のヘッダーのハッシュをURLへ付加します。

移動

クリックで即時移動します。

設定

適用ボタンクリック後に、全項目まとめて適用されます。

カラーテーマ
和文指定 Pagination
和文指定 Scaffold
Largeスクリーン表示幅
インデント
本文フォント
コードフォント
フォント適用確認

フォントの指定フィールドから、フォーカスが外れると、当ブロックの内容に反映されます。EnglishのDisplayもPreviewしてください。

フォント設定時、表示に不具合が出た場合、当サイトのクッキーを削除してください。

バックスラッシュを含むインライン\Code\Blockの例です。

以下はコードブロックの例です。

<?php

namespace App;

use Illuminate\Database\Eloquent\Model;

class User extends Model
{
    /**
     * ユーザに関連する電話レコードを取得
     */
    public function phone()
    {
        return $this->hasOne('App\Phone');
    }
}

設定を保存する前に、表示が乱れないか必ず確認してください。CSSによるフォントファミリー指定の知識がない場合は、フォントを変更しないほうが良いでしょう。

キーボード・ショートカット

オープン操作

PDC

ページ(章)移動の左オフキャンバスオープン

HA

ヘッダー移動モーダルオープン

MS

移動/設定の右オフキャンバスオープン

ヘッダー移動

T

最初のヘッダーへ移動

E

最後のヘッダーへ移動

NJ

次ヘッダー(H2〜H4)へ移動

BK

前ヘッダー(H2〜H4)へ移動

その他

?

このヘルプページ表示
閉じる