7
10

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 1 year has passed since last update.

Laravel Dusk テストコード作成時の困った場合の対処法

Last updated at Posted at 2020-02-06

Laravel dusk でブラウザテストを作成していて困った部分の対処法のメモです。
間違っている箇所があればご指摘いただければ幸いです。

dusk失敗時の画面スクリーンショット

app\tests\Browser\screenshots配下に失敗時の画面スクリーンショットが作成されます。

要素の表示をwaitで待つ

$browser->waitForText('検索', 30);
$browser->waitFor("#search", 30);

要素がクリックできないとき

素のjsで要素をクリックする(サービスプロバイダにマクロを登録する 参照)

//クリックする
$browser->clickToElement(".search_btn");

画面内に表示されていない要素がクリックできないとき

素のjsで要素にスクロールする(サービスプロバイダにマクロを登録する 参照)

//クリックする
$browser->scrollToElement(".search_btn");

サービスプロバイダにマクロを登録する

ブラウザマクロを作成し、サービスプロバイダにマクロを登録する。

[参考]
https://readouble.com/laravel/5.7/ja/dusk.html (ブラウザマクロ 部分参照)
https://readouble.com/laravel/5.3/ja/providers.html (プロバイダの登録 部分参照)
https://github.com/laravel/dusk/issues/203 (マクロ登録例)

<?php
namespace App\Providers;

use Laravel\Dusk\Browser;
use Illuminate\Support\ServiceProvider;

class DuskServiceProvider extends ServiceProvider
{
    /**
     * Bootstrap the application services.
     *
     * @return void
     */
    public function boot()
    {
        //
    }

    /**
     * Register the application services.
     *
     * @return void
     */
    public function register()
    {
        Browser::macro('scrollToElement', function ($element = null) {
            $this->script("$('html, body').animate({ scrollTop: $('$element').offset().top }, 0);");

            return $this;
        });

        Browser::macro('clickToElement', function ($element = null) {
            $this->script("document.querySelector('$element').click();");

            return $this;
        });

        Browser::macro('switchFrame', function ($frame = null) {
            if ($frame) {
                $this->driver->switchTo()->defaultContent()->switchTo()->frame($frame);
            } else {
                // Main frame
                $this->driver->switchTo()->defaultContent();
            }
            return $this;
        });
    }
}
config/app.php
'providers' => [
    // Other Service Providers

    App\Providers\DuskServiceProvider::class,
],

Class 'App\Providers\DuskServiceProvider' not found登録したマクロが見つからないというエラーが表示された場合、キャッシュファイルを削除すること。

artisan cache:clear
artisan config:clear
artisan route:clear
artisan view:clear

testの中断(Ctrl + c)でDB接続先がずれた?

.env / .env.dusk.local(.env.dusk.{environment}) の中身を確認する。
テスト中は.envの内容が一時backupファイルに退避され、.env.dusk.localの内容が.envに書き込まれるようですが、
中断により.envの内容が.env.dusk.localのまま、backupファイルが残った状態という現象が私のDockerテスト環境では起こりました。
.envを戻し、backupファイルを削除すると戻ります。
(そしてキャッシュファイルも削除)

chromeの設定ファイル (UAを変えたい 画面サイズを変更したいなどはここで)

DuskTestCase.php

    protected function driver()
    {
        $options = (new ChromeOptions)->addArguments([
            '--disable-gpu',
            '--headless',
            '--window-size=375,667',
            '--no-sandbox',
            '--lang=ja_JP',
            '--disable-dev-shm-usage'
        ]);

        $ua = 'Mozilla/5.0 (iPhone; CPU iPhone OS 12_0 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) CriOS/69.0.3497.91 Mobile/15E148 Safari/605.1';
        $options->setExperimentalOption('mobileEmulation', ['userAgent' => $ua]);

        return RemoteWebDriver::create(
            'http://selenium:4444/wd/hub', DesiredCapabilities::chrome()->setCapability(
                ChromeOptions::CAPABILITY, $options
            )
        );
    }

head部分のテスト

duskはcssセレクターで検証しようとすると先頭に'body'がつくため、bodyタグより上の要素の検証をしたい場合はこの書き方で

 $browser->assertSourceHas("<meta name=\"description\" content=\"Qiitaは情報満載!\">");

xpathを使って要素の値を取り出すことも可能

use Laravel\Dusk\Browser;
use Facebook\WebDriver\WebDriverBy; //xpath用
略
$browser->driver->findElement(WebDriverBy::xpath("//link[@rel='canonical']"))->getAttribute('href')

Rspec の before after のようなものを実装したい

[参考]
https://cpoint-lab.co.jp/article/201812/7155/

public function setUp() :void
{
    parent::setUp();
    // テストデーターの準備などを行う
}

PHPUnitのアサーションも使えます

$this->assertEquals($element_count, 50);

セッションの破棄

  $browser->driver->manage()->deleteAllCookies();

function日本語化(@testつける)

/**
 * @test
 */
public function ステータステスト()
{
    $res = $this->get("url");
    $res->assertStatus(200);
}

テストをグループ化して実行 (@group アノテーションでグループ化)

php artisan dusk tests/Browser/ --group samplegroup

/**
 * @group samplegroup
 */
public function sampleTest()
{
   //処理

テストをファイル単位で実行

php artisan dusk tests/Browser/SampleTest.php

Factoryで作成したデーターをテスト実行前に書き換える方法

$this->test_data->fill(["time" => "9:00"])->save();
複数でもOK
$data = ["status" => 1, "time" => "9:00", "end_time" => "10:00"];
$this->test_data->fill($data)->save();

The MAC is invalid.

暗号化キーを再生成する → php artisan key:generate
※暗号化したパスワードが複号できなくなるので取り扱い注意
[引用]
https://error-search.com/error-post/detail/144/The%2BMAC%2Bis%2Binvalid.

APP_DEBUG=true のデバックモードにしたままでテストを実行するとfailする

デバックバーが邪魔をして要素が見えていないため
APP_DEBUG=true は.env.dusk.localに入れない

HTML5 Form Validation ブラウザに依存するエラーメッセージがテストの邪魔をする

問題なければ、ブラウザ自動バリデーションを無効化してしまう

<form action="test.php" method="post" novalidate="novalidate">
7
10
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
7
10

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?