Статьи

Laravel Dusk — интуитивно понятное и простое браузерное тестирование для всех!

Эта статья была рецензирована Юнесом Рафи . Спасибо всем рецензентам SitePoint за то, что сделали контент SitePoint как можно лучше!


Непрерывное тестирование приложений JavaScript, в частности одностраничных, всегда было сложной задачей. С этой целью Laravel недавно выпустила версию 5.4 с новой библиотекой тестирования: Dusk .

Laravel Dusk Logo

С выпуском Dusk Laravel надеется предоставить своим пользователям общий API для тестирования браузеров. Он поставляется с ChromeDriver по умолчанию, и если нам нужна поддержка других браузеров, мы можем использовать Selenium. Он по-прежнему будет иметь этот общий API тестирования для удовлетворения наших потребностей.

В этом руководстве предполагается, что вы запускаете новое приложение Laravel 5.4.

Установка

composer require laravel/dusk 

Это установит самую последнюю стабильную версию пакета через Composer .

Далее нам нужно зарегистрировать DuskServiceProvider в нашем приложении. Мы можем сделать это несколькими способами:

Подход 1

Мы можем включить его в массив providers нашего файла config/app.php .

 ... App\Providers\RouteServiceProvider::class, Laravel\Dusk\DuskServiceProvider::class, ... 

Проблема этого подхода заключается в том, что DuskServiceProvider будет зарегистрирован в нашем приложении для всех сред. Нам не нужно, чтобы Dusk был доступен и зарегистрирован в нашей производственной среде. Мы можем избежать этого с помощью второго подхода.

Подход 2

Зарегистрируйте DuskServiceProvider в классе AppServiceProvider для определенных сред:

 namespace App\Providers; use Illuminate\Support\ServiceProvider; use Laravel\Dusk\DuskServiceProvider; class AppServiceProvider extends ServiceProvider { /** * Register any application services. * * @return void */ public function register() { if ($this->app->environment('local', 'testing', 'staging')) { $this->app->register(DuskServiceProvider::class); } } } 

Далее для завершения процесса установки:

 php artisan dusk:install 

Dusk обеспечат основные леса классов и каталогов. Если мы откроем каталог tests , мы увидим новый каталог Browser с необходимыми лесами для тестов Dusk .

Наш первый тест

Сначала мы создадим рабочий процесс аутентификации, используя предварительно созданный механизм аутентификации Laravel.

 php artisan make:auth 

Давайте теперь создадим наш первый тест Dusk:

 php artisan dusk:make LoginTest 

Приведенная выше команда создаст класс LoginTest в нашем каталоге Browser .

 class LoginTest extends DuskTestCase { /** * A Dusk test example. * * @return void */ public function test_I_can_login_successfully() { $this->browse(function ($browser) { $browser->visit('/login') ->type('email', '[email protected]') ->type('password', 'secret') ->press('Login') ->assertSee('You are logged in!'); }); } } 

В приведенном выше тестовом примере мы проверяем, может ли пользователь успешно войти в систему и увидеть домашнюю страницу с приветственным сообщением.

Примечание. Чтобы этот тест прошел успешно, нам нужен фактический пользователь в базе данных. Для этой демонстрации мы уже настроили пользователя в базе данных с вышеуказанными учетными данными.

Давайте теперь выполним наши тесты Dusk:

 php artisan dusk 

Если у вас есть запись пользователя в базе данных с правильными учетными данными, вы можете увидеть следующий вывод:

 PHPUnit 5.7.6 by Sebastian Bergmann and contributors. .. 2 / 2 (100%) Time: 4.71 seconds, Memory: 10.00MB OK (2 tests, 2 assertions) 

Неудачные тесты

Когда тесты не пройдены, PHPUnit выдает нам некоторые ошибки. Мы должны интерпретировать, что пошло не так.

Dusk имеет несколько заметных дополнений, чтобы удовлетворить этот вариант использования.

Сначала мы изменим наш тест, чтобы преднамеренно не выполнить его:

 public function test_I_can_login_successfully() { $this->browse(function ($browser) { $browser->visit('/login') ->type('email', '[email protected]') ->type('password', 'secret') ->press('Login') ->assertSee('You are logged in!'); }); } 

В приведенном выше тестовом примере мы попытаемся войти в систему с пользователем, которого нет в базе данных. Давайте теперь запустим наши тесты Dusk и посмотрим, что произойдет:

Не удались испытания

Если вы посмотрите внимательно, браузер откроется там как раз перед неудачей теста.

За кулисами Dusk делает снимок экрана со страницей, на которой возникла ошибка, и сохраняет ее в директории (автоматически игнорируемой git):

Screenshot-Dusk-Test-Failed

Это дает нам наглядное представление о том, почему наш тест не пройден. Мы видим, что учетные данные не соответствуют ни одной записи в базе данных. Благодаря такой визуальной обратной связи, Dusk гарантирует, что вы сможете быстро определить проблемы.

Тестирование AJAX-звонков

Dusk предназначен для сквозного тестирования браузером современных приложений JavaScript. В таких приложениях типичный вариант использования ожидает ответа на запросы AJAX.

Мы протестируем функцию « Создать задачу» из демонстрационного приложения. Пожалуйста, клонируйте ее, чтобы выполнить следующие действия:

Сумерки - Создать задачу

Мы используем AJAX-запрос для создания новой задачи, а затем перенаправляем пользователя на страницу списка задач. Это идеальный вариант тестирования.

 php artisan dusk:make CreateTaskTest 

Приведенная выше команда создаст класс CreateTaskTest в нашем каталоге Browser . Давайте теперь напишем тест:

 class CreateTaskTest extends DuskTestCase { /** * A Dusk test example. * * @return void */ public function test_I_can_create_task_successfully() { $this->browse(function ($browser) { $browser->visit('/tasks/create') ->type('title', 'My Task') ->press('Add Task') ->pause(5000) ->assertPathIs('/tasks'); }); } } 

