SA
SDET QA

Writing Your First Playwright Test

Learn how to write and run your first automated test with Playwright.

Creating a Test File

Create a new file named example.spec.ts in the tests directory:

typescript
import { test, expect } from '@playwright/test';

test('has title', async ({ page }) => {
  await page.goto('https://playwright.dev/');

  // Expect a title "to contain" a substring.
  await expect(page).toHaveTitle(/Playwright/);
});

test('get started link', async ({ page }) => {
  await page.goto('https://playwright.dev/');

  // Click the get started link.
  await page.getByRole('link', { name: 'Get started' }).click();

  // Expects page to have a heading with the name of Installation.
  await expect(page.getByRole('heading', { name: 'Installation' })).toBeVisible();
});

Understanding the Test Structure

Import Statements

Every test file starts by importing the necessary functions:

typescript
import { test, expect } from '@playwright/test';
  • test: Function to define a test case
  • expect: Function to make assertions

Test Function

Each test is defined using the test function:

typescript
test('test name', async ({ page }) => {
  // Test code here
});
  • First parameter: Test description (string)
  • Second parameter: Async function that receives fixtures like page
  • page: Browser page object to interact with

Common Actions

Navigation

typescript
// Navigate to a URL
await page.goto('https://example.com');

// Navigate back
await page.goBack();

// Navigate forward
await page.goForward();

// Reload page
await page.reload();

Interacting with Elements

typescript
// Click on an element
await page.getByRole('button', { name: 'Submit' }).click();

// Type text into an input
await page.getByLabel('Email').fill('user@example.com');

// Select from dropdown
await page.getByLabel('Country').selectOption('USA');

// Check a checkbox
await page.getByLabel('Accept terms').check();

Assertions

typescript
// Check if element is visible
await expect(page.getByText('Welcome')).toBeVisible();

// Check element text content
await expect(page.getByRole('heading')).toHaveText('Dashboard');

// Check page title
await expect(page).toHaveTitle('My App');

// Check URL
await expect(page).toHaveURL(/dashboard/);

// Check element count
await expect(page.getByRole('listitem')).toHaveCount(5);

Running Tests

Run All Tests

bash
npx playwright test

Run Specific Test File

bash
npx playwright test example.spec.ts

Run in UI Mode

bash
npx playwright test --ui

Run in Debug Mode

bash
npx playwright test --debug

Complete Example

Here's a complete test that demonstrates a login flow:

typescript
import { test, expect } from '@playwright/test';

test.describe('Login Flow', () => {
  test('successful login', async ({ page }) => {
    // Navigate to login page
    await page.goto('https://example.com/login');

    // Fill in credentials
    await page.getByLabel('Email').fill('user@example.com');
    await page.getByLabel('Password').fill('securePassword123');

    // Click login button
    await page.getByRole('button', { name: 'Login' }).click();

    // Verify successful login
    await expect(page).toHaveURL(/dashboard/);
    await expect(page.getByText('Welcome back')).toBeVisible();
  });

  test('login with invalid credentials', async ({ page }) => {
    await page.goto('https://example.com/login');

    await page.getByLabel('Email').fill('wrong@example.com');
    await page.getByLabel('Password').fill('wrongPassword');
    await page.getByRole('button', { name: 'Login' }).click();

    // Verify error message
    await expect(page.getByText('Invalid credentials')).toBeVisible();
    await expect(page).toHaveURL(/login/);
  });
});

Best Practices

  • Use descriptive test names that explain what is being tested
  • Keep tests independent - each test should work on its own
  • Use test.describe() to group related tests
  • Prefer user-facing selectors like getByRole() and getByLabel()
  • Always wait for elements before interacting with them
  • Use auto-waiting - Playwright waits automatically for elements to be ready