Skip to content
bemaruPublic

About

Capture your product flows as visual documents

Topics

Resources

Stars

1 star

Watchers

0 watching

Forks

Repository files navigation

flowsnap

Turn Playwright tests into visual flow documentation.

npm version license CI

flowsnap captures page transitions from your Playwright tests and connects the screenshots in a self-contained HTML report. Use it to explain a user journey, review a tested flow, or share the result without running a report server.


Why flowsnap?

  • See the journey: the fixture captures page navigation and the final test state, with labels and arrows between screenshots.
  • Share one file: open the generated HTML offline, with an interactive sidebar, gallery, search, and status filters.
  • Keep structured results: the CTRF JSON report stores flow data in test.extra.flow for other tools to consume.

Try the demo

The existing basic example uses Playwright routing to serve a fictional storefront, cart, and checkout. It does not need an application server or login.

git clone https://github.com/bemaru/flowsnap.git
cd flowsnap
npm ci
npx playwright install chromium
npm run example:basic

If you already have a checkout, start at npm ci. Open examples/basic/flow-report/index.html after the run.

Generated reports stay out of Git. Review your own reports before sharing them, and use synthetic data for public previews.


Install in your Playwright project

npm install flowsnap -D

Requires @playwright/test >= 1.40.0 as a peer dependency.


Quick Start

Full flow: capture page transitions

Add the reporter to playwright.config.ts:

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

export default defineConfig({
  reporter: [
    ['list'],
    ['flowsnap'],
  ],
});

Then change the import in the tests you want to document. Keep your existing test bodies:

- import { test, expect } from '@playwright/test';
+ import { test, expect } from 'flowsnap/fixture';

Run your tests and open flow-report/index.html:

npx playwright test

The fixture captures navigation on its page and a final screenshot at test end. It takes its own screenshots, so this mode does not require Playwright's use.screenshot option.

Reporter only: collect end-of-test screenshots

To keep importing from @playwright/test, use the reporter with Playwright screenshots enabled:

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

export default defineConfig({
  reporter: [
    ['list'],
    ['flowsnap'],
  ],
  use: {
    screenshot: 'on',
  },
});

Playwright disables screenshots by default. Use 'on' for every test or 'only-on-failure' for failed tests. The reporter collects available PNG attachments; without them, the report has no screenshots. This mode does not capture intermediate navigation or URL metadata.


Configuration

Pass options as the second element of the reporter tuple:

reporter: [
  ['flowsnap', {
    outputDir: './flow-report',  // Output directory (default: './flow-report')
    generateHtml: true,          // Generate HTML report (default: true)
    git: false,                  // Disable automatic Git metadata (default: true)
  }],
],

FlowReporterOptions

Option Type Default Description
outputDir string './flow-report' Directory for the JSON report, HTML report, and screenshots
generateHtml boolean true Whether to auto-generate the HTML report after test run
git boolean | GitOptions true Collect Git metadata automatically, disable it with false, or supply values manually

Automatic Git metadata includes the branch, commit, tag, repository name, and remote URL. A manual GitOptions object accepts branch, commit, tag, repositoryName, and repositoryUrl. Disable collection with git: false when this information should not appear in the JSON report; screenshots, page URLs, file paths, and errors still require separate review.


Output

After running npx playwright test, the output directory contains:

flow-report/
  ctrf-report.json        # CTRF-compliant test report with flow data
  index.html              # Self-contained HTML report (all screenshots inlined as base64)
  screenshots/            # Raw screenshot files
    test-name-a0-0.png
    test-name-a0-1.png
    ...

The HTML report is fully self-contained -- screenshots are embedded as base64 data URIs. You can share the single index.html file and it works offline.

HTML Report Features

  • Sidebar with project tree, test search, and status filters (pass/fail/skip)
  • Flow lanes showing each test as a horizontal strip of connected screenshots
  • Screenshot gallery modal with keyboard navigation (arrow keys, Escape)
  • Error display for failed tests with stack traces
  • Responsive layout with mobile sidebar toggle

