Harness-engineering test-playwright-setup

Test Playwright Setup

install
source · Clone the upstream repo
git clone https://github.com/Intense-Visions/harness-engineering
Claude Code · Install into ~/.claude/skills/
T=$(mktemp -d) && git clone --depth=1 https://github.com/Intense-Visions/harness-engineering "$T" && mkdir -p ~/.claude/skills && cp -r "$T/agents/skills/codex/test-playwright-setup" ~/.claude/skills/intense-visions-harness-engineering-test-playwright-setup-086376 && rm -rf "$T"
manifest: agents/skills/codex/test-playwright-setup/SKILL.md
source content

Test Playwright Setup

Configure Playwright test runner with fixtures, reporters, and browser contexts

When to Use

  • Setting up Playwright for end-to-end testing in a web project
  • Configuring multiple browsers, reporters, and test environments
  • Setting up authentication state sharing across tests
  • Configuring CI-specific Playwright settings

Instructions

  1. Install Playwright:
npm init playwright@latest
# or
npm install -D @playwright/test
npx playwright install
  1. Configure
    playwright.config.ts
    :
import { defineConfig, devices } from '@playwright/test';

export default defineConfig({
  testDir: './e2e',
  fullyParallel: true,
  forbidOnly: !!process.env.CI,
  retries: process.env.CI ? 2 : 0,
  workers: process.env.CI ? 1 : undefined,
  reporter: process.env.CI ? 'github' : 'html',

  use: {
    baseURL: 'http://localhost:3000',
    trace: 'on-first-retry',
    screenshot: 'only-on-failure',
  },

  projects: [
    { name: 'chromium', use: { ...devices['Desktop Chrome'] } },
    { name: 'firefox', use: { ...devices['Desktop Firefox'] } },
    { name: 'webkit', use: { ...devices['Desktop Safari'] } },
    { name: 'mobile-chrome', use: { ...devices['Pixel 5'] } },
  ],

  webServer: {
    command: 'npm run dev',
    url: 'http://localhost:3000',
    reuseExistingServer: !process.env.CI,
    timeout: 120_000,
  },
});
  1. Auto-start the dev server with

    webServer
    config — Playwright starts and waits for the server automatically.

  2. Set up authenticated state with global setup:

// e2e/auth.setup.ts
import { test as setup, expect } from '@playwright/test';

setup('authenticate', async ({ page }) => {
  await page.goto('/login');
  await page.getByLabel('Email').fill('admin@test.com');
  await page.getByLabel('Password').fill('password');
  await page.getByRole('button', { name: 'Log in' }).click();
  await expect(page.getByText('Dashboard')).toBeVisible();

  await page.context().storageState({ path: 'e2e/.auth/user.json' });
});
// playwright.config.ts — add setup project
projects: [
  { name: 'setup', testMatch: /.*\.setup\.ts/ },
  {
    name: 'chromium',
    use: {
      ...devices['Desktop Chrome'],
      storageState: 'e2e/.auth/user.json',
    },
    dependencies: ['setup'],
  },
],
  1. Custom fixtures for reusable test helpers:
// e2e/fixtures.ts
import { test as base } from '@playwright/test';

type Fixtures = {
  todoPage: TodoPage;
};

export const test = base.extend<Fixtures>({
  todoPage: async ({ page }, use) => {
    const todoPage = new TodoPage(page);
    await todoPage.goto();
    await use(todoPage);
  },
});

export { expect } from '@playwright/test';
  1. Configure reporters:
reporter: [
  ['html', { open: 'never' }],
  ['junit', { outputFile: 'test-results/junit.xml' }],
  ['list'],
],
  1. Trace viewer for debugging failed tests:
use: {
  trace: 'on-first-retry', // Records trace on first retry of failed tests
},

View with:

npx playwright show-trace test-results/trace.zip

  1. Add to
    .gitignore
    :
test-results/
playwright-report/
e2e/.auth/

Details

Playwright runs tests across real browsers (Chromium, Firefox, WebKit) with full automation capabilities. Each test gets a fresh browser context by default, providing natural test isolation.

Browser contexts: Each test runs in an isolated browser context (like an incognito window). Cookies, localStorage, and session state do not leak between tests. This is more isolated than sharing a single browser instance.

webServer
configuration: Playwright can start your dev/preview server automatically before running tests. Set
reuseExistingServer: true
for development (uses an already-running server) and
false
for CI (starts a fresh server).

Storage state: Authentication state (cookies, localStorage) can be saved and reused across tests. This avoids logging in for every test, significantly speeding up the suite.

Parallelism:

fullyParallel: true
runs tests in the same file in parallel. Each test gets its own worker process. Set
workers: 1
in CI if your app cannot handle concurrent users.

Trade-offs:

  • Multi-browser testing catches browser-specific bugs — but triples test execution time
  • webServer
    auto-start is convenient — but can mask server startup issues
  • Storage state sharing speeds up tests — but tests may fail if the auth state expires
  • Trace viewer is invaluable for debugging — but traces consume significant disk space

Source

https://playwright.dev/docs/intro

Process

  1. Read the instructions and examples in this document.
  2. Apply the patterns to your implementation, adapting to your specific context.
  3. Verify your implementation against the details and edge cases listed above.

Harness Integration

  • Type: knowledge — this skill is a reference document, not a procedural workflow.
  • No tools or state — consumed as context by other skills and agents.

Success Criteria

  • The patterns described in this document are applied correctly in the implementation.
  • Edge cases and anti-patterns listed in this document are avoided.