1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

LaravelのUnitTestを使ってみる

Last updated at Posted at 2020-07-30

下準備

phpunit.xmlを編集する

DB_DATABASEにテスト用のDB名を記載します。

phpunit.xml
<?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>
    <filter>
        <whitelist processUncoveredFilesFromWhitelist="true">
            <directory suffix=".php">./app</directory>
        </whitelist>
    </filter>
    <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"/>
        // テスト用のDB名を記載する
        <server name="DB_DATABASE" value="laravel_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>

.env.testingを作成・編集する

.envファイルをコピーして.env.testingにリネームし、DB_DATABASEにテスト用のDB名を記載します。

.env.testing
DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=laravel_test
DB_USERNAME=root
DB_PASSWORD=

テスト用テーブルを作成

マイグレーションファイルを作成します。

php artisan make:migration create_articles_table

構成はシンプルにします。

<?php

use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;

class CreateArticlesTable extends Migration
{
    /**
     * Run the migrations.
     *
     * @return void
     */
    public function up()
    {
        Schema::create('articles', function (Blueprint $table) {
            $table->id();
            $table->string('title', 100);
            $table->text('content');
            $table->timestamps();
        });
    }

    /**
     * Reverse the migrations.
     *
     * @return void
     */
    public function down()
    {
        Schema::dropIfExists('articles');
    }
}

テスト用のDBにテーブルを作るには、php artisan migrateコマンドにオプションで--env=testingを付けて実行します。

php artisan migrate --env=testing

これにより、.env.testingに記載されているDBに対してマイグレーションを実行するようになります。

+------------------------+
| Tables_in_laravel_test |
+------------------------+
| articles               |
| failed_jobs            |
| migrations             |
| users                  |
+------------------------+
+------------+---------------------+------+-----+---------+----------------+
| Field      | Type                | Null | Key | Default | Extra          |
+------------+---------------------+------+-----+---------+----------------+
| id         | bigint(20) unsigned | NO   | PRI | NULL    | auto_increment |
| title      | varchar(100)        | NO   |     | NULL    |                |
| content    | text                | NO   |     | NULL    |                |
| created_at | timestamp           | YES  |     | NULL    |                |
| updated_at | timestamp           | YES  |     | NULL    |                |
+------------+---------------------+------+-----+---------+----------------+

テスト用DBのlaravel_testにarticlesテーブルが作成されました。

テストクラス作成

以下のコマンドでtests/Unitディレクトリ以下にテスト用のクラスを作成することができます。

php artisan make:test [テストクラス名] --unit

Unitディレクトリ以下に作成するクラスには、単体テストレベルの内容を記述していきます。

ArticleTest.php
<?php

namespace Tests\Unit;

use PHPUnit\Framework\TestCase;

class ArticleTest extends TestCase
{
    /**
     * A basic unit test example.
     *
     * @return void
     */
    public function testExample()
    {
        $this->assertTrue(true);
    }
}

--unitオプションを外すとtests/Featureディレクトリ以下にテスト用のクラスを作成できます。
Featureディレクトリ以下に作成するクラスには、機能テストレベルの内容を記述します。

テストコード実装

モデルを作成し、記事データを保存するテストコードを実装してみます。

php artisan make:model Article

モデル作成後、ArticleTest.phpを編集します。

ArticleTest.php
<?php

namespace Tests\Unit;

//use PHPUnit\Framework\TestCase;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Foundation\Testing\WithFaker;
use Tests\TestCase;
use App\Article;

class ArticleTest extends TestCase
{
    /**
     * A basic unit test example.
     *
     * @return void
     */
    public function testExample()
    {
        $this->assertTrue(true);
    }

    /**
     * (1) 記事テーブルにデータをインサート
     */
    public function testInsertTest()
    {
        $article = new Article;
        $article->title = '記事タイトル';
        $article->content = '記事本文';
        $result = $article->save();

        $this->assertTrue($result);
    }
}

php artisan testコマンドを実行すると、testInsertArticleTest関数が実行されたことが分かると思います。

  PASS  Tests\Unit\ArticleTest
  ✓ example
  ✓ insert article test


   PASS  Tests\Unit\ExampleTest
  ✓ basic test


   PASS  Tests\Feature\ExampleTest
  ✓ basic test

  Tests:  4 passed
  Time:   0.35s

テーブルを確認すると、testInsertArticleTest関数に記述したデータが保存されています。

+----+--------------+----------+---------------------+---------------------+
| id | title        | content  | created_at          | updated_at          |
+----+--------------+----------+---------------------+---------------------+
|  1 | 記事タイトル | 記事本文 | 2020-07-27 06:27:12 | 2020-07-27 06:27:12 |
+----+--------------+----------+---------------------+---------------------+

ちなみに、use RefreshDatabase;をテストクラスのスコープ内に記述すると、保存したデータの削除までを行ってくれるため、テストデータを手動で削除する手間を省くことができます。

ランダムなダミーデータの作成

FactoryとFaker

ファクトリーを作成します。

php artisan make:factory [ファクトリ名] --model=[対象のモデル名]

database/factoryディレクトリ以下にファクトリーファイルが作成されます。
以下の例ではtitleカラムに3単語から構成される文、contentカラムに文章を保存するように設定しています。

ArticleFactory.php
<?php

/** @var \Illuminate\Database\Eloquent\Factory $factory */

use App\Article;
use Faker\Generator as Faker;

$factory->define(Article::class, function (Faker $faker) {
    return [
        'title' => $faker->sentence(3),
        'content' => $faker->text,
    ];
});

tests/Unit/ArticleTest.phpに以下のメソッドを追記します。
ArticleFactory.phpで設定したテストデータを3個追加するメソッドです。

ArticleTest.php
    /**
     * (2) 記事テーブルにランダムテストデータをインサート
     */
    public function testInsertFactoryTest()
    {
        $articles = factory(Article::class, 3)->create();
        $count = count($articles);

        $this->assertEquals(3, $count);
    }

php artisan testを実行してarticlesテーブルを確認すると、testInsertFactoryTest関数のテストデータが3つ保存されました。

*************************** 1. row ***************************
        id: 1
     title: 記事タイトル
   content: 記事本文
created_at: 2020-07-27 07:56:16
updated_at: 2020-07-27 07:56:16
*************************** 2. row ***************************
        id: 2
     title: Quasi a.
   content: Consequuntur veritatis aut hic id rem minima. Occaecati et quia hic earum quasi eos. Omnis repellat commodi vitae error ut et provident ipsam.
created_at: 2020-07-27 07:56:17
updated_at: 2020-07-27 07:56:17
*************************** 3. row ***************************
        id: 3
     title: Mollitia aut nostrum sint.
   content: Esse saepe distinctio provident. Placeat unde voluptates expedita et consequatur quas. Excepturi ut quo est et provident velit consequatur.
created_at: 2020-07-27 07:56:17
updated_at: 2020-07-27 07:56:17
*************************** 4. row ***************************
        id: 4
     title: Omnis mollitia omnis illo.
   content: Nam odit aut quam est sunt. Ut ullam perferendis error placeat et. Sed non tenetur esse.
created_at: 2020-07-27 07:56:17
updated_at: 2020-07-27 07:56:17

手作業で1つずつデータを登録したりする時間を短縮できるので便利ですね。

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?