В приведенном выше тесте мы пытаемся добавить новый тест, используя форму AJAX:

  1. Введите название
  2. Нажмите кнопку Добавить задачу
  3. Подождите 5 секунд
  4. Утверждают, что мы перенаправлены на страницу tasks

Давайте теперь запустим наши тесты Dusk и посмотрим результат:

Тест AJAX прошел в сумерках

Как видите, вышеуказанный тест пройден.

Мы также можем использовать метод waitUntilMissing API-интерфейса Dusk для проверки вышеуказанного потока:

 <?php namespace Tests\Browser; use Tests\DuskTestCase; use Illuminate\Foundation\Testing\DatabaseMigrations; class CreateTaskTest extends DuskTestCase { /** * A Dusk test example. * * @return void */ public function test_I_can_create_task_successfully() { $this->browse(function ($browser) { $browser->visit('/tasks/create') ->type('title', 'My Task') ->press('Add Task') ->waitUntilMissing('.btn-primary') ->assertPathIs('/tasks'); }); } } 

Вы можете обратиться к официальной документации для изучения других элементов ожидания, доступных в API.

Более продвинутый пример

В нашем приложении есть пункт меню, в котором, если мы нажмем на ссылку поддержки по электронной почте , появится модальное окно с формой для отправки сообщения поддержки:

Open-Support-Modal

Мы напишем контрольный пример для проверки следующего сценария:

  1. Авторизоваться
  2. См. Поддержку по электронной почте
  3. Нажмите на поддержку по электронной почте
  4. Подтвердите, что модальное окно открывается и в текстовом поле есть идентификатор электронной почты пользователя.

В приведенном выше GIF мы взаимодействуем с нашим пользовательским интерфейсом с помощью мыши и открываем модальное. Давайте воссоздадим вышеуказанный поток в нашем тестовом случае Dusk.

Сначала мы создадим новый тестовый класс:

 php artisan dusk:make SupportEmailsTest 

Затем тест:

 class SupportEmailsTest extends DuskTestCase { /** * A Dusk test example. * * @return void */ public function test_I_can_open_modal_for_support_emails() { $this->browse(function ($browser) { $user = factory(User::class)->create(); $browser->loginAs($user) ->visit('/tasks') ->clickLink('Support Email') ->whenAvailable('#modal-support', function ($modal) use($user) { $modal->assertInputValue('#support-from', $user->email); }); }); } } 

Давайте запустим это:

 php artisan dusk tests/Browser/SupportEmailsTest.php 

Мы видим, что наш тест проходит:

 PHPUnit 5.7.13 by Sebastian Bergmann and contributors. . 1 / 1 (100%) Time: 3.63 seconds, Memory: 12.00MB OK (1 test, 1 assertion) 

Для всех других доступных утверждений, вы можете обратиться к официальной документации .

страницы

Есть концепция « Страницы в сумерках». Это не более чем мощные, многоразовые тестовые классы.

Давайте CreateTaskTest рефакторинг CreateTaskTest с использованием Pages.

Давайте сначала создадим новую страницу:

 php artisan dusk:page CreateTaskPage 

Приведенная выше команда создаст новый класс в каталоге Pages . Давайте рассмотрим каждый метод и изменим его, чтобы он лучше подходил к нашему тестовому сценарию Create Task:

 public function url() { return '/tasks/create'; } 

Метод url определяет URL страницы. Всякий раз, когда эта страница вызывается, Dusk будет переходить по этому URL.

 public function assert(Browser $browser) { $browser->assertPathIs($this->url()); } 

assert определяет утверждения для этой страницы. Всякий раз, когда вызывается CreateTaskPage все утверждения, определенные в методе assert .

В приведенном выше примере мы просто утверждаем, что URL активной страницы является подходящим.

 public function elements() { return [ '@addTask' => '.btn-primary', ]; } 

Метод elements может иметь предопределенные селекторы. Мы можем определить удобочитаемые имена для селекторов и повторно использовать их для этой страницы в различных тестовых случаях. В приведенном выше примере я определил селектор для кнопки « Добавить задачу» .

Давайте теперь CreateTaskTest класс CreateTaskTest и используем селектор:

 class CreateTaskTest extends DuskTestCase { /** * A Dusk test example. * * @return void */ public function test_I_can_create_task_successfully() { $this->browse(function ($browser) { $user = factory(User::class)->create(); $browser->loginAs($user) ->visit(new CreateTaskPage) ->type('title', 'My Task') ->click('@addTask') ->waitUntilMissing('@addTask') ->assertPathIs('/tasks'); }); } } 

Мы изменили наш класс, чтобы использовать CreateTaskPage . Давайте теперь повторно запустим наш тест и посмотрим, все ли работает нормально:

 PHPUnit 5.7.13 by Sebastian Bergmann and contributors. . 1 / 1 (100%) Time: 2.76 seconds, Memory: 12.00MB OK (1 test, 2 assertions) 

Все хорошо!

Вы даже можете определить пользовательские методы для выполнения некоторых повторно используемых действий на определенной странице. Подробнее об этом вы можете прочитать в официальной документации .

Вывод

В этой статье мы представили Laravel Dusk , пакет Laravel, который предоставляет альтернативу для сквозного тестирования JavaScript. Мы рассмотрели параметры конфигурации, необходимые для начала работы, и приведенные выше примеры должны помочь вам заполнить пробелы и дать обзор некоторых других доступных параметров конфигурации.

Как вы используете Dusk? Можете ли вы вспомнить какие-либо дополнительные варианты использования этой библиотеки? Кто они такие? Дайте нам знать об этом в комментариях!