/playwright-boilerplate

A NodeJS/Typescript Playwright project utilizing the Page Object Model. Includes accessibility tests, an Actions workflow, and various means of reporting.

Primary LanguageTypeScript

Playwright Test View site - GH Pages View site - GH Pages GitHub Repo stars

Playwright Page Object Model Boilerplate

This is an example of a Playwright project that uses the page object model design pattern. In general, Playwright best practices are followed where possible and the configuration is largely the default configuration generated when you install Playwright.

The site under test is Acme Store, a demo ecommerce store built with Next.js, Vercel, and Shopify.

Previously, the site under test was Automation Exercise. This site was quite outdated and had random pop-up ads that would appear, which made it difficult to test. The Acme Store is far more mordern and a much better candidate for a Playwright boilerplate project in 2023.

The pageObjects Directory

pageObjects
    ├── base.page.ts
    ├── base.pageComponent.ts
    ├── pageFixture.ts
    ├── components
        └── *.pageComponent.ts
    └── pages
        └── *.page.ts

This directory contains our base page class, base page component class, and all page object classes that extend those base classes.

  • base.page.ts
    • The base page class is intended to include Locators and functionality that is shared across all pages. It takes a Page instance as a constructor parameter.
  • base.pageComponent.ts
    • I like to use page components to logically separate page elements that are common across multiple pages from pages themselves. This class takes a Locator parameter in addition to a Page instance. Typically, page components are instantiated within other page classes, and not within the spec file itself.
    • You can see page components being instantiated in our home.page.ts file. These components can then be used in our tests in an easy-to-read format. See here.
  • pageFixture.ts

Accessibility Testing

I'm using the @axe-core/playwright for accessibility testing in axe.spec.ts. These are failing miserably on the test site I'm using so they are currently skipped with the skip() annotation.

Formatting

I'm using Prettier for formatting. I've added an npm script to make excution simpler, although it's currently not tied to any automation. I just make sure to run this before checking in code.

Github Actions

I've made some changes to the default Github Actions workflow that Playwright generates.

Test Execution

Test execution takes place in a job called playwright_test.

Reporting

I'm using multiple methods of reporting here. Reporting tasks are done in a separate job that executes after all test shard execution has completed.

Github Pages

  • Test results from sharded tests are combined into a single report and uploaded to Github Pages. See the badge at the top of this README for a link to the latest test report. I've added a step to automatically comment on the pull request with a link to the report.

dorny/test-reporter

Tesults

  • Tesults is a third-party reporting service that has basic free accounts that are perfect for a boilerplate project like this (and I've also used the paid tiers in a professional setting with great success). They have a playwright-reporter npm package that works with very little configuration, but I took it a step further with a quick and dirty js script to automatically create targets in Tesults for new pull requests/branches. This script is used in our Actions file to set up a target for the current branch. Results are then posted to that target via the Tesults playwright-reporter. Similar to the Github Pages report, I've added a step to automatically comment on the pull request with a link to the report. You can see the dashboard for this project here at https://www.tesults.com/angelo-loria/acme-store-demo.

Upon a pull request being closed, the Tesults branch target is deleted via the same script with another Github Actions job. This is done to keep the number of targets in Tesults to a minimum on my free account.

Lighthouse

I'm using the Google Lighthouse NPM package for performance and additional accessibility testing. The test setup and execution is a bit unique tests so I've separated them into their own spec file, they use a unique config file, and they are uploaded to Tesults separately from the other tests. See the directory here. I've added a specific script in the package.json file for executing these tests with their specific config file and running the tesults-lighthouse.js script afterwards. The script uses the Tesults npm package to upload the results to Tesults to a specific target that's set up with the results interpretation feature to display the individual Lighthouse scores for each page. It looks pretty slick. Tesults is hosting the Lighthouse HTML reports and they're uploaded as artifacts to Github Actions as well. Here's what one of those reports looks like.

Visual Testing

The visual tests are done using Playwright's toHaveScreenshot(). I did have to come up with a way to regenerate them via Actions, which you can see in the workflows directory. This workflow uses Playwright's --update-snapshots CLI command to generate the new snapshots and then commits them to the branch via stefanzweifel/git-auto-commit-action.