Playwright-Testisolierung und Browserkontext

Dieses Kapitel führt in den Mechanismus der Testisolierung von Playwright und das Konzept des Browser-Kontexts ein, das ein zentrales Design darstellt, um stabile und zuverlässige Tests zu gewährleisten.


Was ist Testisolierung

Testisolierung bedeutet, dass jeder Testfall in einervöllig unabhängigenUmgebung ausgeführt wird und sie sich nicht gegenseitig beeinflussen.

In Playwright erhält jeder Test automatisch einen unabhängigen `BrowserContext`Browser-Kontext(Browser-Kontext).


Was ist ein Browser-Kontext?

Ein Browser-Kontext entspricht einembrandneuen Browserprofil。

Das Erstellen eines Kontexts ist wie das Öffnen eines brandneuen Browserfensters, mit eigenem Cookie, localStorage und sessionStorage, aber mit extrem geringem Overhead (Millisekundenbereich).

KonzeptAnalogieBeschreibung
Browser (Browser-Instanz)Öffnet ein BrowserprogrammHoher Overhead; wird in der Regel nur einmal für den gesamten Testlauf erstellt
Browser-Kontext (Browserkontext)Ein unabhängiges Profil im BrowserGeringer Overhead; einer pro Test
Page (Tab)Ein Tab im BrowserÖffnet Seiten im Kontext

Die `page` in jedem Testpageundcontextist brandneu, sodass es sich nicht auf andere Tests auswirkt, wenn ein Test localStorage oder Cookie ändert.


Was der Kontext isoliert

Der folgende Inhalt ist zwischen den einzelnen Browser-Kontexten vollständig isoliert:

IsolationselementBeschreibung
CookiesJeder Kontext verfügt über einen unabhängigen Cookie-Speicher
localStorageLocal Storage ist vollständig isoliert
sessionStorageSession Storage ist vollständig isoliert
IndexedDBIsolierung der Browser-Datenbank
CacheHTTP-Cache-Isolierung

Beispiel

// Test A setzt ein Cookie
test('Test A', async ({ page }) => {
  await page.goto('https://www.example.com/');

  // Cookie setzen (wirkt nur im aktuellen Context)
  await page.context().addCookies([{
    name: 'example_session',
    value: 'abc123',
    domain: 'www.example.com',
    path: '/',
  }]);

  // Nachfolgende Operationen verwenden dieses Cookie
});

// Test B erhält einen brandneuen Context, ohne das von Test A gesetzte Cookie
test('Test B', async ({ page }) => {
  await page.goto('https://www.example.com/');

  // context().cookies() gibt ein leeres Array zurück
  const cookies = await page.context().cookies();
  console.log(cookies); // []
});

Verwendung der context-Fixture

Neben `page`page, kann die Testfunktion auch auf diecontext`context`-Fixture für Operationen auf Context-Ebene zugreifen.

Beispiel

test('Verwendung der context-Fixture', async ({ context, page }) => {
  // Berechtigungen auf Context-Ebene setzen
  await context.grantPermissions(['geolocation']);
  await context.setGeolocation({ latitude: 39.9, longitude: 116.4 });

  // Netzwerkverkehr auf Context-Ebene abfangen
  await context.route('**/*.{png,jpg,jpeg}', route => route.abort());

  // page befindet sich im selben Context und erbt die obigen Einstellungen
  await page.goto('https://www.example.com/');
});

Multi-Context-Szenarien

Wenn du mehrere unabhängige Benutzer im selben Test simulieren musst, kannst du Contexts manuell erstellen.

Beispiel

test('Zwei Benutzer arbeiten unabhängig voneinander', async ({ browser }) => {
  // Unabhängige Contexts für die beiden Benutzer erstellen
  const userAContext = await browser.newContext();
  const userBContext = await browser.newContext();

  // Die Seiten der beiden Benutzer sind vollständig isoliert
  const pageA = await userAContext.newPage();
  const pageB = await userBContext.newPage();

  await pageA.goto('https://www.example.com/login');
  await pageB.goto('https://www.example.com/login');

  // Benutzer A meldet sich an
  await pageA.getByLabel('Username').fill('user_a');
  await pageA.getByLabel('Password').fill('password_a');
  await pageA.getByRole('button', { name: 'Login' }).click();

  // Benutzer B meldet sich an (jeder hat eine unabhängige Cookie/Session, ohne sich gegenseitig zu beeinflussen)
  await pageB.getByLabel('Username').fill('user_b');
  await pageB.getByLabel('Password').fill('password_b');
  await pageB.getByRole('button', { name: 'Login' }).click();

  // Aufräumen
  await userAContext.close();
  await userBContext.close();
});

Vorteile der Testisolierung

1. Reproduzierbarkeit

Jeder Test startet vom gleichen Ausgangszustand und liefert konsistente Ergebnisse unabhängig von der Ausführungsreihenfolge.

2. Verhindert kaskadierende Fehler

Wenn Test A fehlschlägt, führt das nicht dazu, dass Test B fehlschlägt; jeder Test kann unabhängig debuggt werden.

3. Unterstützt parallele Ausführung

Da die Tests vollständig unabhängig sind, kann Playwright sie sicher über mehrere Worker hinweg parallel ausführen.

Die Testisolierung ist das Standardverhalten von Playwright; jedertest()`test` erhält automatisch einen unabhängigenpageundcontext`BrowserContext`, ohne dass eine zusätzliche Konfiguration erforderlich ist.

Andere Erweiterungen