- Published on
Playwright (5. díl) - Testování API - Vlastní APIRequestContext v Playwrightu
Úvod
Playwright nabízí dvě hlavní možnosti, jak pracovat s HTTP požadavky:
requestfixture – rychlá cesta k API testům, ideální pro samostatné testy- vlastní
APIRequestContext– pokročilejší řešení pro případy, kdy potřebujeme sdílet stav (např. autentizaci) mezi více testy
Co je request fixture
request fixture je součástí test runneru Playwrightu. V každém testu je automaticky vytvořena a po jeho dokončení uvolněna vlastní instance APIRequestContext. Každý test tak běží v čistém, izolovaném prostředí – nepřenášejí se mezi nimi cookies, tokeny ani jiný stav.
Kdy použít request fixture
- Jednoduché, izolované testy, např.:
- GET/POST požadavek, který nepotřebuje sdílet cookies nebo tokeny
- testy, které nepotřebují autentizaci nebo přihlašování
- ověření dostupnosti API endpointů
Příklad použití
import { test, expect } from '@playwright/test'
test('Should return welcome text', async ({ request }) => {
const response = await request.get('/hello')
expect(response.status()).toBe(200)
expect(await response.json()).toEqual({
message: 'Hello, API Testing!',
})
})
Co je vlastní APIRequestContext
Někdy potřebujete sdílet stav mezi více testy – např.:
- přihlásíte se do API a získáte JWT token (chcete opakovaně volat chráněné endpointy bez zbytečného přihlašování v každém testu)
- uložíte si cookies pro session
V takovém případě je vhodné vytvořit vlastní APIRequestContext, který bude sdílený napříč testy.
Jak vytvořit vlastní APIRequestContext
Využijeme request.newContext(), nastavíme základní URL, hlavičky (např. Authorization) a použijeme ho ve více testech.
import { test, expect, APIRequestContext } from '@playwright/test'
let apiContext: APIRequestContext
const BASE_URL = 'http://localhost:3000'
const validUser = {
email: `testuser_${Date.now()}@example.com`,
password: 'MyPassword',
}
const userData = { name: 'tmp', email: 'tmp@a.cz', age: '22', role: 'admin' }
test.beforeAll(async ({ playwright }) => {
// Vytvoření contextu s baseURL
apiContext = await playwright.request.newContext({
baseURL: BASE_URL,
})
// Registrace uživatele
const registrationResponse = await apiContext.post('/register', {
data: validUser,
})
// Přihlášení a získání tokenu
const loginResponse = await apiContext.post('/login', {
data: validUser,
})
const { token } = await loginResponse.json()
// Nastavení Authorization headeru pro všechny další požadavky
await apiContext.dispose() // uvolníme předchozí kontext
apiContext = await playwright.request.newContext({
baseURL: BASE_URL,
extraHTTPHeaders: {
Authorization: `Bearer ${token}`,
},
})
})
test.afterAll(async () => {
await apiContext.dispose()
})
test.only('POST /users', async () => {
const response = await apiContext.post('/users', {
data: userData,
})
expect(response.status()).toBe(201)
})
test('GET /users', async () => {
const response = await apiContext.get('/users')
expect(response.status()).toBe(200)
const body = await response.json()
expect(body.name).toEqual(userData.name)
})
Díky tomu nemusíme volat login v každém testu a všechny testy mají stejný sdílený stav.
Kdy použít vlastní APIRequestContext místo request fixture
- Potřebujeme autentizaci jen jednou a sdílet ji v dalších testech
- např. login přes API a následné volání chráněných endpointů
- Chceme ve více testech používat stejné hlavičky (Authorization, Content-Type)
- nemusíte je psát v každém testu zvlášť
- Sdílení cookies/session
- pokud API používá cookies, vlastní context je zachová mezi testy
- Chceme zrychlit testy
- přihlášení je jen jednou, místo opakovaného loginu v každém testu
Na co si dát pozor při práci s APIRequestContext
Uvolnění kontextu
Pokud nepoužijete dispose(), může docházet k plýtvání prostředků.
Sdílení stavu mezi paralelními testy
Playwright spouští testy paralelně v samostatných workerech. Jeden sdílený APIRequestContext pro všechny testy může způsobit konflikty. Každý worker běží izolovaně, takže mezi workery se stav nesdílí. Uvnitř jednoho workeru ale může běžet více testů, které sdílený APIRequestContext využijí. Proto by se měl sdílený APIRequestContext používat jen uvnitř workeru, ne globálně. V takovém případě je lepší použít samostatný APIRequestContext pro každý worker.
Zastaralé tokeny nebo session
Pokud běží testy dlouho, může se token stát neplatným. Je vhodné implementovat mechanismus obnovení.
Závislost testů na pořadí
Sdílený APIRequestContext může vést k tomu, že jeden test ovlivní jiný (např. pokud smaže data). Testy by měly být co nejvíce nezávislé.

