До вмісту
L-SYSTEM

Чому Playwright і що він насправді робить

Прев’ю-юніт: цей юніт відкритий і без запису на курс. Решта — після запису.

Заняття — вашою мовою: його веде асистент. Матеріал: англійська · Іспит: англійська, без перекладу Як під’єднати асистента

Біль

Прія Раман прийшла в команду автоматизації Aldervane того місяця, коли старий набір тестів ENGAGE вимкнули. Його останній звіт досі лежить у вікі: 212 тестів на WebDriver, sleep(5) у 140 з них і хелпер clickWhenReady, який ніхто не міг пояснити. Його згубили дві речі, і жодна з них не була тим, на що скаржилися.

Таймінг. Класичний скрипт WebDriver надсилає команди через HTTP і на кожну отримує одну відповідь. Він не може знати, чи кнопка, яку він щойно знайшов, усе ще буде прикріплена до DOM за мілісекунду. Тож команди латають цей розрив: sleep(2), потім sleep(5), коли CI повільніший, потім цикл повторів. Набір стає повільним і все одно нестабільним — ви платите обидві ціни, між якими намагалися вибрати.

Накладні витрати. Кожному браузеру потрібен власний бінарний драйвер зі своїм графіком релізів. Том Ачебе, який відповідає за CI-пайплайн, пам'ятає той вівторок, коли автооновлення Chrome на білд-агенті зробило весь прогін ENGAGE червоним із причин, що не мали жодного стосунку до продукту.

A cut-away paper theatre: a coral stage floor in front, a wall with three separate rooms behind it, one person in each, while Priya crosses the stage with a clipboard
ІлюстраціяA cut-away paper theatre: a coral stage floor in front, a wall with three separate rooms behind it, one person in each, while Priya crosses the stage with a clipboard
Опис

A cross-section of a small theatre made of layered cut paper. In front is the stage, its floor in coral; it stands for the browser. Behind it rises a wall with three separate rooms — one seen through a window, two through doorways — and in each room stands one person: one dressed in lavender, one in gold, one in dusty rose. Priya, the stage manager, with dark hair in a low bun, a black turtleneck and a headset, walks across the stage carrying a clipboard. The picture shows one browser holding several isolated browser contexts: the rooms share one building, but each is walled off from the others, just as each context keeps its own cookies and storage and nothing passes from one test's session into another. It does not show pages or tabs, and it does not show how many tests run at once.

Відповідь Playwright на обидві проблеми — архітектурна, тому на неї варто витратити десять хвилин, перш ніж писати хоч рядок.

Механізм

Playwright — це Node-бібліотека від Microsoft, яка керує Chromium, Firefox і WebKit через одне двонаправлене з'єднання з браузерами, які вона сама постачає й версіонує. Два наслідки важливіші за решту.

Він постачає браузери. npx playwright install завантажує збірки, закріплені за вашою версією Playwright. Браузер — це рядок у вашому lock-файлі, а не властивість машини: прогін на ноутбуці Маркуса і прогін на білд-агенті Тома — той самий прогін. Починаючи з Playwright 1.57 браузер родини Chromium, який він завантажує, — це збірка Google Chrome for Testing, а не «сира» збірка Chromium (запуски з вікном використовують chrome, headless-запуски — chrome-headless-shell); у 1.63 це поширилося на Linux на arm64. Ваші тести не змінюються. Змінюється значок на панелі інструментів.

Він знає сторінку. Оскільки з'єднання постійне, а протокол багатий, Playwright може перевірити стан елемента, перш ніж діяти. Перед кліком він чекає, доки елемент буде прикріплений, видимий, стабільний (не анімується), здатний отримувати події (нічим не перекритий) і ввімкнений. Цей набір перевірок називається готовністю до дії (actionability; u10 розбирає її на частини), і саме тому в правильному тесті Playwright немає жодних sleep.

Три об'єкти — три рівні ізоляції

const browser = await chromium.launch();          // one process
const context = await browser.newContext();       // one sealed session
const page    = await context.newPage();          // one tab in that session
  • Браузер — процес. Дорогий: сотні мілісекунд на запуск.
  • Контекст — ізольована сесія: власні cookies, localStorage, дозволи та кеш. Дешевий: мілісекунди. Це одиниця ізоляції тестів.
  • Сторінка — вкладка всередині контексту. Контекст може містити кілька.
cluster_browser Browser — one process runner Test process @playwright/test (one worker) engine Browser engine expensive to start runner->engine one persistent connection ctxA Context A timesheet test own cookies + storage engine->ctxA ctxB Context B invoice test own cookies + storage engine->ctxB ctxC Context C approval test own cookies + storage engine->ctxC pA Page ctxA->pA pB1 Page ctxB->pB1 pB2 Page (second tab) ctxB->pB2 pC Page ctxC->pC
ІлюстраціяOne test process talks over one persistent connection to one browser process, which holds three isolated contexts, each with its own pages
Опис

On the left is the test process — a worker of the @playwright/test runner. A single thick arrow labelled "one persistent connection" leads into a frame labelled "Browser — one process", to a box for the browser engine, marked expensive to start. From the engine, arrows lead to three highlighted boxes, Context A, B and C, each belonging to a different test (timesheet, invoice, approval) and each marked "own cookies + storage". Each context has arrows to its pages: A and C have one page each, B has two, the second marked "second tab". The scheme shows that the expensive object (the browser) is shared, while isolation lives one level down, in the contexts; pages are tabs inside a context and share its session. There are no separate driver binaries anywhere in the picture.

У тест-раннері ці три рядки ви пишете рідко. Раннер дає кожному тесту свіжі контекст і сторінку, тому за замовчуванням тести не передають одне одному cookies і сховище. Перший тест ENGAGE, з baseURL, заданим у конфігу (u03):

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

test('an associate can open this week’s timesheet', async ({ page }) => {
  await page.goto('/timesheets');
  await page.getByRole('link', { name: 'This week' }).click();
  await expect(page.getByRole('heading', { name: 'Weekly timesheet' })).toBeVisible();
});

Три рядки, жодних очікувань, і він працює на всіх трьох рушіях. Те, що лежить під цим, стає важливим, щойно в одному тесті потрібні дві людини — співробітник, який надсилає табель, і Девід Оконкво, керівник проєкту, який його затверджує:

test('the manager sees what the associate submitted', async ({ browser }) => {
  const associate = await browser.newContext({ storageState: 'playwright/.auth/associate.json' });
  const manager   = await browser.newContext({ storageState: 'playwright/.auth/manager.json' });
  const associatePage = await associate.newPage();
  const managerPage   = await manager.newPage();
  // associate submits, manager approves — u19 builds this properly
  await associate.close();
  await manager.close();
});

Два контексти, один браузер: два користувачі, що увійшли в систему й не бачать cookies одне одного. Дві сторінки в одному контексті були б тим самим користувачем у двох вкладках.

Бібліотека і раннер — два різні продукти

playwright — бібліотека автоматизації. @playwright/test — тест-раннер, побудований на ній: фікстури, паралельність, повтори, репортери, конфігурація. У цьому курсі всюди використовується раннер. Фрагмент, який запускає браузер вручну і закриває його наприкінці, — це бібліотека: правильна форма для скрипта і зазвичай неправильна для набору тестів, де часом життя й артефактами вже володіють фікстури.

ШІ-інструменти довкола нього

Playwright у 2025–26 роках постачає також інструменти для ШІ-асистентів програмування. Починаючи з 1.56 npx playwright init-agents генерує для вашого асистента (VS Code, Claude Code або opencode) три визначення Test Agent: planner, який досліджує застосунок і пише тест-план у Markdown, generator, який перетворює план на файли тестів, і healer, який запускає набір і намагається полагодити тести, що падають. Починаючи з 1.62 MCP-сервер Playwright — він дає асистентові змогу керувати браузером через Playwright — входить до комплекту і запускається як npx playwright mcp. Усе, що вони створюють, — звичайний код Playwright, і весь цей курс — про те, як його оцінювати. u04 показує, де вони стоять серед інструментів налагодження; u27 розбирає рев'ю їхнього результату на проєкті.

Ціна

Кажіть про це чесно перед клієнтом:

  • Ви купуєте Node. Якщо інструменти проєкту на Java чи C#, у Playwright є прив'язки, але екосистема, приклади й можливості раннера найсильніші в TypeScript. У змішування стеків реальна ціна підтримки.
  • Браузери великі. Сотні мегабайт на рушій. Ізольованим від мережі або обмеженим за пропускною здатністю білд-агентам потрібна стратегія кешування або контейнер (u25).
  • Автоочікування усуває одну причину нестабільності, а не всі. Набір, у якому паралельні воркери ділять один тестовий обліковий запис, буде в Playwright нестабільним рівно так само, як і раніше.
  • Фреймворк не врятує поганий локатор. Усе подальше залежить від запитів до елементів, які переживають редизайн. Це u07 — година курсу з найбільшою віддачею.
  • Згенеровані тести з'являються швидше за розуміння. Healer, який зробив червоний тест зеленим, або полагодив тест, або приховав дефект продукту. Хтось у команді має вміти відрізнити одне від іншого.

Що ви тепер знаєте

Playwright позбавляє від sleep, знаючи стан сторінки через одне постійне з'єднання, і позбавляє від морочливої роботи з драйверами, постачаючи закріплені браузери — для родини Chromium з 1.57 це збірки Chrome for Testing. Браузер — дорогий процес; контекст — дешева ізольована сесія, що відділяє один тест від іншого; сторінки — вкладки всередині контексту. Раннер видає кожному тесту власний контекст. ШІ-інструменти пишуть код Playwright швидше; правильним цей код вони не роблять.

Завдання

Перевірка тут нічого не змінює: відповіді почнуть зараховуватися після запису на курс.

  1. Заповніть пропуск: одиниця ізоляції тестів у Playwright — об'єкт, який має власні cookies і localStorage, — це браузера.

  2. Перед кліком Playwright чекає, доки елемент пройде набір перевірок. Що з цього НЕ входить до їх числа?

  3. Маркус каже команді ENGAGE: «Ми переходимо на Playwright, тож наші нестабільні тести зникнуть». Напишіть дві-три фрази, що пояснюють йому, які види нестабільності це справді усуває, а яких не торкнеться.

    Це завдання судить рубрика автора — її розбирає асистент, а не сайт.

  4. Маркус знаходить в інтернеті фрагмент, який починається з `const browser = await chromium.launch()` і закінчується `await browser.close()`, і хоче вставити його в набір ENGAGE. Що це і чи варто це вставляти?

  5. Що на схемі архітектури спільне в Context A і Context B, а що в кожного своє?

  6. На першому малюнку за однією сценою розташовано три окремі кімнати, відгороджені одна від одної стінами, по одній людині в кожній. Що позначають кімнати?

  7. Маркус пропонує перевикористовувати одну сторінку в усьому наборі ENGAGE, «бо нові контексти повільні». Яка відповідь на рев'ю правильна?

  8. Старий пайплайн Тома на WebDriver зламався того ранку, коли Chrome автоматично оновився на білд-агенті. Чому те саме оновлення не ламає прогін Playwright?

  9. Починаючи з Playwright 1.57, браузер родини Chromium, який завантажує `npx playwright install`, — це збірка Google Chrome for .

  10. Зіставте кожне завдання з Test Agent Playwright, який його виконує (їх генерує `npx playwright init-agents`, починаючи з 1.56).

    1. Досліджує застосунок і пише тест-план у Markdown
    2. Перетворює план у Markdown на файли тестів Playwright
    3. Запускає набір і намагається полагодити тести, що падають
  11. Прія розбирає чотири нестабільні тести ENGAGE. Які з них усуває очікування Playwright (перевірки готовності до дії та повторювані асерти), а яких воно взагалі не побачить?

    1. Клік спрацьовує до того, як кнопка Submit стає доступною
    2. Два паралельні воркери редагують табель одного спільного тестового облікового запису
    3. Асерт читає тижневий підсумок до завершення перерахунку
    4. Сторонній API курсів валют не відповідає вчасно під час нічного прогону
  12. Напишіть тест, у якому співробітник ENGAGE і керівник проєкту увійшли в систему одночасно. За допомогою фікстури `browser` створіть два контексти, кожен із власного файлу стану сховища (`playwright/.auth/associate.json` і `playwright/.auth/manager.json`), відкрийте по одній сторінці в кожному, перейдіть в обох за абсолютним URL `https://engage.test/timesheets`, перевірте, що в обох видно заголовок 'Weekly timesheet', і наприкінці закрийте обидва контексти.

    Це завдання судить рубрика автора — її розбирає асистент, а не сайт.