Test Fixtures for Playwright Test

This page is not available in the language you requested. You have been redirected to the English version of the page.
Link to this page copied to clipboard

Using Axe Watcher for organizations that already use Playwright Test fixtures

Not for use with personal data

If your organization already uses Playwright Test fixtures in your test suites, you'll need to merge your existing fixtures with Axe Watcher's fixtures to enable accessibility testing. This guide walks you through the integration process.

Understanding the Challenge

Playwright Test allows you to create custom fixtures that extend the base test functionality. These fixtures might provide mock data, shared setup logic, or reusable test utilities. When you introduce Axe Watcher, which also uses fixtures for accessibility testing, you need to combine the two sets of fixtures using mergeTests to ensure they work together.

Without merging, your tests will fail because Playwright won't recognize your custom fixtures when using the Axe Watcher test configuration.

Basic Integration Steps

Step 1: Import Required Functions

Start by importing the necessary functions from Playwright Test and Axe Watcher:

import { test as base, mergeTests } from '@playwright/test'
import { playwrightTest } from '@axe-core/watcher/playwright-test'

The mergeTests() function is the key to combining your custom fixtures with Axe Watcher's fixtures.

Step 2: Create Your Custom Fixtures

Define your existing custom fixtures as you normally would. For example, if you have a mock user fixture for authentication testing:

class MockUser {
  #username = 'testuser'
  #password = 'SecurePassword123!'

  get username() {
    return this.#username
  }

  get password() {
    return this.#password
  }
}

const customFixtures = base.extend<{ mockUser: MockUser }>({
  mockUser: async ({}, use) => {
    await use(new MockUser())
  }
})

Step 3: Configure Axe Watcher

Set up your Axe Watcher configuration with your API credentials:

const ACCESSIBILITY_API_KEY = process.env.ACCESSIBILITY_API_KEY
const PROJECT_ID = process.env.PROJECT_ID

const { test: watcherTest, expect } = playwrightTest({
  axe: {
    apiKey: ACCESSIBILITY_API_KEY,
    projectId: PROJECT_ID
  },
})

Step 4: Merge the Fixtures

Use mergeTests to combine your custom fixtures with Axe Watcher's fixtures:

const test = mergeTests(customFixtures, watcherTest)

export { test, expect }

Complete Example

Here's a comprehensive example showing the entire integration:

import { test as base, mergeTests } from '@playwright/test'
import { playwrightTest } from '@axe-core/watcher/playwright-test'

// Environment variables for Axe Developer Hub
const ACCESSIBILITY_API_KEY = process.env.ACCESSIBILITY_API_KEY
const PROJECT_ID = process.env.PROJECT_ID

// Custom fixture: Mock user for authentication
class MockUser {
  #username = 'testuser'
  #password = 'SecurePassword123!'

  get username() {
    return this.#username
  }

  get password() {
    return this.#password
  }
}

// Define custom fixtures
const customFixtures = base.extend<{ mockUser: MockUser }>({
  mockUser: async ({}, use) => {
    await use(new MockUser())
  }
})

// Configure Axe Watcher
const { test: watcherTest, expect } = playwrightTest({
  axe: {
    apiKey: ACCESSIBILITY_API_KEY,
    projectId: PROJECT_ID
  },
  headless: false
})

// Merge fixtures
const test = mergeTests(customFixtures, watcherTest)

// Export merged test and expect
export { test, expect }

Using the Merged Fixtures in Tests

Once you've set up the merged fixtures, use them in your test files by importing from your fixtures file:

import { test, expect } from './fixtures'

test('should login with accessible form', async ({ page, mockUser }) => {
  await page.goto('https://example.com/login')
  
  // Use your custom fixture
  await page.fill('#username', mockUser.username)
  await page.fill('#password', mockUser.password)
  await page.click('#login-button')
  
  // Verify successful login
  await expect(page.locator('.welcome-message')).toBeVisible()
  
  // Accessibility testing happens automatically
})

Multiple Custom Fixtures

If you have multiple custom fixtures, you can merge them all together:

// Define multiple fixture sets
const userFixtures = base.extend<{ mockUser: MockUser }>({
  mockUser: async ({}, use) => {
    await use(new MockUser())
  }
})

const apiFixtures = base.extend<{ apiClient: ApiClient }>({
  apiClient: async ({}, use) => {
    await use(new ApiClient())
  }
})

// Configure Axe Watcher
const { test: watcherTest, expect } = playwrightTest({
  axe: {
    apiKey: ACCESSIBILITY_API_KEY,
    projectId: PROJECT_ID
  }
})

// Merge all fixtures
const test = mergeTests(userFixtures, apiFixtures, watcherTest)

export { test, expect }

Advanced Configuration Options

You can customize Axe Watcher's behavior while maintaining your custom fixtures:

const { test: watcherTest, expect } = playwrightTest({
  axe: {
    apiKey: ACCESSIBILITY_API_KEY,
    projectId: PROJECT_ID,
    autoAnalyze: true,
    configurationOverrides: {
      accessibilityStandard: 'WCAG 2.2 AA',
      bestPractices: true,
      experimentalRules: false
    }
  },
  args: ['--headless=new']
})

Troubleshooting

Fixture Not Available Error

If you see an error like Property 'mockUser' does not exist on type, ensure you've:

  1. Properly merged the fixtures using mergeTests
  2. Imported test from your merged fixtures file, not directly from @playwright/test
  3. Exported both test and expect from your fixtures file

Type Safety Issues

For TypeScript projects, ensure your custom fixture types are properly defined:

type CustomFixtures = {
  mockUser: MockUser
  apiClient: ApiClient
}

const customFixtures = base.extend<CustomFixtures>({
  mockUser: async ({}, use) => {
    await use(new MockUser())
  },
  apiClient: async ({}, use) => {
    await use(new ApiClient())
  }
})

See Also