PHP
laravel

Laravel5.6 テスト用データベースを作成してテストを実行するための設定方法

環境

  • PHP 7.1
  • Laravel 5.6

やりたかったこと

Laravelのテスト実行時に、テスト用データベースに値が格納されるようにしたかった。
これといった確信的にわかりやすい記事がなかったので、残しておきます。

なおこの方法はベストな方法ではありません。 他にいい方法がありましたら、コメントいただけますと幸いです。
個人的には腑に落ちない方法ではあったものの一応やりたいことは実現出来ました。

テスト用データベースを作成する

以下のような二つのDBを作成しておきます。
前者がdevelop用、後者がPHPUnitやDusk用

  • laravel-app
  • laravel-app-test

.envを編集

.envの中身は以下

APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:ランダムな文字列
APP_DEBUG=true
APP_URL=http://localhost:8000

LOG_CHANNEL=stack

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=laravel-app
DB_USERNAME=root
DB_PASSWORD=root

BROADCAST_DRIVER=log
CACHE_DRIVER=file
SESSION_DRIVER=file
SESSION_LIFETIME=120
QUEUE_DRIVER=sync

REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379

MAIL_DRIVER=smtp
MAIL_HOST=smtp.mailtrap.io
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null

PUSHER_APP_ID=
PUSHER_APP_KEY=
PUSHER_APP_SECRET=
PUSHER_APP_CLUSTER=mt1

MIX_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
MIX_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"

.env.dusk.localを作成する

以下コマンドで.envをコピーし、.env.dusk.localファイルを作成

$ cp .env .env.dusk.local

.env.dusk.localの中身は以下

APP_NAME=Laravel
APP_ENV=local
APP_KEY=base64:ランダムな文字列
APP_DEBUG=true
APP_URL=http://localhost:8000

LOG_CHANNEL=stack

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=laravel-app-test
DB_USERNAME=root
DB_PASSWORD=root

BROADCAST_DRIVER=log
CACHE_DRIVER=file
SESSION_DRIVER=file
SESSION_LIFETIME=120
QUEUE_DRIVER=sync

REDIS_HOST=127.0.0.1
REDIS_PASSWORD=null
REDIS_PORT=6379

MAIL_DRIVER=smtp
MAIL_HOST=smtp.mailtrap.io
MAIL_PORT=2525
MAIL_USERNAME=null
MAIL_PASSWORD=null
MAIL_ENCRYPTION=null

PUSHER_APP_ID=
PUSHER_APP_KEY=
PUSHER_APP_SECRET=
PUSHER_APP_CLUSTER=mt1

MIX_PUSHER_APP_KEY="${PUSHER_APP_KEY}"
MIX_PUSHER_APP_CLUSTER="${PUSHER_APP_CLUSTER}"

この時に注意するのは、APP_URLがデフォルトでは、http://localhostになっているので変更をすること。

phpunit.xmlを編集する

以下のように<?php ~ ?>内に<env name="DB_DATABASE" value="laravel-app-test"/>を追加します。

<?xml version="1.0" encoding="UTF-8"?>
<phpunit backupGlobals="false"
         backupStaticAttributes="false"
         bootstrap="vendor/autoload.php"
         colors="true"
         convertErrorsToExceptions="true"
         convertNoticesToExceptions="true"
         convertWarningsToExceptions="true"
         processIsolation="false"
         stopOnFailure="false">
    <testsuites>
        <testsuite name="Feature">
            <directory suffix="Test.php">./tests/Feature</directory>
        </testsuite>

        <testsuite name="Unit">
            <directory suffix="Test.php">./tests/Unit</directory>
        </testsuite>
    </testsuites>
    <filter>
        <whitelist processUncoveredFilesFromWhitelist="true">
            <directory suffix=".php">./app</directory>
        </whitelist>
    </filter>
    <php>
        <env name="APP_ENV" value="testing"/>
        <env name="BCRYPT_ROUNDS" value="4"/>
        <env name="CACHE_DRIVER" value="array"/>
        <env name="SESSION_DRIVER" value="array"/>
        <env name="QUEUE_DRIVER" value="sync"/>
        <env name="MAIL_DRIVER" value="array"/>
                <env name="DB_DATABASE" value="laravel-app-test"/>
    </php>
</phpunit>

--envを使ってビルトインサーバーを立ち上げる

ここまで出来たら、以下のようにしてビルトインサーバーを立ち上げましょう

$ php artisan serve --env=dusk.local

ターミナルで違うウィンドウを開いて、以下を実行するとPHPUnitとDuskでダミーデータを用いたテストを実行しても、laravel-app-testに値が格納されるようになります。

$ vendor/bin/phpunit

$ php artisan dusk

ただし冒頭でも書きましたが、この方法だと、php artisan servephp artisan serve --env=dusk.localをいちいち切り替えないといけないです。。。
このような特殊なことをしたい場合にお役に立てればと思います。