Playwright Test Reporting for the Whole Team

playwright test reporting

Playwright can show which test failed and provide a trace to investigate it. To make that evidence useful after CI finishes, you must choose an output, preserve it, and merge results from any shards. We'll set that up first, then ask what the report tells someone outside engineering. Check our full guide on the playwright test reporting.

How tu Run Playwright Reporting - Quick Look

Playwright includes built-in reporters for different reporting needs. The HTML reporter turns a single test run into an interactive report: you can see the status of each test, inspect a failing test, and open attachments such as screenshots or traces when those were captured. The Playwright HTML report helps you investigate a run, including a large test suite, but it reflects only the tests that actually ran.

To try it, run npx playwright test --reporter=html. For a repeatable reporting setup, configure one or multiple reporters in playwright.config.ts. The list, line, and dot reporters show progress and failures in the terminal; JUnit provides XML for CI systems, while JSON gives integrations structured test results. These options cover most reporting needs. Create a custom reporter or add third-party reporting when a specific reader or integration needs more.

Pick the reporter by who will use its output

Playwright Test can use several reporters at once. Choose each by its reader: a developer scanning CI, someone inspecting a browser report, a system ingesting results, or a job merging shards. See the playwright dashboard. built-in reporter options.

Reporter Use it when Output and caveat of the test execution.
list, line, dot A person needs progress and failures in a terminal or CI log. Terminal output; dot is concise for CI.
html Someone needs to inspect a completed run and its attached evidence, including screenshots of the test results. A report folder, playwright-report/ by default; you still need to upload or host it.
json Your own integration processes detailed results. Structured JSON; choose a file path rather than dumping it into CI logs.
junit A CI or test-management system expects JUnit XML. XML for ingestion; it is not a substitute for a navigable failure report.
github GitHub Actions file annotations help developers find failures in their test automation. Annotations, not report hosting. Playwright warns that a matrix can multiply annotations.
blob Jobs run different shards of the same suite. Archive to collect and merge later; it is not the reader-facing report for the test suite.
perfetto You need to inspect the timeline of workers, tests, hooks, and steps. Trace Event JSON for the Perfetto UI or chrome://tracing for test execution insights.; distinct from a Playwright test trace.
null You deliberately do not want reporter output. No standard report output; uncommon for a team that needs a CI handoff.

Trace Viewer opens diagnostic traces; it is not a reporter. Allure is a separate Playwright integration. You can also write a custom reporter for a specific integration.

For a single CI job, start with a short log and an HTML report:

// playwright.config.ts
import { defineConfig } from '@playwright/test';

export default defineConfig({
  reporter: [
    ['dot'],
    ['html', { open: 'never' }],
  ],
  use: {
    screenshot: 'only-on-failure',
    trace: 'retain-on-failure',
  },
});

The HTML reporter writes playwright-report/ by default. open: 'never' Prevents a browser from opening after failures on a CI runner during test execution. The screenshot and trace settings keep evidence from failed attempts. If a CI consumer requires JUnit, add ['junit', { outputFile: 'test-results/results.xml' }] to the reporter array. A local npx playwright show-report opens the latest HTML report. Reporter configuration and Recording options for the playwright reporter. are documented separately.

When Allure earns the extra setup

Playwright's HTML report is a good default for inspecting one run. Allure Playwright can add structured metadata, hierarchies, attachments, and links to Playwright traces. It also adds steps: install allure-playwright and the Allure report tool, configure the reporter, generate HTML from allure-results/, and publish allure-report/. For example, its reporter entry is part of the test automation process. ['allure-playwright']; after tests run, allure generate produces the HTML report.

Avoid mixing old allure-results/ from previous runs unless that is intentional: Allure says new result files are added to an existing directory. Add Allure when that structure answers a real reader need. You still have to publish the report and assign someone to interpret it.

Make the failure report useful to the person investigating it

A red test is a starting point for investigation, not a diagnosis. The trace policy determines which attempt you can inspect later. Playwright's recording options distinguish these common cases:

Setting What you keep
trace: 'retain-on-failure' A trace from each failed attempt, including an initial failure; passing attempts are discarded.
trace: 'on-first-retry' with retries enabled A trace from the first retry. It does not preserve the initial failed attempt.

