Running Playwright locally is straightforward: your browsers, dependencies, application, and development environment are already available.
In GitHub Actions, the same test starts from a fresh CI runner. You need to install dependencies and browsers, prepare the application or target environment, run the tests, and preserve enough information to debug failures.
Leapwork Play simplifies this execution model. Instead of making GitHub Actions host the browser execution itself, an external CI pipeline can trigger a Play RunList through public API endpoints and check its status over HTTP. The Playwright execution remains in Play's cloud browser environment.
Why do Playwright tests fail in GitHub Actions?
Most failures after moving a working local test into CI are caused by differences in the execution setup.
Common problems include:
-
The test passes locally but fails in GitHub Actions.
-
Required browser dependencies are missing.
-
The Node.js version differs between local and CI.
-
The target environment is not ready when the tests start.
-
Tests share data that changes between runs.
-
Reports or traces are unavailable after a failure.
When a test works locally but fails in CI, check the workflow configuration, browser setup, environment, and test data before assuming the Playwright test itself is broken.
How do you run Playwright tests in GitHub Actions?
A typical GitHub Actions workflow should prepare the runner, install Playwright’s browser dependencies, and then run the test suite.
Use this order:
-
Check out the repository.
-
Set up Node.js.
-
Install project dependencies.
-
Install Playwright browsers and system dependencies.
-
Build, start, or deploy the application if needed.
-
Run the Playwright tests.
-
Upload or preserve test reports and traces.
Example workflow:
name: Playwright Tests
on:
push:
branches: [main]
pull_request:
branches: [main]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
- run: npm ci
- run: npx playwright install --with-deps
- run: npx playwright test
- uses: actions/upload-artifact@v4
if: always()
with:
name: playwright-report
path: playwright-report/
retention-days: 30
Tip: Add build, start, or deployment steps before npx playwright test if your application is not already running in CI.
How does Leapwork Play simplify CI execution?
With Leapwork Play, the external CI system does not need to host the Play browser execution. Instead, the workflow triggers a RunList through Play's public API, monitors the run status, and continues the pipeline based on the result.
CI flow: GitHub Actions → Trigger Play RunList → Play cloud browser executes tests → Check run status → Continue pipeline based on result.
Authentication: Supply the trigger secret using either X-Trigger-Secret: <secret> or Authorization: Bearer <secret>.
The external system coordinates the API calls and status checks instead of recreating Play's browser execution environment inside the CI runner.
Trigger a Play RunList from CI
The integration uses two parts of the trigger API workflow:
-
POST — trigger the RunList
Use the trigger endpoint to start the configured RunList.
-
GET — check run status
Use the returned run information to check the execution status and determine when the run has completed. Keep the trigger secret in your CI provider's secret storage rather than putting it directly into the workflow or repository.
How Play extends the Playwright CI workflow
|
With Playwright in GitHub Actions |
With Leapwork Play |
|---|---|
|
Configure the CI runner and browser dependencies |
Play provides the cloud browser execution environment |
|
Run the browser tests inside the GitHub Actions job |
Trigger the RunList and execute the tests in Play |
|
Maintain browser installation and runner setup |
CI only needs to integrate with the trigger API workflow |
|
Preserve CI artifacts for investigation |
Review execution results within the Play workflow |
|
Scale execution through CI jobs, matrices, or shards |
Use Play's managed execution layer |
Play complements your existing CI pipeline by moving Playwright browser execution into Play while allowing the pipeline to remain the external trigger.
What should stay in GitHub Actions?
Use GitHub Actions for CI/CD orchestration and let Play handle browser test execution:
-
Build and deploy your application.
-
Trigger the Play test run from GitHub Actions.
-
Wait for the Play result.
-
Continue the pipeline on success, or fail it if tests fail.
This keeps GitHub Actions focused on the delivery workflow while Play runs the browser tests. You avoid maintaining browser dependencies in every CI workflow, and the pipeline only needs to coordinate the test run.
Should you test localhost or a deployed environment?
In CI, the target application needs to be available before the browser test starts. If you test a deployed staging or preview environment, make sure deployment has completed before triggering the tests.
For example: Do not start the browser tests while the environment they depend on is still being deployed.
Best practices
-
Use Play's trigger API when you want CI to orchestrate the test while Play handles browser execution.
-
Store the trigger secret securely in your CI provider.
-
Make sure the target application is ready before triggering the RunList.
-
Keep CI orchestration separate from browser-test execution where appropriate.
-
Keep test data independent between concurrent executions.
-
Check the final RunList status before allowing the pipeline to continue.
-
When running Playwright directly in GitHub Actions, preserve reports and diagnostic artifacts after failures.
Troubleshooting
|
Problem |
What to check |
|---|---|
|
Test passes locally but fails in GitHub Actions |
Compare browser dependencies, Node.js version, environment, and test data |
|
Browser installation fails |
Check the Playwright browser installation and system dependencies |
|
Test starts before staging is ready |
Make the test execution wait for deployment/environment readiness |
|
Play RunList does not start |
Check the trigger endpoint, trigger secret, and request |
|
CI triggers Play but does not know when it finishes |
Use the status endpoint to check the run until it reaches its final state |
|
Concurrent runs interfere with each other |
Check shared accounts, sessions, and test data |
Frequently asked questions
Does GitHub Actions need Playwright installed separately from my project?
When running Playwright directly in GitHub Actions, install your project dependencies and the required Playwright browsers as part of the workflow.
With Play, browser execution happens in the Play environment instead of requiring the GitHub Actions runner to host that execution.
Why does a Playwright test pass locally but fail in GitHub Actions?
The local and CI environments may differ in browser dependencies, Node.js version, application availability, test data, or other execution conditions. Check those differences before changing the test.
Does GitHub Actions run the browser when using Leapwork Play?
Not in the workflow described here. GitHub Actions acts as the external trigger, while the RunList executes through Play's cloud browser environment.
How does CI authenticate when triggering Play?
The supplied workflow uses a trigger secret through either X-Trigger-Secret or Authorization: Bearer.
Can I use a CI system other than GitHub Actions?
The trigger mechanism is HTTP-based, so the supplied approach is not inherently tied to GitHub Actions. An external system capable of making the required authenticated API calls can coordinate the trigger and status requests.
How do I know whether the Play tests passed?
After triggering the RunList, use the status endpoint to check its execution state and use the final result in the surrounding CI workflow.
Is Play replacing GitHub Actions?
No. GitHub Actions can continue to orchestrate build and deployment while Play handles the Playwright browser execution. This keeps the two responsibilities separate.