CTRF Extension: extra.flow

flowsnap outputs standard CTRF (Common Test Report Format) JSON. Flow-specific data is stored in the extra.flow namespace on each test, keeping the report fully compatible with other CTRF tools.

JSON example and flow data types
{
  "reportFormat": "CTRF",
  "specVersion": "0.0.0",
  "results": {
    "tool": { "name": "playwright" },
    "summary": { "tests": 5, "passed": 4, "failed": 1, "..." : "..." },
    "tests": [
      {
        "name": "user login flow",
        "status": "passed",
        "duration": 3200,
        "extra": {
          "flow": {
            "screenshots": [
              {
                "id": "default-user-login-flow-0",
                "url": "https://example.com/",
                "previousUrl": null,
                "timestamp": 1700000000000,
                "screenshotPath": "screenshots/default-user-login-flow-a0-0.png",
                "label": "Start: /"
              },
              {
                "id": "default-user-login-flow-1",
                "url": "https://example.com/login",
                "previousUrl": "https://example.com/",
                "timestamp": 1700000001000,
                "screenshotPath": "screenshots/default-user-login-flow-a0-1.png",
                "label": "/login navigate"
              }
            ],
            "edges": [
              {
                "from": "default-user-login-flow-0",
                "to": "default-user-login-flow-1",
                "label": "/login navigate"
              }
            ]
          }
        }
      }
    ]
  }
}

Flow Data Types

  • FlowScreenshot -- id, url, previousUrl, timestamp, screenshotPath, label
  • FlowEdge -- from (screenshot id), to (screenshot id), optional label

This structure allows other tools to consume the CTRF report normally while ignoring the extra.flow extension, or to build custom visualizations on top of the flow data.


Retry Handling

flowsnap automatically merges retries. When a test is retried, only the final attempt's screenshots are kept. Previous attempt screenshots are cleaned up from disk to avoid clutter.


Programmatic HTML Generation

You can generate (or regenerate) the HTML report from an existing CTRF JSON file:

import { generateFlowHtml } from 'flowsnap';

await generateFlowHtml('./flow-report/ctrf-report.json', './flow-report/index.html');

Capture boundaries and safe sharing

  • Navigation, not every interaction: automatic capture follows main-frame navigation on the fixture's page. Clicks, typing, or opening a modal without navigation do not create separate steps; the final state is also captured.
  • Best-effort capture: screenshots are taken after waiting for rendering, not synchronously with navigation. Rapid transitions can finish before a capture does. Allow each important screen to settle; screenshot failures do not fail the test.
  • Review both HTML and JSON: screenshots can contain private UI data. URLs can include query parameters, errors can contain sensitive values, and JSON can include local test paths and Git metadata. git: false is not a general redaction switch.
  • Keep generated output private by default: exclude flow-report/, test-results/, and playwright-report/ from version control. Only publish explicitly reviewed, synthetic examples.
  • Pre-1.0: APIs and the report shape may change before a stable release.

For questions or bug reports, open an issue. Include a minimal synthetic reproduction, not an unreviewed production report.


Maintainer checks and release notes

Before publishing or cutting a release tag, run:

npm run check
npm pack --dry-run

For a smoke test that exercises the fixture and reporter together:

npm run example:basic

The release workflow publishes only from v* tags and now verifies that the pushed tag matches package.json (for example, v0.0.3 for version 0.0.3).

Public-readiness Caveats

  • This package is still pre-1.0. Treat APIs and report shape as subject to change until a stable release is declared.
  • Automated coverage is currently limited to typecheck/build and the example smoke path. Add focused unit or integration tests before relying on release automation alone.
  • Raw reports remain ignored because they can contain screenshots, URLs, stack traces, and other sensitive data. Any public preview should be captured from the bundled synthetic example and reviewed separately.
  • Confirm npm package version, git tag, and GitHub release notes are aligned before any public announcement.

License

MIT

About

Capture your product flows as visual documents

Topics

Resources

Stars

1 star

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages