From 578c847d9e6e5a0dbb2b96a21f7e6517e36d5ec5 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Fri, 20 Mar 2026 14:39:52 +0300 Subject: [PATCH 01/14] docs: parallelism-add --- docs/basic-guides/parallelism.mdx | 1 + .../current/basic-guides/parallelism.mdx | 309 ++++++++++++++++++ 2 files changed, 310 insertions(+) create mode 100644 docs/basic-guides/parallelism.mdx create mode 100644 i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx diff --git a/docs/basic-guides/parallelism.mdx b/docs/basic-guides/parallelism.mdx new file mode 100644 index 0000000..5c3fb84 --- /dev/null +++ b/docs/basic-guides/parallelism.mdx @@ -0,0 +1 @@ +# Parallelism diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx new file mode 100644 index 0000000..2eabc78 --- /dev/null +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -0,0 +1,309 @@ +# Параллельный запуск тестов + +## Введение + +Testplane запускает тесты параллельно, используя несколько рабочих процессов (воркеров), которые работают одновременно. По умолчанию тесты распределяются между воркерами и выполняются параллельно. Каждый воркер работает с отдельным экземпляром браузера. + +## Модель параллелизма + +Testplane использует двухуровневую модель параллелизма: + +```css +Testplane Master Process +│ +├── Worker 1 +│ ├── Browser Session A → test-1.js +│ └── Browser Session B → test-2.js +│ +├── Worker 2 +│ ├── Browser Session C → test-3.js +│ └── Browser Session D → test-4.js +│ +└── Worker N + └── ... +``` + +Мастер-процесс управляет очередью тестов и распределяет их по воркерам. Каждый воркер — это отдельный `Node.js`-процесс, который может держать одну или несколько браузерных сессий и последовательно выполнять в них тесты. + +Тесты внутри одного `describe`-блока по умолчанию выполняются последовательно — в том порядке, в котором они объявлены. Параллелизм достигается за счет одновременного выполнения тестов из разных файлов и разных браузеров в разных воркерах. + +## Ключевые параметры + +Поведение параллельного запуска контролируется тремя ключевыми настройками в `testplane.config.ts`. + +#### Рабочие процессы + +Параметр `workers` определяет максимальное количество параллельных процессов, которые Testplane запустит одновременно. Каждый воркер обрабатывает один тест за раз, а после завершения теста переходит к следующему из очереди. + +```typescript +// .testplane.config.ts +module.exports = { + workers: 4, // количество параллельных воркеров +}; +``` + +#### Ограничение количества рабочих процессов + +Чтобы ограничить количество воркеров, воспользуйтесь командной строкой. + +```bash +npx testplane --workers 4 +``` + +Или укажите нужное значение в файле `testplane.config.ts` + +```typescript +// .testplane.config.ts +module.exports = { + workers: 4, // количество параллельных процессов + // ... +}; +``` + +Testplane также поддерживает параметр `testsPerWorker` — максимальное количество тестов, которое один воркер выполнит перед перезапуском. + +```typescript +// .testplane.config.ts +module.exports = { + workers: 4, + testsPerWorker: 50, // воркер перезапустится после 50 тестов +}; +``` + +#### Лимит сессий на браузер + +Параметр `sessionsPerBrowser` отвечает за максимальное число одновременно открытых браузерных сессий для одного браузера. + +```typescript +export default { + sessionsPerBrowser: 5, // по умолчанию: 1 + browsers: { + chrome: { + sessionsPerBrowser: 10, // переопределение на уровне браузера + desiredCapabilities: { + browserName: "chrome", + }, + }, + firefox: { + sessionsPerBrowser: 3, + desiredCapabilities: { + browserName: "firefox", + }, + }, + }, +}; +``` + +Важные моменты: + +- лимит применяется к каждому браузеру независимо; +- суммарное число активных сессий может превышать значение workers; +- воркер может управлять несколькими сессиями последовательно, но одновременно — только одной. + +#### Лимит тестов за сессию + +Параметр `testsPerSession` отвечает за максимальное число тестов, которые выполнятся в одной браузерной сессии до ее пересоздания. + +```typescript +export default { + testsPerSession: 20, // по умолчанию: Infinity + browsers: { + chrome: { + testsPerSession: 50, + }, + }, +}; +``` + +Варианты использования: + +- 1 — каждый тест в новой сессии (максимальная изоляция, медленнее); +- `Infinity` — все тесты в одной сессии (быстро, но есть риск утечек состояния); +- 20–50 — баланс скорости и изоляции (рекомендуется для большинства проектов). + +## Отключение параллелизма + +Чтобы запустить все тесты последовательно, ограничьте количество воркеров до одного через командную строку. + +```bash +npx testplane --workers 1 +``` + +Или напрямую в файле `testplane.config.ts`. + +```typescript +// .testplane.conf.js +module.exports = { + workers: 1, +}; +``` + +## Рекомендуемые настройки и их расчет + +#### Базовая формула + +Отправной точкой для расчета является количество ядер CPU и доступная память на машине, где запускаются браузеры (Selenium Grid, Selenoid, или локальная машина). + +```text +sessionsPerBrowser = количество доступных слотов на grid / количество браузеров +workers = sessionsPerBrowser × количество браузеров +testsPerSession = 20–40 (для ускорения) или 1 (для максимальной изоляции) +``` + +#### Пример расчета для CI + +Допустим, ваш Selenoid-сервер выдерживает 20 одновременных браузеров, и вы тестируете в 2 браузерах (chrome, firefox). + +```typescript +export default { + workers: 20, + + browsers: { + chrome: { + sessionsPerBrowser: 10, // 20 слотов / 2 браузера + testsPerSession: 20, // переиспользуем сессию для 20 тестов + }, + firefox: { + sessionsPerBrowser: 10, + testsPerSession: 20, + }, + }, +}; +``` + +#### Пример расчета для локального запуска + +На локальной машине ресурсы ограничены. Рекомендуется: + +```typescript +export default { + workers: 4, // ~количество ядер CPU / 2 + + browsers: { + chrome: { + sessionsPerBrowser: 4, + testsPerSession: 5, + }, + }, +}; +``` + +#### Рекомендации по testsPerSession + +| Сценарий | Рекомендуемое значение | +| ----------------------------------------------------------- | ---------------------- | +| Тесты полностью изолированы, нет глобального состояния | 20–50 | +| Тесты частично изолированы (авторизация через `beforeEach`) | 10–20 | +| Тесты меняют глобальное состояние браузера | 1 | +| Отладка нестабильных тестов | 1 | +| Максимальное ускорение на `CI` | 40–100 | + +## Шардирование + +При наличии тысяч тестов время одного запуска может быть неприемлемо большим даже при максимальном параллелизме. В таких случаях используют шардирование — разбивку всего набора тестов на несколько независимых частей (чанков), которые запускаются параллельно на разных машинах или в разных `CI`-джобах. + +#### Плагин testplane-chunks + +Для шардирования в Testplane используется официальный плагин `@testplane/chunks`. + +#### Установка и подключение + +Чтобы установить плагин `@testplane/chunks`, выполните команду. + +```bash +npm install -D @testplane/chunks +``` + +И укажите параметры в файле `testplane.config.ts`. + +```typescript +// testplane.config.ts +export default { + plugins: { + "@testplane/chunks": { + enabled: true, + }, + }, + // остальные настройки... +}; +``` + +#### Как работает шардирование + +Плагин делит список всех тестов на равные части по количеству тестов. Каждый запуск получает свой номер чанка и выполняет только свою часть тестов. + +```yaml +Все тесты (1000 штук) +│ +├── Чанк 1/4: тесты 1–250 → CI Job 1 +├── Чанк 2/4: тесты 251–500 → CI Job 2 +├── Чанк 3/4: тесты 501–750 → CI Job 3 +└── Чанк 4/4: тесты 751–1000 → CI Job 4 +``` + +Все 4 джобы выполняются параллельно, что теоретически сокращает общее время в 4 раза. + +#### Запуск с указанием чанка + +Номер чанка и общее количество чанков передаются через переменные окружения или CLI-параметры: + +```bash +# Запустить первый чанк из четырех +npx testplane --chunks 4 --chunk 1 + +# Запустить второй чанк из четырех +npx testplane --chunks 4 --chunk 2 +``` + +Или через переменные окружения: + +```bash +TESTPLANE_CHUNKS=4 TESTPLANE_CHUNK=1 npx testplane +``` + +#### Пример конфигурации GitHub Actions + +```yaml +# .github/workflows/tests.yml +jobs: + test: + strategy: + matrix: + chunk: [1, 2, 3, 4] + steps: + - uses: actions/checkout@v3 + - run: npm ci + - run: npx testplane --chunks 4 --chunk ${{ matrix.chunk }} +``` + +#### Как рассчитать оптимальное количество чанков + +```scss +Количество чанков = ceil(Общее время запуска / Целевое время запуска) +``` + +Пример: + +```text +2000 тестов выполняются за 60 минут на одной машине +Цель: уложиться в 10 минут +Необходимо: ceil(60 / 10) = 6 чанков +``` + +При этом убедитесь, что в каждом чанке достаточно тестов для эффективной загрузки воркеров: + +```text +Тестов в одном чанке = Общее число тестов / Количество чанков + = 2000 / 6 ≈ 333 теста на чанк +``` + +333 теста на чанк при `sessionsPerBrowser`: 10 и `testsPerSession`: 20 — разумное соотношение. + +## Сводная таблица настроек + +| Настройка | Уровень | За что отвечает | Влияет на | +| -------------------- | ------------ | ---------------------------------------------------------- | ------------------------------------------------- | +| `workers` | Глобальный | Количество параллельных `Node.js`-процессов | CPU, память на машине с тестами | +| `sessionsPerBrowser` | Браузер | Количество одновременных браузерных сессий | Нагрузку на `grid`, скорость прохождения | +| `testsPerSession` | Браузер | Сколько тестов выполнить в одной сессии до ее пересоздания | Скорость (меньше накладных расходов) vs изоляция | +| `chunks` (плагин) | `CI`-уровень | Разбивка всего набора на независимые части | Горизонтальное масштабирование на несколько машин | From fa7c1be60aeeb3fc407836ec469b325be30a2f41 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 6 Apr 2026 12:14:35 +0300 Subject: [PATCH 02/14] docs: perallelism-fix --- .../current/basic-guides/parallelism.mdx | 502 ++++++++++-------- 1 file changed, 294 insertions(+), 208 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index 2eabc78..cec6b06 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -1,202 +1,171 @@ # Параллельный запуск тестов -## Введение +## Параллельность в Testplane -Testplane запускает тесты параллельно, используя несколько рабочих процессов (воркеров), которые работают одновременно. По умолчанию тесты распределяются между воркерами и выполняются параллельно. Каждый воркер работает с отдельным экземпляром браузера. +Параллельность в Testplane — это возможность одновременно выполнять несколько тестовых сценариев в разных браузерных сессиях, чтобы сократить общее время прогона тестов. -## Модель параллелизма +#### sessionsPerBrowser -Testplane использует двухуровневую модель параллелизма: +В конфигурационном файле объявляются типы браузеров в поле `browsers`. Для каждого типа браузера независимо настраивается, сколько экземпляров может работать одновременно: -```css -Testplane Master Process -│ -├── Worker 1 -│ ├── Browser Session A → test-1.js -│ └── Browser Session B → test-2.js -│ -├── Worker 2 -│ ├── Browser Session C → test-3.js -│ └── Browser Session D → test-4.js -│ -└── Worker N - └── ... +```typescript +// .testplane.config.ts +export default { + browsers: { + chrome: { + sessionsPerBrowser: 5, // до 5 параллельных сессий Chrome + }, + firefox: { + sessionsPerBrowser: 2, // до 2 параллельных сессий Firefox + }, + }, +}; ``` -Мастер-процесс управляет очередью тестов и распределяет их по воркерам. Каждый воркер — это отдельный `Node.js`-процесс, который может держать одну или несколько браузерных сессий и последовательно выполнять в них тесты. +Параметр `sessionsPerBrowser` является ключевым в рамках управления параллельностью. Он определяет, сколько браузеров одного типа Testplane запустит одновременно. По умолчанию значение: `1`. -Тесты внутри одного `describe`-блока по умолчанию выполняются последовательно — в том порядке, в котором они объявлены. Параллелизм достигается за счет одновременного выполнения тестов из разных файлов и разных браузеров в разных воркерах. +#### Воркеры -## Ключевые параметры +Параметр `workers` определяет, сколько дочерних процессов-воркеров будет запущено. Архитектурно это выглядит так: -Поведение параллельного запуска контролируется тремя ключевыми настройками в `testplane.config.ts`. +* `Master`-процесс — координирует запуск, формирует очереди тестов и раздает задания воркерам +* `Worker`-процессы — непосредственно исполняют тесты -#### Рабочие процессы +Каждый воркер — это отдельный поток, но внутри одного воркера тесты выполняются конкурентно: когда тест ждет ответа от браузера (`await`), воркер не простаивает, а переключается на следующий тест. Поэтому даже один воркер способен обслуживать множество параллельных браузерных сессий. -Параметр `workers` определяет максимальное количество параллельных процессов, которые Testplane запустит одновременно. Каждый воркер обрабатывает один тест за раз, а после завершения теста переходит к следующему из очереди. +:::warning Важно +`workers` и `sessionsPerBrowser` — независимые ограничения. Увеличение числа воркеров не увеличивает реальную параллельность, если `sessionsPerBrowser` остается прежним. +::: -```typescript -// .testplane.config.ts -module.exports = { - workers: 4, // количество параллельных воркеров -}; -``` - -#### Ограничение количества рабочих процессов +#### testsPerSession -Чтобы ограничить количество воркеров, воспользуйтесь командной строкой. +Параметр `testsPerSession` отвечает за то, сколько тестов можно запускать последовательно в одной сессии браузера. Параметр ограничивает переиспользование сессии, чтобы не допустить падения тестов из-за деградации браузера, и не имеет отношения к параллельному запуску тестов. -```bash -npx testplane --workers 4 -``` +#### Пример -Или укажите нужное значение в файле `testplane.config.ts` +В рамках примера исполнять тесты будет один воркер: ```typescript -// .testplane.config.ts -module.exports = { - workers: 4, // количество параллельных процессов - // ... -}; +system: { + workers: 1, + }, ``` - -Testplane также поддерживает параметр `testsPerWorker` — максимальное количество тестов, которое один воркер выполнит перед перезапуском. +Параметру sessionsPerBrowser присвоены значения `5`: ```typescript -// .testplane.config.ts -module.exports = { - workers: 4, - testsPerWorker: 50, // воркер перезапустится после 50 тестов -}; +chrome: { + headless: true, + desiredCapabilities: { + browserName: "chrome" + }, + sessionsPerBrowser: 5, // 5 параллельных сессий Chrome + testsPerSession: 3, + waitTimeout: 10000, + } ``` - -#### Лимит сессий на браузер - -Параметр `sessionsPerBrowser` отвечает за максимальное число одновременно открытых браузерных сессий для одного браузера. +и `2`: ```typescript -export default { - sessionsPerBrowser: 5, // по умолчанию: 1 - browsers: { - chrome: { - sessionsPerBrowser: 10, // переопределение на уровне браузера +firefox: { + headless: true, desiredCapabilities: { - browserName: "chrome", + browserName: "firefox" }, - }, - firefox: { - sessionsPerBrowser: 3, - desiredCapabilities: { - browserName: "firefox", - }, - }, - }, -}; + sessionsPerBrowser: 2, // 2 параллельные сессии Firefox + testsPerSession: 3, + waitTimeout: 10000, + } ``` -Важные моменты: - -- лимит применяется к каждому браузеру независимо; -- суммарное число активных сессий может превышать значение workers; -- воркер может управлять несколькими сессиями последовательно, но одновременно — только одной. - -#### Лимит тестов за сессию - -Параметр `testsPerSession` отвечает за максимальное число тестов, которые выполнятся в одной браузерной сессии до ее пересоздания. +Далее тесты: ```typescript -export default { - testsPerSession: 20, // по умолчанию: Infinity - browsers: { - chrome: { - testsPerSession: 50, - }, - }, -}; -``` +describe("test examples", () => { + it("Поиск элемента по data-testid", async ({ browser }) => { + // Открываем страницу и ждем ее загрузки + await browser.openAndWait("https://testplane.io/"); -Варианты использования: + // Ищем элемент по атрибуту data-testid + const element = await browser.$('[data-testid="main-content"]'); -- 1 — каждый тест в новой сессии (максимальная изоляция, медленнее); -- `Infinity` — все тесты в одной сессии (быстро, но есть риск утечек состояния); -- 20–50 — баланс скорости и изоляции (рекомендуется для большинства проектов). + // Проверяем существование элемента в DOM + const isExisting = await element.isExisting(); + console.log("Элемент с data-testid существует:", isExisting); + }); -## Отключение параллелизма + it("Поиск элемента на главной странице", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); -Чтобы запустить все тесты последовательно, ограничьте количество воркеров до одного через командную строку. + // Ищем элемент по классу "navbar" + const navbar = await browser.$(".navbar"); -```bash -npx testplane --workers 1 -``` + // Проверяем, отображается ли элемент на странице + const isDisplayed = await navbar.isDisplayed(); + console.log("Навбар отображается:", isDisplayed); + }); -Или напрямую в файле `testplane.config.ts`. + it("Поиск элемента по id на главной странице", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); -```typescript -// .testplane.conf.js -module.exports = { - workers: 1, -}; -``` + // Ищем элемент по id "__docusaurus" + const main = await browser.$("#__docusaurus"); -## Рекомендуемые настройки и их расчет + // Проверяем, отображается ли элемент на странице + const isDisplayed = await main.isDisplayed(); + console.log("Элемент отображается:", isDisplayed); + }); -#### Базовая формула + it("Поиск элемента по типу атрибута", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); -Отправной точкой для расчета является количество ядер CPU и доступная память на машине, где запускаются браузеры (Selenium Grid, Selenoid, или локальная машина). + // Ищем кнопку по атрибуту type="button" + // Формат селектора: element[type="value"] + const button = await browser.$('button[type="button"]'); -```text -sessionsPerBrowser = количество доступных слотов на grid / количество браузеров -workers = sessionsPerBrowser × количество браузеров -testsPerSession = 20–40 (для ускорения) или 1 (для максимальной изоляции) -``` + // Проверяем существование элемента в DOM + const isExisting = await button.isExisting(); + console.log("Кнопка существует:", isExisting); + }); -#### Пример расчета для CI + it("Поиск элемента по тексту", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); -Допустим, ваш Selenoid-сервер выдерживает 20 одновременных браузеров, и вы тестируете в 2 браузерах (chrome, firefox). + // Ищем элемент по тексту внутри него + const link = await browser.$('//a[text()="Docs"]'); -```typescript -export default { - workers: 20, + // Проверяем существование элемента в DOM + const isExisting = await link.isExisting(); + console.log("Элемент с текстом существует:", isExisting); + }); - browsers: { - chrome: { - sessionsPerBrowser: 10, // 20 слотов / 2 браузера - testsPerSession: 20, // переиспользуем сессию для 20 тестов - }, - firefox: { - sessionsPerBrowser: 10, - testsPerSession: 20, - }, - }, -}; -``` + it("Поиск элемента по атрибуту", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); -#### Пример расчета для локального запуска + // Ищем элемент по атрибуту type + const button = await browser.$('//button[@type="button"]'); -На локальной машине ресурсы ограничены. Рекомендуется: + // Проверяем существование элемента в DOM + const isExisting = await button.isExisting(); + console.log("Элемент с атрибутом существует:", isExisting); + }); -```typescript -export default { - workers: 4, // ~количество ядер CPU / 2 + it("Поиск кнопки с помощью метода getByRole", async ({ browser }) => { + await browser.url("https://testplane.io/"); - browsers: { - chrome: { - sessionsPerBrowser: 4, - testsPerSession: 5, - }, - }, -}; + const button = await browser.getByRole("button", { name: "Get started" }); + + await button.click(); + }); +}); ``` -#### Рекомендации по testsPerSession +#### Как работает параллелизм в данном примере + +Когда воркер получает тесты для Chrome, он открывает до 5 окон браузера одновременно. Каждое окно — это отдельная независимая сессия со своим `sessionId`. Для Firefox логика та же, но одновременно работают только 2 окна. -| Сценарий | Рекомендуемое значение | -| ----------------------------------------------------------- | ---------------------- | -| Тесты полностью изолированы, нет глобального состояния | 20–50 | -| Тесты частично изолированы (авторизация через `beforeEach`) | 10–20 | -| Тесты меняют глобальное состояние браузера | 1 | -| Отладка нестабильных тестов | 1 | -| Максимальное ускорение на `CI` | 40–100 | +:::warning Важно +`workers` управляет количеством `Node.js`-процессов, а `sessionsPerBrowser` — количеством одновременных браузерных сессий внутри каждого воркера. При workers: 1 все 7 сессий управляются одним процессом. +::: ## Шардирование @@ -204,11 +173,11 @@ export default { #### Плагин testplane-chunks -Для шардирования в Testplane используется официальный плагин `@testplane/chunks`. +Плагин `@testplane/chunks` позволяет распараллелить запуск тестов на нескольких серверах, тем самым ускорив процесс. Однако сам плагин не занимается какой-либо оркестрацией, распараллеливанием запуска или слиянием получившихся отдельных отчетов в один итоговый отчет. #### Установка и подключение -Чтобы установить плагин `@testplane/chunks`, выполните команду. +Для установки выполните команду: ```bash npm install -D @testplane/chunks @@ -217,93 +186,210 @@ npm install -D @testplane/chunks И укажите параметры в файле `testplane.config.ts`. ```typescript -// testplane.config.ts -export default { +module.exports = { plugins: { - "@testplane/chunks": { - enabled: true, + '@testplane/chunks': { + count: 7, // Разбить тесты на 7 порций (чанков) + run: 1 // Запустить первую порцию }, + + // другие плагины Testplane... }, - // остальные настройки... + + // другие настройки Testplane... }; ``` -#### Как работает шардирование +#### Расшифровка параметров конфигурации -Плагин делит список всех тестов на равные части по количеству тестов. Каждый запуск получает свой номер чанка и выполняет только свою часть тестов. +| Параметр | Тип | По умолчанию | Описание | +| --- | --- | --- | --- | +| `count` | `Number` | `1` | Количество порций (чанков), на которые нужно разбить набор тестов | +| `run` | `Number` | `1` | Номер чанка, тесты из которого нужно запустить | -```yaml -Все тесты (1000 штук) -│ -├── Чанк 1/4: тесты 1–250 → CI Job 1 -├── Чанк 2/4: тесты 251–500 → CI Job 2 -├── Чанк 3/4: тесты 501–750 → CI Job 3 -└── Чанк 4/4: тесты 751–1000 → CI Job 4 -``` +#### Как разбить запуск тестов -Все 4 джобы выполняются параллельно, что теоретически сокращает общее время в 4 раза. +В качестве примера будет использован следующий набор тестов: -#### Запуск с указанием чанка +```typescript +describe("test examples", () => { + it("Поиск элемента по data-testid", async ({ browser }) => { + // Открываем страницу и ждем ее загрузки + await browser.openAndWait("https://testplane.io/"); -Номер чанка и общее количество чанков передаются через переменные окружения или CLI-параметры: + // Ищем элемент по атрибуту data-testid + const element = await browser.$('[data-testid="main-content"]'); -```bash -# Запустить первый чанк из четырех -npx testplane --chunks 4 --chunk 1 + // Проверяем существование элемента в DOM + const isExisting = await element.isExisting(); + console.log("Элемент с data-testid существует:", isExisting); + }); -# Запустить второй чанк из четырех -npx testplane --chunks 4 --chunk 2 -``` + it("Поиск элемента на главной странице", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); -Или через переменные окружения: + // Ищем элемент по классу "navbar" + const navbar = await browser.$(".navbar"); -```bash -TESTPLANE_CHUNKS=4 TESTPLANE_CHUNK=1 npx testplane + // Проверяем, отображается ли элемент на странице + const isDisplayed = await navbar.isDisplayed(); + console.log("Навбар отображается:", isDisplayed); + }); + + it("Поиск элемента по id на главной странице", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); + + // Ищем элемент по id "__docusaurus" + const main = await browser.$("#__docusaurus"); + + // Проверяем, отображается ли элемент на странице + const isDisplayed = await main.isDisplayed(); + console.log("Элемент отображается:", isDisplayed); + }); + + it("Поиск элемента по типу атрибута", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); + + // Ищем кнопку по атрибуту type="button" + // Формат селектора: element[type="value"] + const button = await browser.$('button[type="button"]'); + + // Проверяем существование элемента в DOM + const isExisting = await button.isExisting(); + console.log("Кнопка существует:", isExisting); + }); + + it("Поиск элемента по тексту", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); + + // Ищем элемент по тексту внутри него + const link = await browser.$('//a[text()="Docs"]'); + + // Проверяем существование элемента в DOM + const isExisting = await link.isExisting(); + console.log("Элемент с текстом существует:", isExisting); + }); + + it("Поиск элемента по атрибуту", async ({ browser }) => { + await browser.openAndWait("https://testplane.io/"); + + // Ищем элемент по атрибуту type + const button = await browser.$('//button[@type="button"]'); + + // Проверяем существование элемента в DOM + const isExisting = await button.isExisting(); + console.log("Элемент с атрибутом существует:", isExisting); + }); + + it("Поиск кнопки с помощью метода getByRole", async ({ browser }) => { + await browser.url("https://testplane.io/"); + + const button = await browser.getByRole("button", { name: "Get started" }); + + await button.click(); + }); +}); ``` +Резделение тестов на чанки: -#### Пример конфигурации GitHub Actions - -```yaml -# .github/workflows/tests.yml -jobs: - test: - strategy: - matrix: - chunk: [1, 2, 3, 4] - steps: - - uses: actions/checkout@v3 - - run: npm ci - - run: npx testplane --chunks 4 --chunk ${{ matrix.chunk }} +```css +Чанк 0 → тесты 1, 2, 3 (≈ первая треть) +Чанк 1 → тесты 4, 5 (≈ вторая треть) +Чанк 2 → тесты 6, 7 (≈ третья треть) ``` -#### Как рассчитать оптимальное количество чанков +Запуск каждого чанка отдельно через терминал: -```scss -Количество чанков = ceil(Общее время запуска / Целевое время запуска) +```bash +# Терминал 1 — Чанк 0 +CHUNKS_COUNT=3 CHUNKS_CURRENT=0 npx testplane + +# Терминал 2 — Чанк 1 +CHUNKS_COUNT=3 CHUNKS_CURRENT=1 npx testplane + +# Терминал 2 — Чанк 2 +CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane ``` -Пример: +#### Как плагин делит тесты -```text -2000 тестов выполняются за 60 минут на одной машине -Цель: уложиться в 10 минут -Необходимо: ceil(60 / 10) = 6 чанков +```css +Все тесты (после сортировки по fullTitle): +┌───┬────────────────────────────────────────────────────────┐ +│ 1 │ test examples. Поиск кнопки с помощью метода getByRole │ +├───┼────────────────────────────────────────────────────────┤ +│ 2 │ test examples. Поиск элемента на главной странице │ +├───┼────────────────────────────────────────────────────────┤ +│ 3 │ test examples. Поиск элемента по атрибуту │ +├───┼────────────────────────────────────────────────────────┤ +│ 4 │ test examples. Поиск элемента по data-testid │ +├───┼────────────────────────────────────────────────────────┤ +│ 5 │ test examples. Поиск элемента по id на главной стр. │ +├───┼────────────────────────────────────────────────────────┤ +│ 6 │ test examples. Поиск элемента по тексту │ +├───┼────────────────────────────────────────────────────────┤ +│ 7 │ test examples. Поиск элемента по типу атрибута │ +└───┴────────────────────────────────────────────────────────┘ + + │ + ▼ CHUNKS_COUNT=3 + +┌──────────┬──────────┬──────────┐ +│ Чанк 0 │ Чанк 1 │ Чанк 2 │ +├──────────┼──────────┼──────────┤ +│ тест 1 │ тест 4 │ тест 6 │ +│ тест 2 │ тест 5 │ тест 7 │ +│ тест 3 │ │ │ +└──────────┴──────────┴──────────┘ ``` -При этом убедитесь, что в каждом чанке достаточно тестов для эффективной загрузки воркеров: +:::tip Примечание +Главная идея чанков: если `workers` распределяет тесты внутри одного процесса, то чанки делят тесты между несколькими независимыми процессами — например, на разных `CI`-агентах или на одной машине через `concurrently`. +::: + +## Рекомендуемые настройки и их расчет + +| Параметр | Значение | Объяснение | +|---------------------|-------------------------------------------------------|-------------------------------------------------------------------------------------------------------------| +| `workers` | 8 | Рекомендованное значение — 8, но не больше количества ядер CPU | +| `sessionsPerBrowser`| min(слоты_грида_для_браузера, доступная_RAM / RAM_одного_браузера) | Реальное ограничение — ресурсы грида (слоты и RAM) | +| `testsPerSession` | min(тесты_до_деградации_браузера, тесты_за_время_жизни_сессии_грида) | Сессию нельзя переиспользовать бесконечно — браузер деградирует. Если грид принудительно закрывает сессию по времени, нужно вписаться в этот лимит. Параметр не влияет на параллельность, но влияет на стабильность прогона. | -```text -Тестов в одном чанке = Общее число тестов / Количество чанков - = 2000 / 6 ≈ 333 теста на чанк + +#### Пример + +```css +// CPU: 16 ядер +// Грид: Chrome 20 слотов, Firefox 10 слотов +// RAM грида: 8GB, Chrome ~500MB, Firefox ~300MB +// Грид убивает сессию через 10 минут +// Средний тест: 30 секунд +// Деградация браузера: после 100 тестов + +system: { + workers: 8 // min(8, 16) +}, +browsers: { + chrome: { + sessionsPerBrowser: 16, // min(20, 8000/500) + testsPerSession: 20 // min(100, 600/30) + }, + firefox: { + sessionsPerBrowser: 10, // min(10, 8000/300=26) + testsPerSession: 20 // min(100, 600/30) + } +} ``` -333 теста на чанк при `sessionsPerBrowser`: 10 и `testsPerSession`: 20 — разумное соотношение. -## Сводная таблица настроек -| Настройка | Уровень | За что отвечает | Влияет на | -| -------------------- | ------------ | ---------------------------------------------------------- | ------------------------------------------------- | -| `workers` | Глобальный | Количество параллельных `Node.js`-процессов | CPU, память на машине с тестами | -| `sessionsPerBrowser` | Браузер | Количество одновременных браузерных сессий | Нагрузку на `grid`, скорость прохождения | -| `testsPerSession` | Браузер | Сколько тестов выполнить в одной сессии до ее пересоздания | Скорость (меньше накладных расходов) vs изоляция | -| `chunks` (плагин) | `CI`-уровень | Разбивка всего набора на независимые части | Горизонтальное масштабирование на несколько машин | + + + + + + + + + + From 7440dd51bc24ca6ec3c8062a97366444fcbac3fe Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 6 Apr 2026 12:15:32 +0300 Subject: [PATCH 03/14] docs: character-fix --- .../current/basic-guides/parallelism.mdx | 101 +++++++----------- 1 file changed, 39 insertions(+), 62 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index cec6b06..37d4074 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -11,14 +11,14 @@ ```typescript // .testplane.config.ts export default { - browsers: { - chrome: { - sessionsPerBrowser: 5, // до 5 параллельных сессий Chrome - }, - firefox: { - sessionsPerBrowser: 2, // до 2 параллельных сессий Firefox + browsers: { + chrome: { + sessionsPerBrowser: 5, // до 5 параллельных сессий Chrome + }, + firefox: { + sessionsPerBrowser: 2, // до 2 параллельных сессий Firefox + }, }, - }, }; ``` @@ -28,8 +28,8 @@ export default { Параметр `workers` определяет, сколько дочерних процессов-воркеров будет запущено. Архитектурно это выглядит так: -* `Master`-процесс — координирует запуск, формирует очереди тестов и раздает задания воркерам -* `Worker`-процессы — непосредственно исполняют тесты +- `Master`-процесс — координирует запуск, формирует очереди тестов и раздает задания воркерам +- `Worker`-процессы — непосредственно исполняют тесты Каждый воркер — это отдельный поток, но внутри одного воркера тесты выполняются конкурентно: когда тест ждет ответа от браузера (`await`), воркер не простаивает, а переключается на следующий тест. Поэтому даже один воркер способен обслуживать множество параллельных браузерных сессий. @@ -43,13 +43,14 @@ export default { #### Пример -В рамках примера исполнять тесты будет один воркер: +В рамках примера исполнять тесты будет один воркер: ```typescript system: { workers: 1, }, ``` + Параметру sessionsPerBrowser присвоены значения `5`: ```typescript @@ -63,6 +64,7 @@ chrome: { waitTimeout: 10000, } ``` + и `2`: ```typescript @@ -188,9 +190,9 @@ npm install -D @testplane/chunks ```typescript module.exports = { plugins: { - '@testplane/chunks': { + "@testplane/chunks": { count: 7, // Разбить тесты на 7 порций (чанков) - run: 1 // Запустить первую порцию + run: 1, // Запустить первую порцию }, // другие плагины Testplane... @@ -202,10 +204,10 @@ module.exports = { #### Расшифровка параметров конфигурации -| Параметр | Тип | По умолчанию | Описание | -| --- | --- | --- | --- | -| `count` | `Number` | `1` | Количество порций (чанков), на которые нужно разбить набор тестов | -| `run` | `Number` | `1` | Номер чанка, тесты из которого нужно запустить | +| Параметр | Тип | По умолчанию | Описание | +| -------- | -------- | ------------ | ----------------------------------------------------------------- | +| `count` | `Number` | `1` | Количество порций (чанков), на которые нужно разбить набор тестов | +| `run` | `Number` | `1` | Номер чанка, тесты из которого нужно запустить | #### Как разбить запуск тестов @@ -290,6 +292,7 @@ describe("test examples", () => { }); }); ``` + Резделение тестов на чанки: ```css @@ -314,33 +317,21 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane #### Как плагин делит тесты ```css -Все тесты (после сортировки по fullTitle): -┌───┬────────────────────────────────────────────────────────┐ -│ 1 │ test examples. Поиск кнопки с помощью метода getByRole │ -├───┼────────────────────────────────────────────────────────┤ -│ 2 │ test examples. Поиск элемента на главной странице │ -├───┼────────────────────────────────────────────────────────┤ -│ 3 │ test examples. Поиск элемента по атрибуту │ -├───┼────────────────────────────────────────────────────────┤ -│ 4 │ test examples. Поиск элемента по data-testid │ -├───┼────────────────────────────────────────────────────────┤ -│ 5 │ test examples. Поиск элемента по id на главной стр. │ -├───┼────────────────────────────────────────────────────────┤ -│ 6 │ test examples. Поиск элемента по тексту │ -├───┼────────────────────────────────────────────────────────┤ -│ 7 │ test examples. Поиск элемента по типу атрибута │ -└───┴────────────────────────────────────────────────────────┘ - - │ - ▼ CHUNKS_COUNT=3 - -┌──────────┬──────────┬──────────┐ -│ Чанк 0 │ Чанк 1 │ Чанк 2 │ -├──────────┼──────────┼──────────┤ -│ тест 1 │ тест 4 │ тест 6 │ -│ тест 2 │ тест 5 │ тест 7 │ -│ тест 3 │ │ │ -└──────────┴──────────┴──────────┘ +всетесты (после сортировки по fullTitle): ┌───┬────────────────────────────────────────────────────────┐ + │ 1 │ test examples. Поиск кнопки с помощью метода getByRole │ + ├───┼────────────────────────────────────────────────────────┤ │ 2 │ test examples. Поиск + элемента на главной странице │ ├───┼────────────────────────────────────────────────────────┤ │ + 3 │ test examples. Поиск элемента по атрибуту │ + ├───┼────────────────────────────────────────────────────────┤ │ 4 │ test examples. Поиск + элемента по data-testid │ ├───┼────────────────────────────────────────────────────────┤ │ 5 │ + test examples. Поиск элемента по id на главной стр. │ + ├───┼────────────────────────────────────────────────────────┤ │ 6 │ test examples. Поиск + элемента по тексту │ ├───┼────────────────────────────────────────────────────────┤ │ 7 │ test + examples. Поиск элемента по типу атрибута │ + └───┴────────────────────────────────────────────────────────┘ │ ▼ CHUNKS_COUNT=3 + ┌──────────┬──────────┬──────────┐ │ Чанк 0 │ Чанк 1 │ Чанк 2 │ + ├──────────┼──────────┼──────────┤ │ тест 1 │ тест 4 │ тест 6 │ │ тест 2 │ тест 5 │ тест 7 │ │ + тест 3 │ │ │ └──────────┴──────────┴──────────┘; ``` :::tip Примечание @@ -349,12 +340,11 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane ## Рекомендуемые настройки и их расчет -| Параметр | Значение | Объяснение | -|---------------------|-------------------------------------------------------|-------------------------------------------------------------------------------------------------------------| -| `workers` | 8 | Рекомендованное значение — 8, но не больше количества ядер CPU | -| `sessionsPerBrowser`| min(слоты_грида_для_браузера, доступная_RAM / RAM_одного_браузера) | Реальное ограничение — ресурсы грида (слоты и RAM) | -| `testsPerSession` | min(тесты_до_деградации_браузера, тесты_за_время_жизни_сессии_грида) | Сессию нельзя переиспользовать бесконечно — браузер деградирует. Если грид принудительно закрывает сессию по времени, нужно вписаться в этот лимит. Параметр не влияет на параллельность, но влияет на стабильность прогона. | - +| Параметр | Значение | Объяснение | +| -------------------- | -------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `workers` | 8 | Рекомендованное значение — 8, но не больше количества ядер CPU | +| `sessionsPerBrowser` | min(слоты*грида*для*браузера, доступная_RAM / RAM*одного_браузера) | Реальное ограничение — ресурсы грида (слоты и RAM) | +| `testsPerSession` | min(тесты*до*деградации*браузера, тесты*за*время*жизни*сессии*грида) | Сессию нельзя переиспользовать бесконечно — браузер деградирует. Если грид принудительно закрывает сессию по времени, нужно вписаться в этот лимит. Параметр не влияет на параллельность, но влияет на стабильность прогона. | #### Пример @@ -380,16 +370,3 @@ browsers: { } } ``` - - - - - - - - - - - - - From c98a6c52c47067eb20340dfe74a2521c37c1d3da Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 6 Apr 2026 12:20:51 +0300 Subject: [PATCH 04/14] docs: character-fix --- .../current/basic-guides/parallelism.mdx | 44 ++++++++++++------- 1 file changed, 29 insertions(+), 15 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index 37d4074..1624bcc 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -317,21 +317,35 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane #### Как плагин делит тесты ```css -всетесты (после сортировки по fullTitle): ┌───┬────────────────────────────────────────────────────────┐ - │ 1 │ test examples. Поиск кнопки с помощью метода getByRole │ - ├───┼────────────────────────────────────────────────────────┤ │ 2 │ test examples. Поиск - элемента на главной странице │ ├───┼────────────────────────────────────────────────────────┤ │ - 3 │ test examples. Поиск элемента по атрибуту │ - ├───┼────────────────────────────────────────────────────────┤ │ 4 │ test examples. Поиск - элемента по data-testid │ ├───┼────────────────────────────────────────────────────────┤ │ 5 │ - test examples. Поиск элемента по id на главной стр. │ - ├───┼────────────────────────────────────────────────────────┤ │ 6 │ test examples. Поиск - элемента по тексту │ ├───┼────────────────────────────────────────────────────────┤ │ 7 │ test - examples. Поиск элемента по типу атрибута │ - └───┴────────────────────────────────────────────────────────┘ │ ▼ CHUNKS_COUNT=3 - ┌──────────┬──────────┬──────────┐ │ Чанк 0 │ Чанк 1 │ Чанк 2 │ - ├──────────┼──────────┼──────────┤ │ тест 1 │ тест 4 │ тест 6 │ │ тест 2 │ тест 5 │ тест 7 │ │ - тест 3 │ │ │ └──────────┴──────────┴──────────┘; +все тесты (после сортировки по fullTitle): + +┌───┬────────────────────────────────────────────────────────┐ +│ 1 │ test examples. Поиск кнопки с помощью метода getByRole │ +├───┼────────────────────────────────────────────────────────┤ +│ 2 │ test examples. Поиск элемента на главной странице │ +├───┼────────────────────────────────────────────────────────┤ +│ 3 │ test examples. Поиск элемента по атрибуту │ +├───┼────────────────────────────────────────────────────────┤ +│ 4 │ test examples. Поиск элемента по data-testid │ +├───┼────────────────────────────────────────────────────────┤ +│ 5 │ test examples. Поиск элемента по id на главной стр. │ +├───┼────────────────────────────────────────────────────────┤ +│ 6 │ test examples. Поиск элемента по тексту │ +├───┼────────────────────────────────────────────────────────┤ +│ 7 │ test examples. Поиск элемента по типу атрибута │ +└───┴────────────────────────────────────────────────────────┘ + + │ + ▼ CHUNKS_COUNT=3 + +┌──────────┬──────────┬──────────┐ +│ Чанк 0 │ Чанк 1 │ Чанк 2 │ +├──────────┼──────────┼──────────┤ +│ тест 1 │ тест 4 │ тест 6 │ +│ тест 2 │ тест 5 │ тест 7 │ +│ тест 3 │ │ │ +└──────────┴──────────┴──────────┘ + ``` :::tip Примечание From 4468c114fb1793150804cbbcfd4d048212225a32 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 6 Apr 2026 12:26:45 +0300 Subject: [PATCH 05/14] docs: character-fix --- .../current/basic-guides/parallelism.mdx | 24 ++----------------- 1 file changed, 2 insertions(+), 22 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index 1624bcc..ef0d6f6 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -316,28 +316,9 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane #### Как плагин делит тесты -```css -все тесты (после сортировки по fullTitle): - -┌───┬────────────────────────────────────────────────────────┐ -│ 1 │ test examples. Поиск кнопки с помощью метода getByRole │ -├───┼────────────────────────────────────────────────────────┤ -│ 2 │ test examples. Поиск элемента на главной странице │ -├───┼────────────────────────────────────────────────────────┤ -│ 3 │ test examples. Поиск элемента по атрибуту │ -├───┼────────────────────────────────────────────────────────┤ -│ 4 │ test examples. Поиск элемента по data-testid │ -├───┼────────────────────────────────────────────────────────┤ -│ 5 │ test examples. Поиск элемента по id на главной стр. │ -├───┼────────────────────────────────────────────────────────┤ -│ 6 │ test examples. Поиск элемента по тексту │ -├───┼────────────────────────────────────────────────────────┤ -│ 7 │ test examples. Поиск элемента по типу атрибута │ -└───┴────────────────────────────────────────────────────────┘ - - │ - ▼ CHUNKS_COUNT=3 +После сортировки по `fullTitle` набор тестов делится на 3 чанка: +```css ┌──────────┬──────────┬──────────┐ │ Чанк 0 │ Чанк 1 │ Чанк 2 │ ├──────────┼──────────┼──────────┤ @@ -345,7 +326,6 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane │ тест 2 │ тест 5 │ тест 7 │ │ тест 3 │ │ │ └──────────┴──────────┴──────────┘ - ``` :::tip Примечание From c0370dc5ce264554741adf6d8b6475557aef2822 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 6 Apr 2026 13:32:26 +0300 Subject: [PATCH 06/14] docs: settings-fix --- .../current/basic-guides/parallelism.mdx | 28 +++++++++---------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index ef0d6f6..ca279f4 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -334,11 +334,10 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane ## Рекомендуемые настройки и их расчет -| Параметр | Значение | Объяснение | -| -------------------- | -------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `workers` | 8 | Рекомендованное значение — 8, но не больше количества ядер CPU | -| `sessionsPerBrowser` | min(слоты*грида*для*браузера, доступная_RAM / RAM*одного_браузера) | Реальное ограничение — ресурсы грида (слоты и RAM) | -| `testsPerSession` | min(тесты*до*деградации*браузера, тесты*за*время*жизни*сессии*грида) | Сессию нельзя переиспользовать бесконечно — браузер деградирует. Если грид принудительно закрывает сессию по времени, нужно вписаться в этот лимит. Параметр не влияет на параллельность, но влияет на стабильность прогона. | +| Параметр | Значение | Объяснение | +| -------------------- | -------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `workers` | 8 | Рекомендованное значение — 8, но не больше количества ядер CPU. | +| `sessionsPerBrowser` | — | Количество сессий подбирается исходя из доступных ресурсов. При этом важно учитывать и возможности, например, вашего dev‑сервера, который раздаёт страницы для тестирования. Например, вы можете поднять 100 браузеров, но ваш сервер не будет успевать отдавать статику каждому браузеру. В итоге при большей параллельности вы получите замедление выполнения тестов. | #### Пример @@ -351,16 +350,17 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane // Деградация браузера: после 100 тестов system: { - workers: 8 // min(8, 16) -}, + workers: 8 // min(8, 16) +; +} +, browsers: { - chrome: { - sessionsPerBrowser: 16, // min(20, 8000/500) - testsPerSession: 20 // min(100, 600/30) - }, + chrome: { + sessionsperbrowser: 16; + } + , firefox: { - sessionsPerBrowser: 10, // min(10, 8000/300=26) - testsPerSession: 20 // min(100, 600/30) - } + sessionsperbrowser: 10; + } } ``` From 9e6ef78d15a2ecebb54c310d29eeeb1b2ab42ed0 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 6 Apr 2026 14:30:40 +0300 Subject: [PATCH 07/14] docs: sessions-fix --- .../current/basic-guides/parallelism.mdx | 53 +++++++++---------- 1 file changed, 25 insertions(+), 28 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index ca279f4..270d947 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -163,7 +163,25 @@ describe("test examples", () => { #### Как работает параллелизм в данном примере -Когда воркер получает тесты для Chrome, он открывает до 5 окон браузера одновременно. Каждое окно — это отдельная независимая сессия со своим `sessionId`. Для Firefox логика та же, но одновременно работают только 2 окна. +Когда воркер получает тесты для Chrome, он открывает до 5 окон браузера одновременно. Каждое окно — это отдельная независимая сессия со своим `sessionId`: + +```bash +Тест 1 → сессия chrome:abc123 → открывается окно Chrome #1 +Тест 2 → сессия chrome:def456 → открывается окно Chrome #2 +Тест 3 → сессия chrome:ghi789 → открывается окно Chrome #3 +Тест 4 → сессия chrome:jkl012 → открывается окно Chrome #4 +Тест 5 → сессия chrome:mno345 → открывается окно Chrome #5 +``` + +Логика та же, но одновременно работают только 2 окна Firefox. Это ограничение задано через `sessionsPerBrowser`: + +```bash +Тест 1 → сессия firefox:fb59f7 → открывается окно Firefox #1 +Тест 2 → сессия firefox:660ee0 → открывается окно Firefox #2 +Тест 3 → ждёт в очереди... + как только тест 1 завершился → сессия fb59f7 освободилась +Тест 3 → сессия firefox:fb59f7 → то же окно Firefox #1, новый тест +``` :::warning Важно `workers` управляет количеством `Node.js`-процессов, а `sessionsPerBrowser` — количеством одновременных браузерных сессий внутри каждого воркера. При workers: 1 все 7 сессий управляются одним процессом. @@ -334,33 +352,12 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane ## Рекомендуемые настройки и их расчет -| Параметр | Значение | Объяснение | -| -------------------- | -------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `workers` | 8 | Рекомендованное значение — 8, но не больше количества ядер CPU. | -| `sessionsPerBrowser` | — | Количество сессий подбирается исходя из доступных ресурсов. При этом важно учитывать и возможности, например, вашего dev‑сервера, который раздаёт страницы для тестирования. Например, вы можете поднять 100 браузеров, но ваш сервер не будет успевать отдавать статику каждому браузеру. В итоге при большей параллельности вы получите замедление выполнения тестов. | +#### workers -#### Пример +Рекомендуемым значение — `8`. Любое другое не должно превышать количество ядер CPU. -```css -// CPU: 16 ядер -// Грид: Chrome 20 слотов, Firefox 10 слотов -// RAM грида: 8GB, Chrome ~500MB, Firefox ~300MB -// Грид убивает сессию через 10 минут -// Средний тест: 30 секунд -// Деградация браузера: после 100 тестов +#### sessionsPerBrowser -system: { - workers: 8 // min(8, 16) -; -} -, -browsers: { - chrome: { - sessionsperbrowser: 16; - } - , - firefox: { - sessionsperbrowser: 10; - } -} -``` +При локальном запуске значение не превышает `5`. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. + +#### Рассчет чанков From f96dad948d0a98493cb41178a2fa0575d0108752 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Tue, 7 Apr 2026 09:29:01 +0300 Subject: [PATCH 08/14] docs: character-fix --- .../current/basic-guides/parallelism.mdx | 39 +++++++++++-------- 1 file changed, 22 insertions(+), 17 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index 270d947..3e96a97 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -4,7 +4,7 @@ Параллельность в Testplane — это возможность одновременно выполнять несколько тестовых сценариев в разных браузерных сессиях, чтобы сократить общее время прогона тестов. -#### sessionsPerBrowser +### sessionsPerBrowser В конфигурационном файле объявляются типы браузеров в поле `browsers`. Для каждого типа браузера независимо настраивается, сколько экземпляров может работать одновременно: @@ -24,7 +24,7 @@ export default { Параметр `sessionsPerBrowser` является ключевым в рамках управления параллельностью. Он определяет, сколько браузеров одного типа Testplane запустит одновременно. По умолчанию значение: `1`. -#### Воркеры +### Воркеры Параметр `workers` определяет, сколько дочерних процессов-воркеров будет запущено. Архитектурно это выглядит так: @@ -37,21 +37,13 @@ export default { `workers` и `sessionsPerBrowser` — независимые ограничения. Увеличение числа воркеров не увеличивает реальную параллельность, если `sessionsPerBrowser` остается прежним. ::: -#### testsPerSession +### testsPerSession Параметр `testsPerSession` отвечает за то, сколько тестов можно запускать последовательно в одной сессии браузера. Параметр ограничивает переиспользование сессии, чтобы не допустить падения тестов из-за деградации браузера, и не имеет отношения к параллельному запуску тестов. -#### Пример +### Как это работает -В рамках примера исполнять тесты будет один воркер: - -```typescript -system: { - workers: 1, - }, -``` - -Параметру sessionsPerBrowser присвоены значения `5`: +В рамках примера параметру `sessionsPerBrowser` присвоены значения `5`: ```typescript chrome: { @@ -79,6 +71,14 @@ firefox: { } ``` +Значение параметра `workers`: + +```typescript +system: { + workers: 1, + }, +``` + Далее тесты: ```typescript @@ -184,14 +184,14 @@ describe("test examples", () => { ``` :::warning Важно -`workers` управляет количеством `Node.js`-процессов, а `sessionsPerBrowser` — количеством одновременных браузерных сессий внутри каждого воркера. При workers: 1 все 7 сессий управляются одним процессом. +`workers` управляет количеством `Node.js`-процессов, а `sessionsPerBrowser` — количеством одновременных браузерных сессий внутри каждого воркера. При `workers`: `1` все 7 сессий управляются одним процессом. ::: ## Шардирование При наличии тысяч тестов время одного запуска может быть неприемлемо большим даже при максимальном параллелизме. В таких случаях используют шардирование — разбивку всего набора тестов на несколько независимых частей (чанков), которые запускаются параллельно на разных машинах или в разных `CI`-джобах. -#### Плагин testplane-chunks +### Плагин testplane-chunks Плагин `@testplane/chunks` позволяет распараллелить запуск тестов на нескольких серверах, тем самым ускорив процесс. Однако сам плагин не занимается какой-либо оркестрацией, распараллеливанием запуска или слиянием получившихся отдельных отчетов в один итоговый отчет. @@ -227,7 +227,7 @@ module.exports = { | `count` | `Number` | `1` | Количество порций (чанков), на которые нужно разбить набор тестов | | `run` | `Number` | `1` | Номер чанка, тесты из которого нужно запустить | -#### Как разбить запуск тестов +### Как разбить запуск тестов В качестве примера будет использован следующий набор тестов: @@ -350,6 +350,11 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane Главная идея чанков: если `workers` распределяет тесты внутри одного процесса, то чанки делят тесты между несколькими независимыми процессами — например, на разных `CI`-агентах или на одной машине через `concurrently`. ::: +#### Как объединить отчеты чанков + +Чтобы объединить несколько отчетов в один, используйте команду `merge-reports` + + ## Рекомендуемые настройки и их расчет #### workers @@ -360,4 +365,4 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane При локальном запуске значение не превышает `5`. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. -#### Рассчет чанков +#### Расчет чанков From d47f5ce85961b02d50f83f8c870acd951dae506f Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Tue, 7 Apr 2026 09:31:23 +0300 Subject: [PATCH 09/14] docs: character-fix --- .../current/basic-guides/parallelism.mdx | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index 3e96a97..e4f95ab 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -39,7 +39,7 @@ export default { ### testsPerSession -Параметр `testsPerSession` отвечает за то, сколько тестов можно запускать последовательно в одной сессии браузера. Параметр ограничивает переиспользование сессии, чтобы не допустить падения тестов из-за деградации браузера, и не имеет отношения к параллельному запуску тестов. +Параметр `testsPerSession` отвечает за то, сколько тестов можно запускать последовательно в одной сессии браузера. Он ограничивает переиспользование сессии, чтобы не допустить падения тестов из-за деградации браузера, и не имеет отношения к параллельному запуску тестов. ### Как это работает @@ -52,7 +52,6 @@ chrome: { browserName: "chrome" }, sessionsPerBrowser: 5, // 5 параллельных сессий Chrome - testsPerSession: 3, waitTimeout: 10000, } ``` @@ -66,7 +65,6 @@ firefox: { browserName: "firefox" }, sessionsPerBrowser: 2, // 2 параллельные сессии Firefox - testsPerSession: 3, waitTimeout: 10000, } ``` @@ -354,7 +352,6 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane Чтобы объединить несколько отчетов в один, используйте команду `merge-reports` - ## Рекомендуемые настройки и их расчет #### workers From 80ec6b9514288f076a151c64d5b2c904138395d5 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Tue, 7 Apr 2026 09:38:06 +0300 Subject: [PATCH 10/14] docs: reports-add --- .../current/basic-guides/parallelism.mdx | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index e4f95ab..daacc89 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -330,7 +330,7 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=1 npx testplane CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane ``` -#### Как плагин делит тесты +### Как плагин делит тесты После сортировки по `fullTitle` набор тестов делится на 3 чанка: @@ -348,13 +348,19 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane Главная идея чанков: если `workers` распределяет тесты внутри одного процесса, то чанки делят тесты между несколькими независимыми процессами — например, на разных `CI`-агентах или на одной машине через `concurrently`. ::: -#### Как объединить отчеты чанков +### Как объединить отчеты -Чтобы объединить несколько отчетов в один, используйте команду `merge-reports` +Чтобы объединить несколько отчетов в один, используйте команду `merge-reports`. Она принимает пути к директориям с отчетами, файлам баз данных или к файлам `databaseUrls.json`, после чего создает новый html-отчет в папке назначения с данными из всех переданных отчетов. + +Пример использования: + +```bash +npx html-reporter merge-reports report-dir/ path-to-database.db path-to-databaseUrls.json -d dest-report -h foo=bar +``` ## Рекомендуемые настройки и их расчет -#### workers +#### Воркеры Рекомендуемым значение — `8`. Любое другое не должно превышать количество ядер CPU. From 7cb70b5b3b02f0e73444e8128efd86016e41a937 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Tue, 7 Apr 2026 11:25:25 +0300 Subject: [PATCH 11/14] docs: chunks-fix --- .../current/basic-guides/parallelism.mdx | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index daacc89..de6fc9e 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -161,7 +161,7 @@ describe("test examples", () => { #### Как работает параллелизм в данном примере -Когда воркер получает тесты для Chrome, он открывает до 5 окон браузера одновременно. Каждое окно — это отдельная независимая сессия со своим `sessionId`: +Для Chrome открывается до 5 окон браузера одновременно. Каждое из них — это отдельная независимая сессия со своим `sessionId`: ```bash Тест 1 → сессия chrome:abc123 → открывается окно Chrome #1 @@ -171,7 +171,7 @@ describe("test examples", () => { Тест 5 → сессия chrome:mno345 → открывается окно Chrome #5 ``` -Логика та же, но одновременно работают только 2 окна Firefox. Это ограничение задано через `sessionsPerBrowser`: +Для Firefox логика та же, но одновременно работают только 2 окна. Это ограничение задано через `sessionsPerBrowser`: ```bash Тест 1 → сессия firefox:fb59f7 → открывается окно Firefox #1 @@ -369,3 +369,4 @@ npx html-reporter merge-reports report-dir/ path-to-database.db path-to-database При локальном запуске значение не превышает `5`. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. #### Расчет чанков + From 7817151f95fcc84455b63c93e86c6bcd61638a4e Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Tue, 7 Apr 2026 11:29:02 +0300 Subject: [PATCH 12/14] docs: character-fix --- .../current/basic-guides/parallelism.mdx | 1 - 1 file changed, 1 deletion(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index de6fc9e..53db17e 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -369,4 +369,3 @@ npx html-reporter merge-reports report-dir/ path-to-database.db path-to-database При локальном запуске значение не превышает `5`. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. #### Расчет чанков - From d1eaf7f4564b2659a73b3d842b2a6d6c70dea328 Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Thu, 9 Apr 2026 08:06:32 +0300 Subject: [PATCH 13/14] docs: chunks-fix --- .../current/basic-guides/parallelism.mdx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index 53db17e..f6b7856 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -368,4 +368,4 @@ npx html-reporter merge-reports report-dir/ path-to-database.db path-to-database При локальном запуске значение не превышает `5`. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. -#### Расчет чанков +#### Количество чанков From 4695057e3a6ac90085abe8bd9ba28d4642afb29a Mon Sep 17 00:00:00 2001 From: Nikolaengel Date: Mon, 13 Apr 2026 10:48:35 +0300 Subject: [PATCH 14/14] docs: chunks-fix --- .../current/basic-guides/parallelism.mdx | 131 ++++++++---------- 1 file changed, 56 insertions(+), 75 deletions(-) diff --git a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx index f6b7856..e75a078 100644 --- a/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx +++ b/i18n/ru/docusaurus-plugin-content-docs/current/basic-guides/parallelism.mdx @@ -43,7 +43,7 @@ export default { ### Как это работает -В рамках примера параметру `sessionsPerBrowser` присвоены значения `5`: +В рамках примера параметру `sessionsPerBrowser` присвоены значения 5: ```typescript chrome: { @@ -56,7 +56,7 @@ chrome: { } ``` -и `2`: +и 2: ```typescript firefox: { @@ -229,92 +229,64 @@ module.exports = { В качестве примера будет использован следующий набор тестов: -```typescript -describe("test examples", () => { - it("Поиск элемента по data-testid", async ({ browser }) => { - // Открываем страницу и ждем ее загрузки - await browser.openAndWait("https://testplane.io/"); - - // Ищем элемент по атрибуту data-testid - const element = await browser.$('[data-testid="main-content"]'); - - // Проверяем существование элемента в DOM - const isExisting = await element.isExisting(); - console.log("Элемент с data-testid существует:", isExisting); - }); - - it("Поиск элемента на главной странице", async ({ browser }) => { - await browser.openAndWait("https://testplane.io/"); - - // Ищем элемент по классу "navbar" - const navbar = await browser.$(".navbar"); - - // Проверяем, отображается ли элемент на странице - const isDisplayed = await navbar.isDisplayed(); - console.log("Навбар отображается:", isDisplayed); - }); - - it("Поиск элемента по id на главной странице", async ({ browser }) => { - await browser.openAndWait("https://testplane.io/"); +```text +project/ +├── .testplane.conf.js +├── package.json +└── tests/ + ├── registration.testplane.js # 500 тестов + ├── payment.testplane.js # 500 тестов + └── auth.testplane.js # 500 тестов +``` - // Ищем элемент по id "__docusaurus" - const main = await browser.$("#__docusaurus"); +```javascript +//registration.testplane.js - // Проверяем, отображается ли элемент на странице - const isDisplayed = await main.isDisplayed(); - console.log("Элемент отображается:", isDisplayed); - }); +describe("Регистрация", () => { + it("тест 1 - пустой email показывает ошибку", async ({ browser }) => {}); + it("тест 2 - невалидный формат email", async ({ browser }) => {}); + it("тест 3 - пустой пароль показывает ошибку", async ({ browser }) => {}); - it("Поиск элемента по типу атрибута", async ({ browser }) => { - await browser.openAndWait("https://testplane.io/"); + // ... - // Ищем кнопку по атрибуту type="button" - // Формат селектора: element[type="value"] - const button = await browser.$('button[type="button"]'); - - // Проверяем существование элемента в DOM - const isExisting = await button.isExisting(); - console.log("Кнопка существует:", isExisting); - }); - - it("Поиск элемента по тексту", async ({ browser }) => { - await browser.openAndWait("https://testplane.io/"); + // тест 500 +}); +``` - // Ищем элемент по тексту внутри него - const link = await browser.$('//a[text()="Docs"]'); +```javascript +//payment.testplane.js - // Проверяем существование элемента в DOM - const isExisting = await link.isExisting(); - console.log("Элемент с текстом существует:", isExisting); - }); +describe("Оплата", () => { + it("тест 1 - пустой номер карты показывает ошибку", async ({ browser }) => {}); + it("тест 2 - невалидный номер карты", async ({ browser }) => {}); + it("тест 3 - истёкший срок действия карты", async ({ browser }) => {}); - it("Поиск элемента по атрибуту", async ({ browser }) => { - await browser.openAndWait("https://testplane.io/"); + // ... - // Ищем элемент по атрибуту type - const button = await browser.$('//button[@type="button"]'); + // тест 500 +}); +``` - // Проверяем существование элемента в DOM - const isExisting = await button.isExisting(); - console.log("Элемент с атрибутом существует:", isExisting); - }); +```javascript +//auth.testplane.js - it("Поиск кнопки с помощью метода getByRole", async ({ browser }) => { - await browser.url("https://testplane.io/"); +describe("Авторизация", () => { + it("тест 1 - пустой email показывает ошибку", async ({ browser }) => {}); + it("тест 2 - пустой пароль показывает ошибку", async ({ browser }) => {}); + it("тест 3 - неверный пароль показывает ошибку", async ({ browser }) => {}); - const button = await browser.getByRole("button", { name: "Get started" }); + // ... - await button.click(); - }); + // тест 500 }); ``` Резделение тестов на чанки: ```css -Чанк 0 → тесты 1, 2, 3 (≈ первая треть) -Чанк 1 → тесты 4, 5 (≈ вторая треть) -Чанк 2 → тесты 6, 7 (≈ третья треть) +Чанк 0 → тесты 1, 2, ..., 500 (≈ первая треть) +Чанк 1 → тесты 1, 2, ..., 500 (≈ вторая треть) +Чанк 2 → тесты 1, 2, ..., 500 (≈ третья треть) ``` Запуск каждого чанка отдельно через терминал: @@ -338,9 +310,10 @@ CHUNKS_COUNT=3 CHUNKS_CURRENT=2 npx testplane ┌──────────┬──────────┬──────────┐ │ Чанк 0 │ Чанк 1 │ Чанк 2 │ ├──────────┼──────────┼──────────┤ -│ тест 1 │ тест 4 │ тест 6 │ -│ тест 2 │ тест 5 │ тест 7 │ -│ тест 3 │ │ │ +│ тест 1 │ тест 1 │ тест 1 │ +│ тест 2 │ тест 2 │ тест 2 │ +│ ... │ ... │ ... │ +│ тест 500 │ тест 500 │ тест 500 │ └──────────┴──────────┴──────────┘ ``` @@ -362,10 +335,18 @@ npx html-reporter merge-reports report-dir/ path-to-database.db path-to-database #### Воркеры -Рекомендуемым значение — `8`. Любое другое не должно превышать количество ядер CPU. +Рекомендуемое значение — 8. Любое другое не должно превышать количество ядер CPU. #### sessionsPerBrowser -При локальном запуске значение не превышает `5`. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. +При локальном запуске значение не превышает 5. В ином случает примерное значение можно вычислить путем деления доступных ресурсов на требуемое для конкретного браузера. При расчете помните о затратах на запуск самих тестов. #### Количество чанков + +При расчете количества чанков необходимо отталкиваться от: + +- количества доступных браузеров +- оверхеда на создание чанка +- желаемого общего времени прогона + +Рекомендация — не меньше 500 тестов на чанк.