/** * Sprint 26: worker-scoped org fixture. * * Каждый Playwright worker = свой long-lived org. Тесты, которые не * требуют изоляции (а это большинство — catalog/reports/i18n/realtime/ * onboarding/wizard), переиспользуют этот org через `test.extend` * вместо вызова `OrgFactory.build()` per-test. * * Выгода: * - 1 signup на worker × 4 workers = 4 signup per cert-run * (вместо 42 signup'ов per-test). * - Меньше нагрузка на signup rate-limit (per-IP). * - Быстрее: фикстура переиспользуется, нет setup-overhead. * * Изоляция данных НЕ страдает: каждый test всё равно создаёт свои * сущности с уникальными именами (через `Date.now()` суффикс), и * `pageSize=N` ограничивает list-запросы — другие тесты в той же org * не мешают. * * Кому НЕ подходит: * - 06-multi-tenant.spec.ts — нужно ДВЕ свежие org per-test, иначе * тест становится бессмысленным (используем OrgFactory напрямую). * - 02-auth.spec.ts — тестирует сам signup, нужна fresh org. * - 09-onboarding-wizard.spec.ts — тестирует онбординг свежей org'и. * * Использование: * import { test } from '../lib/worker-org.js' * test('foo', async ({ workerOrg }) => { * const products = await request(Endpoints.products, { token: workerOrg.session.accessToken }) * ... * }) */ import { test as baseTest } from '@playwright/test' import { OrgFactory } from '../factories/OrgFactory.js' import type { BuiltOrg } from '../factories/OrgFactory.js' interface WorkerFixtures { workerOrg: BuiltOrg } export const test = baseTest.extend<{}, WorkerFixtures>({ workerOrg: [async ({}, use, workerInfo) => { // Одна org на весь worker. Имя содержит workerIndex чтобы // параллельные workers получали разные org'и (и поэтому // не конкурировали за уникальные суффиксы). const slug = `w${workerInfo.workerIndex}` const org = await OrgFactory.for(slug) .withProducts(3) // базовый каталог чтобы reports что-то видели .withCounterparties(1) .build() await use(org) // После всех тестов worker'a — org остаётся (cleanup делает // Hangfire-job `prune-quality-test-orgs`, см. [[sprint25_done]]). // Можно делать явный DELETE здесь, но это требует SuperAdmin-токена // и cascade-обвязки — пока не реализуем. }, { scope: 'worker' }], }) export { expect } from '@playwright/test'