Skip to content

Latest commit

 

History

History
163 lines (113 loc) · 12.8 KB

README.md

File metadata and controls

163 lines (113 loc) · 12.8 KB

Useful Playwright Fixtures

Description

A proper description of what a Playwright fixture is can be found on the official docs. For the purpose of this code demo, you can think of fixtures as a way to provide, or even automatically apply, behaviour to your tests.

The fixtures used in this code demo are all declared on the app-fixtures.ts file.

How to build, run the app, run tests and view the test results

Important

Required dependencies:

  • Node. Tested working with v20.10.0. If you need to have different versions of node installed it's recommended that you use Node Version Manager to install and swap between node versions.
  • npm@latest: package manager used on the demos. Tested working on 10.2.5.
  • VS Code is recommended as a code editor but you can use whatever you prefer.
  1. Clone the repo.
  2. Using your favorite shell go to /demos/fixtures.
  3. Install the required npm packages with:
    npm install
    
  4. Install the playwright browsers with:
    npx playwright install
    
  5. Run the tests with:
    npm test
    
    This will start the app and run the playwright tests against it.
  6. After running the tests you can view test results with:
    npm run test:show-report
    
  7. If you just want to run the app execute the command:
    npm start
    
    Once the command finishes the app should open in your default browser at http://127.0.0.1:4200/.

Note

When you run the tests in this fixtures demo with npm test you will have 8 tests that pass, 1 test that is skipped and 9 that fail. This is intentional as the tests are meant to show the fixtures in action. For more information see the comments at example.spec.ts.

Playwright configuration

The majority of the content of the playwright.config.ts file is what you get by default after adding Playwright to your project with npm init playwright@latest.

The main changes are:

  1. Declared a few variables at the start that are reused throughout the playwright configuration.
  2. Updated the reporter array. In addition to using the default html reporter, we've added the built-in list reporter.
  3. Defined a baseURL so that we can use relative URLs when doing page navigations on the tests.
  4. Configured the webServer block to run the Angular app locally so that the tests can be executed against it. If you're not testing an Angular app that's fine, you just need to adjust the webServer.command so that it launches your app and set the webServer.url to the url your app will be running at. For more information see the webServer docs.

Note

The _isRunningOnCI variable used on the playwright.config.ts changes the value of some options when running tests on CI. To set the _isRunningOnCI variable to true you must set the environment variable CI to true before running the tests. For more information regarding using Playwright on a CI environment see Playwright docs on Continuous Integration.

Furthermore, we have created:

Note

You don't have to create the playwright.cli-options.ts or the playwright.env-vars.ts file. You can have all of this on the playwright.config.ts. Code structure is up to you.

Note

Depending on your playwright.config.ts, make sure you update your .gitignore to exclude any directory used by test results, report results, etc. Scroll to the end of this demo's .gitignore to see an example.

Fixtures

Time/Date emulation

Playwright let's you emulate a real device such as a mobile phone or tablet. This means you can control things like a Locale & Timezone, however if you need to control the value of the Time/Date then there's nothing built-in to Playwright to help you do that.

Setting the value of Time/Date is very useful when you need to take a screenshot or assert on values that contain Time/Date information. It's also important if your app has time based actions such as "press a button and after X amount of time some action occurs". To be able to implement reliable tests on these scenarios you need to be able to control Time/Date.

The setDate fixture is an automatic fixture that shows how you can use the Page.addInitScript function to control the values returned by JavaScript's Date constructor and the Date.now function. See set-date.ts file.

The setDate test at example.spec.ts shows this fixture at work by allowing reliable asserts on a text field that is based on the current Date and on the screenshot.

Note

This fixture is based on this comment from the microsoft/playwright [Feature] Time/Date emulation via e.g. a clock() primitive #6347 GitHub issue.

The issue contains other solutions such as the one from this comment which uses Sinon.JS fake timers. The Sinon.JS fake timers solution not only allows you to set the current Date but it also allows you to control the flow of time. This type of solution is useful if you need to do a test where you need to perform an action and then wait X amount of time before doing something else. Using the Sinon.JS fake timers would let you code tests for that behaviour in a reliable way.

Tip

You can also consider using the mask option of the toHaveScreenshot to take a screenshot and ignore the part that has dynamic data such as a Time/Date.

Capture Console Messages

The consoleMessages fixture shows how you can use the Page.on('console') event to capture all Console Messages. See console-messages.ts.

The console-messages.ts has a filter function named isExcluded so that you can filter out Console Messages you don't care about. For instance when running an Angular 17 app with Vite (which this demo is), the Vite dev server will produce some Console Messages we want to ignore.

The consoleMessages and failOnUnexpectedConsoleMessages test at example.spec.ts shows how you can use the fixture to assert that the app is producing an expected console message.

Fail tests upon unexpected console messages

The failOnUnexpectedConsoleMessages fixture adds an assert to all the tests to check for unexpected Console Messages. If your app produces some Console Messages then you should exclude them using the isAllowed function available on the fixture. See fail-on-unexpected-console-messages.ts.

This fixture is great to catch left over debug/temp Console Messages.

The failOnUnexpectedConsoleMessages test at example.spec.ts shows how this fixture fails a test if an unexpect console message is produced.

Note

This fixture makes use of the composable property of fixtures and builds upon the consoleMessages fixture.

Capture page errors

The uncaughtExceptions fixture shows how you can use the Page.on('pageerror') event to capture all uncaught exceptions that happen within the page. See page-errors.ts.

The uncaughtExceptions test at example.spec.ts shows how this fixture fails a test if an unexpect exception occurs.

Fail tests on page errors

The failOnUncaughtExceptions fixture adds an assert to all tests to make sure they don't produce any uncaught exceptions. See fail-on-page-errors.ts.

The failOnUncaughtExceptions test at example.spec.ts shows this fixture making a test fail because it produces an uncaught exception.

Note

This fixture makes use of the composable property of fixtures and builds upon the uncaughtExceptions fixture.

Project name

The projectName fixture allows you to control behaviour of your tests based on the Playwright project name. For instance, you might want to skip a test or provide different values to a test depending on the project name.

The projectName test at example.spec.ts shows an example usage of this fixture.

This fixture is useful because it uses the PlaywrightProjectName enum to define the valid names for a Project. With this enum you have a type safe way to filter on Project names.

Custom annotations

Playwright supports custom annotations. Annotations are key/value pairs accessible via test.info().annotations. Many reporters support annotations.

The annotations fixture shows how you can add custom annotations to your tests, which are visible on the html test report:

custom-annotations

See annotations.ts. All tests will have these custom annotations.