Архитектура Playwright

Урок: Архитектура Playwright

Введение

Когда ты запускаешь тест в Playwright, кажется, что всё происходит «магически»: браузер открывается, страница загружается, кнопки нажимаются, данные проверяются.

Но если заглянуть глубже, становится понятно, что за этим стоит чёткая архитектура.

Представь ресторан:

  • ты делаешь заказ официанту;
  • официант передаёт его на кухню;
  • кухня готовит блюдо;
  • официант приносит результат.

Ты не видишь кухню, но понимаешь, что без неё ничего бы не работало.

Playwright устроен похожим образом:

  • есть тесты (то, что ты пишешь);
  • есть слой управления браузером;
  • есть сам браузер;
  • есть страница, с которой происходит взаимодействие.

Понимание этой архитектуры важно, потому что:

  • помогает писать более стабильные тесты;
  • упрощает отладку;
  • даёт понимание, где именно может возникнуть проблема.

Общая картина: из чего состоит Playwright

На самом верхнем уровне у нас есть тест:

import { test } from '@playwright/test';

test('пример', async ({ page }) => {
  await page.goto('https://example.com');
});

Этот код — только вершина айсберга.

Под капотом происходит следующее:

  1. Playwright запускает браузер;
  2. создаёт контекст;
  3. открывает страницу;
  4. выполняет команды;
  5. возвращает результат.

Это многослойная система, где каждый уровень отвечает за свою часть.


Уровень теста: test runner

Когда ты пишешь:

test('открытие страницы', async ({ page }) => {
  await page.goto('https://example.com');
});

ты работаешь с тестовым раннером.

Он отвечает за:

  • запуск тестов;
  • управление жизненным циклом;
  • передачу объектов (page, browser);
  • параллельное выполнение.

Проще говоря, это «дирижёр», который управляет всем процессом.


Browser — запуск браузера

Под тестом находится уровень браузера.

Playwright умеет запускать браузер:

import { chromium } from 'playwright';

(async () => {
  const browser = await chromium.launch();
})();

Здесь:

  • chromium.launch() запускает браузер;
  • создаётся отдельный процесс браузера.

Важно: браузер — это не страница, а целое приложение (как Chrome).


BrowserContext — изоляция

Следующий уровень — BrowserContext.

const context = await browser.newContext();

Контекст — это как отдельный пользователь.

Он хранит:

  • cookies;
  • localStorage;
  • сессии.

Если открыть два контекста:

const context1 = await browser.newContext();
const context2 = await browser.newContext();

они не будут знать друг о друге.

Это важно для тестов:

  • можно запускать сценарии независимо;
  • нет «грязных» данных от предыдущих тестов.

Page — вкладка браузера

Внутри контекста создаётся страница:

const page = await context.newPage();
await page.goto('https://example.com');

page — это вкладка браузера.

Именно с ней ты работаешь:

  • переходишь по URL;
  • кликаешь;
  • вводишь текст;
  • проверяешь элементы.

Как команды доходят до браузера

Когда ты пишешь:

await page.click('button');

происходит следующее:

  1. Playwright получает команду;
  2. отправляет её в браузер;
  3. браузер находит элемент;
  4. выполняет клик;
  5. возвращает результат.

Ты видишь только одну строку, но внутри это цепочка действий.


Автоматические ожидания

Playwright встроил в архитектуру механизм ожиданий.

await page.click('button');

Даже если кнопка появится через секунду, Playwright:

  • подождёт;
  • проверит, что элемент доступен;
  • только потом кликнет.

Это часть архитектуры — не нужно вручную писать ожидания.


Locator — современный способ работы с элементами

В Playwright есть отдельный слой — локаторы.

const button = page.getByText('Войти');
await button.click();

Локатор:

  • не просто находит элемент;
  • следит за его состоянием;
  • ждёт, пока он станет доступен.

Это делает тесты более устойчивыми.


Связь всех уровней

Соберём всё вместе:

test('пример', async ({ page }) => {
  await page.goto('https://example.com');
  await page.click('button');
});

Под капотом:

  • test runner запускает тест;
  • создаётся browser;
  • создаётся context;
  • создаётся page;
  • команды отправляются в браузер;
  • браузер выполняет действия.

Каждый уровень выполняет свою роль.


Почему архитектура важна

Если тест не работает, важно понимать, где проблема:

  • не открывается браузер → уровень browser;
  • данные «смешиваются» → проблема context;
  • элемент не найден → уровень page/locator;
  • тест падает → уровень test runner.

Без понимания архитектуры это выглядит как «что-то не работает». С пониманием — можно точно найти причину.


Где это используется на практике

Архитектура Playwright особенно важна в:

  • больших проектах;
  • CI/CD;
  • параллельных тестах;
  • тестировании разных пользователей.

Например:

  • несколько пользователей → разные contexts;
  • разные сценарии → разные pages;
  • разные браузеры → разные browser instances.

Итоговое понимание

Playwright — это не просто библиотека, а система из нескольких уровней:

  • тест (test runner);
  • браузер (browser);
  • изоляция (context);
  • вкладка (page);
  • взаимодействие (locator, команды).

Ключевая идея в том, что каждый уровень решает свою задачу.

Понимание этой архитектуры позволяет:

  • писать более надёжные тесты;
  • быстрее находить ошибки;
  • осознанно управлять процессом тестирования.

Когда ты понимаешь, как всё устроено внутри, Playwright перестаёт быть «магией» и становится инструментом, которым ты полностью управляешь.