A comprehensive Playwright test reporter that automatically sends test results to the QAStudio.dev test management platform.
- β Automatic test result reporting to QAStudio.dev
- β Auto-creation of test runs
- β Map Playwright tests to QAStudio.dev test cases
- β Upload screenshots and videos for failed tests
- β Capture error context (code snippets, error location, test steps)
- β Include console output for enhanced debugging
- β Batch API requests for optimal performance
- β Retry handling (only reports final results)
- β Detailed error handling with fallback mode
- β Rich metadata extraction from test annotations
- β TypeScript support with full type definitions
npm install --save-dev @qastudio-dev/playwrightOr with yarn:
yarn add -D @qastudio-dev/playwrightCreate a .env file in your project root:
QA_STUDIO_API_URL=https://qastudio.dev/api
QA_STUDIO_API_KEY=your-api-key-here
QA_STUDIO_PROJECT_ID=your-project-id-hereAdd the reporter to your playwright.config.ts:
import { defineConfig } from '@playwright/test';
export default defineConfig({
reporter: [
['list'], // Keep default reporters
[
'@qastudio-dev/playwright',
{
apiUrl: process.env.QA_STUDIO_API_URL!,
apiKey: process.env.QA_STUDIO_API_KEY!,
projectId: process.env.QA_STUDIO_PROJECT_ID!,
environment: process.env.CI ? 'CI' : 'local',
createTestRun: true,
},
],
],
});npx playwright testTest results will be automatically sent to QAStudio.dev!
| Option | Type | Required | Default | Description |
|---|---|---|---|---|
apiUrl |
string | β | - | QAStudio.dev API base URL |
apiKey |
string | β | - | API key for authentication |
projectId |
string | β | - | QAStudio.dev project ID |
testRunId |
string | β | - | Existing test run ID (auto-created if not provided) |
environment |
string | β | 'default' |
Environment name (e.g., 'CI', 'staging') |
createTestRun |
boolean | β | true |
Auto-create test run if testRunId not provided |
testRunName |
string | β | Auto-generated | Name for new test runs |
testRunDescription |
string | β | - | Description for new test runs |
milestoneId |
string | β | - | Associate test run with milestone |
verbose |
boolean | β | false |
Enable detailed logging |
batchSize |
number | β | 10 |
Batch size for sending results |
uploadScreenshots |
boolean | β | true |
Upload screenshots for failed tests |
uploadVideos |
boolean | β | true |
Upload videos for failed tests |
includeErrorSnippet |
boolean | β | true |
Include code snippet showing where error occurred |
includeErrorLocation |
boolean | β | true |
Include precise error location (file, line, column) |
includeTestSteps |
boolean | β | true |
Include test execution steps for failed tests |
includeConsoleOutput |
boolean | β | false |
Include console output (stdout/stderr) |
maxRetries |
number | β | 3 |
Max retry attempts for API requests |
timeout |
number | β | 30000 |
API request timeout (ms) |
silent |
boolean | β | true |
Don't fail tests if API is unavailable |
Test case mapping is optional! The reporter will automatically send all test results to QAStudio.dev, even without explicit test case IDs. Tests are automatically mapped based on the hierarchy of test names and groups from your Playwright test structure (using describe blocks and test titles). This maintains the same organization in QAStudio.dev as in your test files.
However, if you want to link specific Playwright tests to existing QAStudio.dev test cases for better organization and traceability, there are two ways to do so:
import { test, expect } from '@playwright/test';
test('user can login', async ({ page }) => {
test.info().annotations.push({
type: 'testCaseId',
description: 'QA-123', // QAStudio.dev test case ID
});
// Your test code...
});test('[QA-123] user can login', async ({ page }) => {
// Your test code...
});test('user can login', async ({ page }) => {
// Your test code...
// This test will still be reported to QAStudio.dev automatically!
});Enhance your test reports with custom metadata:
test('critical user flow', async ({ page }) => {
test
.info()
.annotations.push(
{ type: 'testCaseId', description: 'QA-124' },
{ type: 'tag', description: 'critical' },
{ type: 'tag', description: 'smoke' },
{ type: 'priority', description: 'high' },
{ type: 'owner', description: 'qa-team' }
);
// Your test code...
});All annotations are sent to QAStudio.dev as metadata.
By default, the reporter captures rich error context to help debug failed tests:
- Error Code Snippet: The actual code where the error occurred, with the failing line highlighted
- Precise Error Location: File path, line number, and column where the error happened
- Test Execution Steps: Step-by-step trace of what Playwright was doing when the test failed
- Console Output: Standard output and errors (disabled by default, opt-in)
You can control what error context is captured:
export default defineConfig({
reporter: [
[
'@qastudio-dev/playwright',
{
// ... other options
includeErrorSnippet: true, // Include code snippet (default: true)
includeErrorLocation: true, // Include error location (default: true)
includeTestSteps: true, // Include execution steps (default: true)
includeConsoleOutput: false, // Include stdout/stderr (default: false)
},
],
],
});To reduce data sent to the platform, you can disable specific features:
{
includeErrorSnippet: false, // Don't send code snippets
includeErrorLocation: false, // Don't send precise error location
includeTestSteps: false, // Don't send execution steps
includeConsoleOutput: false, // Don't send console output (already default)
}When a test fails with error context enabled, the reporter sends:
{
error: "Expected 'Login' to be visible",
stackTrace: "Error: Expected 'Login' to be visible\n at ...",
errorSnippet: " 23 | await expect(page.getByRole('button', { name: 'Login' })).toBeVisible();\n ^",
errorLocation: {
file: "/tests/auth.spec.ts",
line: 23,
column: 5
},
steps: [
{
title: "page.goto",
category: "pw:api",
duration: 1245,
location: { file: "/tests/auth.spec.ts", line: 21, column: 3 }
},
{
title: "expect.toBeVisible",
category: "expect",
duration: 5000,
error: "Expected 'Login' to be visible",
location: { file: "/tests/auth.spec.ts", line: 23, column: 5 }
}
],
consoleOutput: {
stdout: "Test starting...\nNavigating to login page...",
stderr: "Warning: Deprecated API usage"
}
}This rich context makes it much easier to understand and debug test failures directly in QAStudio.dev.
To add results to an existing test run instead of creating a new one:
export default defineConfig({
reporter: [
[
'@qastudio-dev/playwright',
{
apiUrl: process.env.QA_STUDIO_API_URL!,
apiKey: process.env.QA_STUDIO_API_KEY!,
projectId: process.env.QA_STUDIO_PROJECT_ID!,
testRunId: 'existing-run-id', // Use existing run
createTestRun: false, // Don't create new run
},
],
],
});Example GitHub Actions workflow:
name: E2E Tests
on: [push, pull_request]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Setup Node.js
uses: actions/setup-node@v3
with:
node-version: '18'
- name: Install dependencies
run: npm ci
- name: Install Playwright browsers
run: npx playwright install --with-deps
- name: Run tests
env:
QA_STUDIO_API_URL: ${{ secrets.QA_STUDIO_API_URL }}
QA_STUDIO_API_KEY: ${{ secrets.QA_STUDIO_API_KEY }}
QA_STUDIO_PROJECT_ID: ${{ secrets.QA_STUDIO_PROJECT_ID }}
run: npx playwright testEnable verbose logging to troubleshoot issues:
export default defineConfig({
reporter: [
[
'@qastudio-dev/playwright',
{
// ... other options
verbose: true, // Enable detailed logs
silent: false, // Throw errors instead of failing silently
},
],
],
});By default, the reporter operates in "silent" mode, meaning it won't fail your tests if the QAStudio.dev API is unavailable. Errors are logged to the console but don't affect test execution.
To make API failures throw errors:
{
silent: false;
}The reporter follows Playwright's reporter lifecycle:
onBegin- Creates or connects to test runonTestBegin- Tracks test start timeonTestEnd- Collects test results and attachmentsonEnd- Sends results in batches and completes test run
Each test result includes:
- Test case ID (if linked)
- Title and full path
- Status (passed/failed/skipped/timedOut)
- Duration
- Error messages and stack traces
- Code snippet showing where error occurred (if available)
- Precise error location (file, line, column)
- Test execution steps with timing and errors
- Console output (stdout/stderr, optional)
- Attachments (screenshots, videos, traces)
- Browser/project information
- Custom metadata from annotations
- Check your API credentials are correct
- Enable verbose mode to see detailed logs
- Verify the project ID exists in QAStudio.dev
- Check that tests are linked with valid test case IDs
Increase the timeout value:
{
timeout: 60000; // 60 seconds
}Increase batch size to reduce number of requests:
{
batchSize: 50;
}Ensure Playwright is configured to capture them:
export default defineConfig({
use: {
screenshot: 'only-on-failure',
video: 'retain-on-failure',
},
});Check the examples/ directory for complete working examples:
examples/playwright.config.ts- Full configuration exampleexamples/example.spec.ts- Test examples with annotationsexamples/.env.example- Environment variables template
Contributions are welcome! Please feel free to submit a Pull Request.
# Clone the repository
git clone https://github.com/QAStudio-Dev/playwright.git
cd @qastudio-dev/playwright
# Install dependencies
npm install
# Build the project
npm run build
# Run tests
npm testMIT License - see LICENSE file for details
- π Documentation
- π Issue Tracker
- π¬ Discussions
See CHANGELOG.md for release history.
Made with β€οΈ for the QA community