The configuration above uses retain-on-failure and screenshot: 'only-on-failure'. If you prefer Playwright's common CI recommendation, set retries: 1 and trace: 'on-first-retry'. Choose deliberately: when an intermittent problem vanishes on retry, a trace of the successful retry may not reveal why the first attempt failed. See the Trace Viewer guide for opening a trace from the HTML report.

For a failed checkout check, inspect the screenshot and trace. Was the expected button absent? Did a request fail? Was the test using stale data? Record the evidence and what remains uncertain before describing the failure as a product bug in the list reporter. If the result changes between runs, investigate common causes of flaky tests before treating a retry as proof that checkout works.

Publish the HTML report after CI finishes, including failed runs

Generating a report with the playwright HTML format. playwright-report/ on an ephemeral runner is not enough for the next person to read it. Upload the folder as an artifact. Here is a minimal GitHub.com Actions workflow for an existing Playwright Test project with its dependencies in package.json for the test automation setup.:

# .github/workflows/playwright.yml
name: Playwright tests
on:
  push:
  pull_request:

jobs:
  test:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v6
      - uses: actions/setup-node@v6
        with:
          node-version: lts/*
      - run: npm ci
      - run: npx playwright install --with-deps
      - run: npx playwright test
      - uses: actions/upload-artifact@v5
        if: ${{ !cancelled() }}
        with:
          name: playwright-report
          path: playwright-report/
          retention-days: 14

The upload condition lets the report upload after a test failure, unless the job was cancelled. The job still fails; the workflow does not need continue-on-error. Find the artifact on the workflow run and download it for inspection. Playwright can serve the extracted folder with npx playwright show-report path/to/playwright-report. This follows Playwright's test execution guidelines. GitHub Actions CI example and HTML reporter instructions.

An artifact is available under your repository's access rules and retention settings; GitHub documents how to download workflow artifacts and set their retention period. It is not automatically a public, stable web page. If Product or Support cannot access GitHub Actions, choose a trusted hosting or sharing path, decide who may see failure evidence, and publish the report there. Check the handoff with someone who did not write the workflow: can they find the latest report for the release and open the failure detail? If the upload is missing, inspect the report path and step condition first; if it has expired or access is denied, adjust retention or access rather than changing reporters.

Merge all shard results before you report a release result

A separate HTML report from shard 1 cannot tell you whether tests on shard 2 passed. Use blob on each shard, collect the archives, and run merge-reports once. The example below is a two-shard version of Playwright's documented GitHub.com Actions pattern. The --reporter=blob flag applies to the test command; your local playwright.config.ts may keep its HTML and terminal reporters.

# .github/workflows/playwright-sharded.yml
name: Playwright tests (sharded)
on:
  push:
  pull_request:

jobs:
  test:
    runs-on: ubuntu-latest
    strategy:
      fail-fast: false
      matrix:
        shard: [1, 2]
    steps:
      - uses: actions/checkout@v6
      - uses: actions/setup-node@v6
        with:
          node-version: lts/*
      - run: npm ci
      - run: npx playwright install --with-deps
      - run: npx playwright test --shard=${{ matrix.shard }}/2 --reporter=blob
      - uses: actions/upload-artifact@v4
        if: ${{ !cancelled() }}
        with:
          name: blob-report-${{ matrix.shard }}
          path: blob-report/
          retention-days: 1

  merge:
    if: ${{ !cancelled() }}
    needs: [test]
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v6
      - uses: actions/setup-node@v6
        with:
          node-version: lts/*
      - run: npm ci
      - uses: actions/download-artifact@v5
        with:
          path: all-blob-reports
          pattern: blob-report-*
          merge-multiple: true
      - name: Check that both shard reports arrived
        run: test "$(find all-blob-reports -maxdepth 1 -type f -name '*.zip' | wc -l)" -eq 2
      - run: npx playwright merge-reports --reporter=html ./all-blob-reports
      - uses: actions/upload-artifact@v4
        with:
          name: html-report-attempt-${{ github.run_attempt }}
          path: playwright-report/
          retention-days: 14

Each shard uploads a uniquely named artifact. The merge job downloads both archives, checks the file count, builds playwright-report/, and uploads the combined HTML. fail-fast: false keeps the other shard running when one fails. The merge job is set to run after failed shards if the workflow is not cancelled. Playwright's sharding example uses the same overall path.

The count check only confirms that two ZIP files arrived. Before calling this a complete release result, verify their shard identities, build, environment, project list, and run attempt. A cancelled job or a missing artifact leaves an incomplete result, even if another shard passed. When merging across different operating systems, Playwright calls for an explicit merge configuration; for distinct environments, it recommends tagging the runs.

The report is ready at 2am. Who reads it?

You have configured reporters, captured evidence, published HTML, and merged the shards. Who opens the result at 2am? When the Head of Support asks whether the release passed, who explains the answer?

The HTML report tells you what happened in a test run. It cannot say whether that run covered this release's critical workflows, whether a failed test is a product defect, or who has authority to proceed. A GitHub artifact link may also be inaccessible to the person asking. Those are ownership and handoff decisions the team has to make.

Take an illustrative 2am run: two shards completed, a checkout test failed, and two tests were skipped. The engineer on call opens the merged report and trace. They record what is known, what remains uncertain, and whether checkout is affected. The release owner decides whether the release should be held, retested, or allowed to proceed. The Head of Support gets that decision and its customer-facing implication in plain language. The outcome stays open until someone has investigated and decided.

Give the result a release owner and a Support update

Attach a short handoff to the report so the next reader does not have to reconstruct the decision:

Release / build: [ID or commit] · Environment: [staging/production] · Run: [timestamp and attempt] Scope: [browser/project, critical journeys, and what was not tested] · Shards: [expected/received] Result: [passed / failed / flaky / skipped] · Evidence: [merged report and relevant trace links] Triage: [known cause, impact, unresolved questions, investigation owner] Decision: [hold / proceed / retest / pending], made by [owner] at [time] Support update: [one sentence describing customer impact or the fact that impact is still being assessed]

This is a team practice, not a Playwright feature or a guarantee that a release is safe for the playwright reporter. “Pending” matters: a green subset and a missing shard do not add up to a passed release.

If engineers already own Playwright tests, CI, artifact access, and the release message, keep that setup and make the handoff explicit. If QA or Product should own a separate set of recurring Chromium web checks, BugBug lets them create and edit those tests visually and review run history without building their own cloud runner and report-hosting workflow. Cloud runs, schedules, alerts, and summary PDF reports start on CORE test suite., which allows three users; detailed screenshot PDFs and JSON/CSV exports are on BUSINESS. Keep each scenario authoritative in one tool; BugBug does not decide whether to release, and it does not test Firefox, Safari, or native apps.

Before the next run, assign a triage owner and a release decision owner. At 2am, one knows who investigates. When the Head of Support asks, the other can say which release was checked, what remains uncertain, who decided, and what happens next in the test suite. No reporter configuration assigns those responsibilities.

Happy (automated) testing!

Your next release. Properly tested.

Join 1,200+ QA teams that automated their
regression coverage with BugBug.

Start testing. It's free.
  • Free plan
  • No credit card
  • 14-days trial

Author

Dominik Szahidewicz

Software Quality Evangelist

Dominik Szahidewicz is a Software Quality Evangelist specialising in quality assurance, test automation, and modern software testing practices. He creates practical, research-driven content that helps QA professionals, developers, and product teams improve test coverage, automate repetitive testing, and release more reliable web applications.

Drawing on his experience in technical writing, data analysis, and application consulting, Dominik translates complex testing concepts into clear, actionable guidance. His areas of interest include end-to-end testing, low-code test automation, regression testing, and the use of AI in software quality assurance.

Reviewer

Bartek Krzyzanowski

QA & Test Automation Expert

Bartek Krzyżanowski is a QA and test automation expert at BugBug with 15 years of experience in software testing and quality assurance. Throughout his career, he has worked with software teams on improving testing processes, designing effective test strategies, and building maintainable automated test coverage.

His expertise spans manual and automated testing, end-to-end and regression testing, test automation strategy, and the practical challenges teams face when maintaining reliable test suites as products evolve. He focuses particularly on approaches that help QA and engineering teams increase coverage while keeping test automation understandable, maintainable, and useful in everyday development workflows.

At BugBug, Bartek contributes his testing expertise to educational content for QA professionals, developers, and product teams. As an author on the BugBug blog, he writes about software testing methodologies, test automation tools, industry practices, and practical techniques teams can use to improve software quality.

His writing combines extensive industry experience with a pragmatic perspective on modern test automation, helping teams understand not only which tools and techniques are available, but how to apply them effectively in real-world software development.