События testplane
Обзор
Как устроено описание событий
Ниже описаны все события testplane, на которые можно подписаться в своем плагине.
Описание каждого события начинается с тегов, которые представлены следующими вариантами:
- sync или async обозначают, соответственно, синхронный и асинхронный режимы вызова обработчика события;
- master обозначает, что данное событие доступно из мастер-процесса testplane;
- worker обозначает, что данное событие доступно из воркеров (подпроцессов) testplane;
- can be intercepted обозначает, что данное событие можно перехватить и соответственно, изменить.
Далее идут:
- описание обстоятельств, при которых триггерится событие;
- сниппет с кодом, показывающим как на него подписаться;
- параметры обработчика события;
- и опционально, примеры использования данного события в плагине или плагинах.
Схема генерации событий
Описание последовательности событий
Testplane можно запускать как через CLI (командную строку), так и через её API: из скрипта с помощью команды run.
После запуска testplane загружает все плагины и переходит к парсингу CLI, если она была запущена через CLI, или сразу к стадии инициализации, если её запустили через API.
Парсинг CLI
Если testplane была запущена через CLI, то она триггерит событие CLI. Любой плагин может подписаться на это событие, чтобы добавить свои опции и команды к testplane до того, как testplane распарсит CLI.
Если testplane была запущена с помощью API, то стадия парсинга CLI будет пропущена и сразу же начнется стадия инициализации.
Инициализация
Во время инициализации testplane триггерит событие INIT. Это событие срабатывает всего 1 раз за весь запуск testplane. Подписавшись на это событие, плагины могут выполнить всю необходимую им подготовительную работу: открыть и прочитать какие-то файлы, поднять dev-сервер, инициализировать структуры данных, и т. д. и т. п.
Затем testplane запускает подпроцессы (так называемые воркеры), в рамках которых будут выполняться все тесты. В мастер-процессе testplane тесты не выполняются, а только осуществляется общая оркестрация всего процесса запуска тестов, включая генерацию событий при завершении выполнения отдельных тес тов.
Количество воркеров, которые запускает testplane, регулируется параметром workers в разделе system конфига testplane. При запуске очередного воркера testplane триггерит специальное событие NEW_WORKER_PROCESS.
Все тесты testplane запускает в воркерах, чтобы не столкнуться с ограничениями по памяти и CPU для мастер-процесса. Как только в воркере количество выполненных тестов достигнет значения testsPerWorker, воркер завершит свою работу, и будет запущен новый воркер. Соответственно, будет снова послано событие NEW_WORKER_PROCESS.
Чтение тестов
После этого testplane читает все тесты с файловой системы в мастер-процессе. Посылая для каждого файла, перед тем как его прочитать, событие BEFORE_FILE_READ и после прочтения — событие AFTER_FILE_READ.
После того, как все тесты будут прочитаны, триггерится событие AFTER_TESTS_READ.
Запуск тестов
Затем testplane посылает события RUNNER_START и BEGIN. И стартует новую сессию (браузерную сессию), в которой будут выполняться тесты. При старте сессии testplane триггерит событие SESSION_START.
Если количество тестов, выполненных в рамках одной сессии, достигнет значения параметра testsPerSession, то testplane завершит сессию, стриггерив событие SESSION_END, и запустит новую, послав событие SESSION_START.
Если тест при выполнении упадет с критической ошибкой, то testplane:
- досрочно удалит сессию и браузер, который с ней связан;
- создаст новую сессию;
- запросит новый браузер, и привяжет его к новой сессии.
Это нужно для того, чтобы сбой в сессии при выполнении одного из тестов не начал влиять на запуски последующих тестов.
После создания новой сессии testplane переходит к выполнению тестов. Все тесты выполняются в воркерах, но сам запуск и сбор результатов прогона тестов осуществляется в рамках мастер-процесса. Мастер-процесс триггерит событие SUITE_BEGIN для describe-блоков в файле с тестами и TEST_BEGIN для it-блоков. Если тест отключен с помощью хелперов типа skip.in и тому подобных, то триггерится событие TEST_PENDING.
Далее воркеры получают от мастер-процесса информацию о конкретных тестах, которые они должны запустить. Так как тесты хранятся в файлах, то воркеры читают конкретно те файлы, в которых находятся требуемые тесты. И перед чтением каждого такого файла, в каждом воркере триггерится событие BEFORE_FILE_READ, а после прочтения — событие AFTER_FILE_READ.
После того как соответствующие файлы с тестами будут прочитаны воркером, триггерится событие AFTER_TESTS_READ.
Перечисленные 3 события — BEFORE_FILE_READ, AFTER_FILE_READ и AFTER_TESTS_READ будут триггериться в воркерах в процессе прогона тестов каждый раз как воркеры будут получать от мастер-процесса очередные тесты, которые нужно запустить. Кроме случаев, когда соответствующий файл с тестами уже был прочитан воркером ранее. Так как после первого чтения какого-либо файла, воркер сохраняет его в кэше, чтобы в следующий раз избежать повторного чтения файла с тестами.
Потому что один файл может содержать множество тестов. А запуск тестов идет по отдельным тестам, а не по файлам. Поэтому в какой-то момент времени может прогоняться тест из файла, из которого уже прогонялся другой тест. В таких случаях кэширование защищает от ненужных повторных чтений одних и тех же файлов.
Прежде чем тест будет запущен, триггерится событие NEW_BROWSER. Однако это событие будет триггериться не для всех тестов, так как один и тот же браузер может использоваться много раз для запуска тестов (см. параметр sessionsPerBrowser). Также в случае падения теста с критической ошибкой происходит пересоздание браузера, чтобы не допустить падения других тестов в этом браузере из-за системного сбоя. В этом случае снова будет послано событие NEW_BROWSER.
Завершение тестов
После того как тест завершается, может быть послано событие SESSION_END. Но это только в том случае, если суммарное количество тестов, которые были запущены в использованной сессии, превысило значение testsPerSession.
Далее всё будет зависеть от того, с каким результатом завершился прогон теста. Если тест прошел успешно, то testplane стриггерит событие TEST_PASS. Если тест упал — TEST_FAIL. Если тест упал, но его следует запустить повторно (см. настройки retry и shouldRetry в конфиге testplane), то вместо события TEST_FAIL будет отправлено событие RETRY.
Если тест не нужно запускать повторно, и результат — окончательный, то testplane триггерит события TEST_END и SUITE_END, если речь идет о завершении выполнения describe-блока.
После того как все тесты будут выполнены, а сессии завершены, testplane триггерит события END и RUNNER_END.
Обновление эталонных скриншотов
Во время запуска тестов может произойти обновление эталонных скриншотов. Это может произойти по следующим причинам:
- разработчик запустил testplane в специальном GUI-режиме и дал команду «принять скриншоты»;
- разработчик указал опцию
--update-ref
при запуске testplane; - у тестов не было эталонных скриншотов.
Во всех этих случаях триггерится событие UPDATE_REFERENCE.