From 5af1762d38698267220029efa86e94a32a673796 Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Mon, 13 Apr 2026 17:55:52 -0400 Subject: [PATCH 1/7] docs: Add Snapshots EA product documentation Add three new pages for the Snapshots visual regression testing feature (Early Adopter). Covers the overview and prerequisites, upload setup with CI workflow, and the review/approval workflow with project settings. Co-Authored-By: Claude Opus 4.6 (1M context) --- docs/product/snapshots/index.mdx | 29 ++++ .../snapshots/review-workflow/index.mdx | 44 ++++++ docs/product/snapshots/setup/index.mdx | 126 ++++++++++++++++++ 3 files changed, 199 insertions(+) create mode 100644 docs/product/snapshots/index.mdx create mode 100644 docs/product/snapshots/review-workflow/index.mdx create mode 100644 docs/product/snapshots/setup/index.mdx diff --git a/docs/product/snapshots/index.mdx b/docs/product/snapshots/index.mdx new file mode 100644 index 0000000000000..3ee0b8c0a7ff9 --- /dev/null +++ b/docs/product/snapshots/index.mdx @@ -0,0 +1,29 @@ +--- +title: Snapshots +sidebar_order: 138 +description: Detect visual changes by comparing PNG snapshots against a baseline on every pull request. +new: true +--- + + + +Snapshots catches visual regressions before they reach users. Your CI pipeline generates PNG screenshots, uploads them to Sentry, and Sentry compares each image against a baseline from your main branch using pixel-level diffing. + +When a snapshot changes, Sentry posts a failing GitHub Check on your pull request. You review the diff in Sentry's comparison viewer and approve or reject the changes. + +## How It Works + +1. **Generate snapshots** — Your CI job produces PNG screenshots however you like: Playwright, Storybook, simulator captures, or any tool that outputs PNGs. +2. **Upload to Sentry** — `sentry-cli` uploads the snapshot directory along with Git metadata so Sentry can associate each upload with a commit. +3. **Sentry diffs against the baseline** — Sentry finds the most recent snapshot set from your base branch (matched by `app_id`) and categorizes each image as added, removed, modified, renamed, or unchanged. +4. **Result posted to your PR** — A "Snapshot Testing" GitHub Check appears on the pull request. It passes if nothing changed and fails if any snapshots need approval. +5. **Review and approve** — Click through to Sentry's comparison viewer to inspect diffs, then approve to resolve the failing check. + +## Prerequisites + +- **Early Adopter access** — Enable the Early Adopter toggle in your [organization settings](/organization/early-adopter-features/). +- **Auth token** — A Sentry auth token with `project:write` scope (personal token) or `org:ci` scope (org-level token). +- **sentry-cli >= 3.3.4** — The `build snapshots` command requires version 3.3.4 or later. +- **GitHub integration** — Install the [Sentry GitHub App](/organization/integrations/source-code-mgmt/github/) and grant it access to your repository so Sentry can post Check Runs. + + diff --git a/docs/product/snapshots/review-workflow/index.mdx b/docs/product/snapshots/review-workflow/index.mdx new file mode 100644 index 0000000000000..6682f1f494ebe --- /dev/null +++ b/docs/product/snapshots/review-workflow/index.mdx @@ -0,0 +1,44 @@ +--- +title: Review Snapshots +sidebar_order: 20 +description: Review snapshot diffs on your pull request and approve changes. +--- + + + +## Status Checks + +After you upload snapshots from a pull request branch, a **Snapshot Testing** GitHub Check appears on the pull request. If no snapshots changed, the check passes. If any snapshots were added, removed, or modified, the check fails and requires approval. + +IMAGE: GitHub Check showing Snapshot Testing results on a pull request + +## Comparison Viewer + +Click **Details** on the GitHub Check to open Sentry's comparison viewer. The viewer has two panels: + +- **Sidebar** — Lists all snapshots grouped by status: modified, added, removed, renamed, and unchanged. Click a snapshot to view it. +- **Main panel** — Displays the selected snapshot's diff with three viewing modes: + - **Split** — Side-by-side view of base and current branch with a diff overlay highlighting changed pixels. + - **Wipe** — Drag a slider across the image to compare base and current branch. + - **Onion** — Overlay both images with an adjustable opacity slider. + +IMAGE: Sentry Snapshot comparison viewer showing a modified image with split diff + +## Approve Changes + +There are two ways to approve snapshot changes: + +- Click the **Approve** button on the GitHub Check Run. +- Click **Approve** in the Sentry comparison viewer. + +Approval resolves the failing check. If new changes are pushed to the PR, the check resets and requires approval again. + +## Settings + +Configure snapshot behavior in **Project Settings > Mobile Builds > Snapshots**. + +| Setting | Default | Description | +| --- | :---: | --- | +| Status Checks Enabled | On | Post GitHub Check Runs for snapshot comparisons. | +| Fail on Added Snapshots | Off | Require approval when new snapshots are added. | +| Fail on Removed Snapshots | On | Require approval when existing snapshots are removed. | diff --git a/docs/product/snapshots/setup/index.mdx b/docs/product/snapshots/setup/index.mdx new file mode 100644 index 0000000000000..858340acd8c09 --- /dev/null +++ b/docs/product/snapshots/setup/index.mdx @@ -0,0 +1,126 @@ +--- +title: Upload Snapshots +sidebar_order: 10 +description: Structure your snapshot directory and upload from CI with sentry-cli. +--- + + + +Each snapshot consists of two files: a `.png` image and a `.json` metadata sidecar with the same base name. You can organize snapshots into subdirectories — the CLI reads the entire directory tree. + +``` +snapshots/ +├── homepage.png +├── homepage.json +├── settings/ +│ ├── profile.png +│ ├── profile.json +│ ├── billing.png +│ └── billing.json +``` + +Filenames are the identity key for each snapshot. Keep them stable across runs so Sentry can accurately diff head against base. + +## Metadata + +The `.json` sidecar describes its paired `.png`: + +```json +{ + "display_name": "Billing Page", + "group": "Settings" +} +``` + +| Field | Type | Description | +| --- | --- | --- | +| `display_name` | string | Human-readable label shown in the comparison viewer. | +| `group` | string | Groups related snapshots in the comparison viewer sidebar. | + +You can add arbitrary custom key-value pairs to the JSON file — they are preserved as metadata. + +The CLI automatically computes and adds `content_hash`, `width`, and `height` at upload time. Do not set these yourself. + +## Upload With CI + +To see the workflow Sentry uses on its own codebase, view the [frontend snapshots workflow](https://github.com/getsentry/sentry/blob/master/.github/workflows/frontend-snapshots.yml). + +Below is a complete GitHub Actions workflow you can copy into your repository. Replace the placeholder values with your own snapshot generation command, app ID, and Sentry project slug. + +```yml {filename:.github/workflows/snapshots.yml} +name: Snapshots + +on: + push: + branches: [main] + pull_request: + +concurrency: + group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} + cancel-in-progress: true + +env: + SNAPSHOT_OUTPUT_DIR: .artifacts/snapshots + +jobs: + snapshots: + runs-on: ubuntu-24.04 + timeout-minutes: 20 + steps: + - uses: actions/checkout@v4 + with: + # Use PR head SHA, not the merge commit — avoids phantom diffs + ref: ${{ github.event.pull_request.head.sha || github.sha }} + + # ------------------------------------------------------- + # YOUR SNAPSHOT GENERATION STEP(S) HERE + # ------------------------------------------------------- + # Generate PNG + JSON pairs into $SNAPSHOT_OUTPUT_DIR. + # Examples: + # - Playwright screenshots + # - Storybook captures + # - iOS/Android simulator screenshots + # - Any tool that produces PNGs + # ------------------------------------------------------- + - name: Generate snapshots + run: + + - name: Install sentry-cli + if: ${{ !cancelled() }} + run: curl -sL https://sentry.io/get-cli/ | SENTRY_CLI_VERSION=3.3.4 sh + + - name: Upload snapshots + if: ${{ !cancelled() }} + env: + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_SNAPSHOTS_AUTH_TOKEN }} + run: | + ARGS=( + --auth-token "$SENTRY_AUTH_TOKEN" + build snapshots "${{ env.SNAPSHOT_OUTPUT_DIR }}" + --app-id + --project + --head-sha "${{ github.event.pull_request.head.sha || github.sha }}" + --vcs-provider github + --head-repo-name "${{ github.repository }}" + ) + + if [[ "${{ github.event_name }}" == "pull_request" ]]; then + ARGS+=( + --base-sha "${{ github.event.pull_request.base.sha }}" + --base-repo-name "${{ github.repository }}" + --head-ref "${{ github.head_ref }}" + --base-ref "${{ github.base_ref }}" + --pr-number "${{ github.event.number }}" + ) + fi + + sentry-cli "${ARGS[@]}" +``` + +A few things to note about this workflow: + +- **Checkout at PR head SHA** — Using `ref: ${{ github.event.pull_request.head.sha || github.sha }}` avoids phantom diffs caused by the merge commit GitHub generates by default. +- **Upload even on partial failure** — The `if: ${{ !cancelled() }}` condition ensures partial results still get uploaded if some snapshot tests fail. +- **Keep `--app-id` consistent** — The `app_id` ties head and base uploads together. Sentry finds the baseline by matching the same `app_id` at the `base_sha`. Use one `app_id` per logical app or bundle. + +Other CI systems work by passing the same flags to `sentry-cli build snapshots` explicitly. From 86507a0fafde0c0a8c962a771ea2ce3fc707ab52 Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Mon, 13 Apr 2026 18:01:05 -0400 Subject: [PATCH 2/7] path and title change --- .../index.mdx | 12 ++++++------ .../{setup => uploading-snapshots}/index.mdx | 18 ++++++++++-------- 2 files changed, 16 insertions(+), 14 deletions(-) rename docs/product/snapshots/{review-workflow => reviewing-snapshots}/index.mdx (76%) rename docs/product/snapshots/{setup => uploading-snapshots}/index.mdx (87%) diff --git a/docs/product/snapshots/review-workflow/index.mdx b/docs/product/snapshots/reviewing-snapshots/index.mdx similarity index 76% rename from docs/product/snapshots/review-workflow/index.mdx rename to docs/product/snapshots/reviewing-snapshots/index.mdx index 6682f1f494ebe..94e7323523562 100644 --- a/docs/product/snapshots/review-workflow/index.mdx +++ b/docs/product/snapshots/reviewing-snapshots/index.mdx @@ -1,5 +1,5 @@ --- -title: Review Snapshots +title: Reviewing Snapshots sidebar_order: 20 description: Review snapshot diffs on your pull request and approve changes. --- @@ -37,8 +37,8 @@ Approval resolves the failing check. If new changes are pushed to the PR, the ch Configure snapshot behavior in **Project Settings > Mobile Builds > Snapshots**. -| Setting | Default | Description | -| --- | :---: | --- | -| Status Checks Enabled | On | Post GitHub Check Runs for snapshot comparisons. | -| Fail on Added Snapshots | Off | Require approval when new snapshots are added. | -| Fail on Removed Snapshots | On | Require approval when existing snapshots are removed. | +| Setting | Default | Description | +| ------------------------- | :-----: | ----------------------------------------------------- | +| Status Checks Enabled | On | Post GitHub Check Runs for snapshot comparisons. | +| Fail on Added Snapshots | Off | Require approval when new snapshots are added. | +| Fail on Removed Snapshots | On | Require approval when existing snapshots are removed. | diff --git a/docs/product/snapshots/setup/index.mdx b/docs/product/snapshots/uploading-snapshots/index.mdx similarity index 87% rename from docs/product/snapshots/setup/index.mdx rename to docs/product/snapshots/uploading-snapshots/index.mdx index 858340acd8c09..134ecbe7000a8 100644 --- a/docs/product/snapshots/setup/index.mdx +++ b/docs/product/snapshots/uploading-snapshots/index.mdx @@ -1,11 +1,15 @@ --- -title: Upload Snapshots +title: Uploading Snapshots sidebar_order: 10 description: Structure your snapshot directory and upload from CI with sentry-cli. --- +Snapshots can be used with any frontend screenshot framework. We have examples in different platform documentaiton pages (TODO: EXAMPLES). This page covers the general upload structure and metadata schema. + +## Snapshots Upload Structure + Each snapshot consists of two files: a `.png` image and a `.json` metadata sidecar with the same base name. You can organize snapshots into subdirectories — the CLI reads the entire directory tree. ``` @@ -32,14 +36,12 @@ The `.json` sidecar describes its paired `.png`: } ``` -| Field | Type | Description | -| --- | --- | --- | -| `display_name` | string | Human-readable label shown in the comparison viewer. | -| `group` | string | Groups related snapshots in the comparison viewer sidebar. | - -You can add arbitrary custom key-value pairs to the JSON file — they are preserved as metadata. +| Field | Type | Description | +| -------------- | ------ | ---------------------------------------------------------- | +| `display_name` | string | Human-readable label shown in the comparison viewer. | +| `group` | string | Groups related snapshots in the comparison viewer sidebar. | -The CLI automatically computes and adds `content_hash`, `width`, and `height` at upload time. Do not set these yourself. +TODO: IMAGE OF DISPLAY NAME AND GROUP ## Upload With CI From 61464bd8e7213eefcb16d25e61973417d54505c0 Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Tue, 14 Apr 2026 11:03:59 -0400 Subject: [PATCH 3/7] cleanup --- docs/product/snapshots/index.mdx | 12 ++-- .../snapshots/uploading-snapshots/index.mdx | 57 ++++++++++++++++--- 2 files changed, 58 insertions(+), 11 deletions(-) diff --git a/docs/product/snapshots/index.mdx b/docs/product/snapshots/index.mdx index 3ee0b8c0a7ff9..fa69856a92829 100644 --- a/docs/product/snapshots/index.mdx +++ b/docs/product/snapshots/index.mdx @@ -11,19 +11,23 @@ Snapshots catches visual regressions before they reach users. Your CI pipeline g When a snapshot changes, Sentry posts a failing GitHub Check on your pull request. You review the diff in Sentry's comparison viewer and approve or reject the changes. +TODO: some sort of image + ## How It Works 1. **Generate snapshots** — Your CI job produces PNG screenshots however you like: Playwright, Storybook, simulator captures, or any tool that outputs PNGs. 2. **Upload to Sentry** — `sentry-cli` uploads the snapshot directory along with Git metadata so Sentry can associate each upload with a commit. -3. **Sentry diffs against the baseline** — Sentry finds the most recent snapshot set from your base branch (matched by `app_id`) and categorizes each image as added, removed, modified, renamed, or unchanged. -4. **Result posted to your PR** — A "Snapshot Testing" GitHub Check appears on the pull request. It passes if nothing changed and fails if any snapshots need approval. -5. **Review and approve** — Click through to Sentry's comparison viewer to inspect diffs, then approve to resolve the failing check. +3. **Sentry diffs against the baseline** — Sentry compares uploaded snapshots against snapshots corresponding to the upload's `base_sha`. With Sentry, you do not have to manage "Golden" images and everything is determined via git metadata. +4. **Results post to your PR** — Snapshot results post to your PR\*. You can configure settings to control status check and comment behavior. +5. **Review and approve** — You can view snapshot results on the Sentry UI. If the Snapshot "failed" you can approve it from either the PR or the Sentry UI. + +\*Note: Snapshots EA only supports Github ## Prerequisites - **Early Adopter access** — Enable the Early Adopter toggle in your [organization settings](/organization/early-adopter-features/). - **Auth token** — A Sentry auth token with `project:write` scope (personal token) or `org:ci` scope (org-level token). - **sentry-cli >= 3.3.4** — The `build snapshots` command requires version 3.3.4 or later. -- **GitHub integration** — Install the [Sentry GitHub App](/organization/integrations/source-code-mgmt/github/) and grant it access to your repository so Sentry can post Check Runs. +- **GitHub integration** — Snapshots can be used with any VCS provider, but only Github is supported for status check integration and PR comments. Install the [Sentry GitHub App](/organization/integrations/source-code-mgmt/github/) and grant it access to your repository for PR integration. diff --git a/docs/product/snapshots/uploading-snapshots/index.mdx b/docs/product/snapshots/uploading-snapshots/index.mdx index 134ecbe7000a8..de25f85aade84 100644 --- a/docs/product/snapshots/uploading-snapshots/index.mdx +++ b/docs/product/snapshots/uploading-snapshots/index.mdx @@ -8,9 +8,25 @@ description: Structure your snapshot directory and upload from CI with sentry-cl Snapshots can be used with any frontend screenshot framework. We have examples in different platform documentaiton pages (TODO: EXAMPLES). This page covers the general upload structure and metadata schema. -## Snapshots Upload Structure +## Upload command + +You upload snapshots with the `sentry-cli build snapshots` command, which takes a directory of images and optional JSON metadata files. + +```bash +sentry-cli build snapshots \ + --auth-token "$SENTRY_SNAPSHOTS_AUTH_TOKEN" \ + --app-id \ + --project \ + --head-sha \ + --vcs-provider github \ + --head-repo-name +``` + +You can reference our [example workflow](#upload-with-ci) and [full flag reference](#sentry-cli-build-snapshots-reference) below. -Each snapshot consists of two files: a `.png` image and a `.json` metadata sidecar with the same base name. You can organize snapshots into subdirectories — the CLI reads the entire directory tree. +### Upload Structure + +Each snapshot consists of two files: a `.png` image and an optional `.json` metadata file with the same base name and path. You can organize snapshots into subdirectories, but is not required and will not affect the UX. ``` snapshots/ @@ -25,9 +41,9 @@ snapshots/ Filenames are the identity key for each snapshot. Keep them stable across runs so Sentry can accurately diff head against base. -## Metadata +### JSON Metadata -The `.json` sidecar describes its paired `.png`: +You can optionally include a JSON file to add metadata to each image: ```json { @@ -47,7 +63,7 @@ TODO: IMAGE OF DISPLAY NAME AND GROUP To see the workflow Sentry uses on its own codebase, view the [frontend snapshots workflow](https://github.com/getsentry/sentry/blob/master/.github/workflows/frontend-snapshots.yml). -Below is a complete GitHub Actions workflow you can copy into your repository. Replace the placeholder values with your own snapshot generation command, app ID, and Sentry project slug. +Below is an example GitHub Actions workflow you can use as a starting point. Replace the placeholder values with your own snapshot generation command, app ID, and Sentry project slug. ```yml {filename:.github/workflows/snapshots.yml} name: Snapshots @@ -80,8 +96,8 @@ jobs: # Generate PNG + JSON pairs into $SNAPSHOT_OUTPUT_DIR. # Examples: # - Playwright screenshots - # - Storybook captures - # - iOS/Android simulator screenshots + # - iOS/Android screenshots + # - Laravel Dusk screenshots # - Any tool that produces PNGs # ------------------------------------------------------- - name: Generate snapshots @@ -126,3 +142,30 @@ A few things to note about this workflow: - **Keep `--app-id` consistent** — The `app_id` ties head and base uploads together. Sentry finds the baseline by matching the same `app_id` at the `base_sha`. Use one `app_id` per logical app or bundle. Other CI systems work by passing the same flags to `sentry-cli build snapshots` explicitly. + +## `sentry-cli build snapshots` Reference + +```bash +sentry-cli build snapshots [OPTIONS] --app-id +``` + +| Flag | Description | +| ------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `` | Directory containing `.png` images (and optional `.json`). | +| `--app-id ` | Identifier for the app or bundle (e.g., `web-frontend`, `ios-app`). Must be consistent across uploads — Sentry uses it to match head and base snapshots. Max 255 characters. | +| `--auth-token ` | Sentry auth token with `project:write` or `org:ci` scope. Can also be set via `SENTRY_AUTH_TOKEN`. | +| `-o`, `--org ` | Sentry organization slug. Can also be set via `SENTRY_ORG`. | +| `-p`, `--project ` | Sentry project slug. Can also be set via `SENTRY_PROJECT`. | +| `--head-sha ` | 40-character commit SHA of the snapshot build. Auto-detected in CI. | +| `--base-sha ` | Base branch commit SHA for comparison (PR only). Auto-detected in CI. | +| `--vcs-provider ` | VCS provider, e.g., `github`. Auto-detected from git remote. | +| `--head-repo-name ` | Repository in `owner/repo` format. Auto-detected from git remote. | +| `--base-repo-name ` | Base repository in `owner/repo` format (PR only, for forks). Auto-detected in CI. | +| `--head-ref ` | Head branch name. Auto-detected in CI. | +| `--base-ref ` | Base branch name (PR only). Auto-detected in CI. | +| `--pr-number ` | Pull request number (PR only). Auto-detected in GitHub Actions. | +| `--diff-threshold ` | Float between 0.0 and 1.0. Sentry only reports images as changed if the percentage of changed pixels exceeds this value. For example, `0.01` ignores changes under 1%. | +| `--no-git-metadata` | Skip automatic git metadata detection. | +| `--force-git-metadata` | Force git metadata collection even outside CI. | +| `--log-level ` | Logging verbosity: `debug`, `info`, `warn`, or `error`. | +| `--url ` | Sentry instance URL. Defaults to `https://sentry.io`. | From 47891dd71dcdde1f4546861c2ae0cebc0fb6e0c2 Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Tue, 14 Apr 2026 15:32:43 -0400 Subject: [PATCH 4/7] nelson comments --- docs/product/snapshots/index.mdx | 2 +- .../snapshots/uploading-snapshots/index.mdx | 14 +------------- 2 files changed, 2 insertions(+), 14 deletions(-) diff --git a/docs/product/snapshots/index.mdx b/docs/product/snapshots/index.mdx index fa69856a92829..25128784fc134 100644 --- a/docs/product/snapshots/index.mdx +++ b/docs/product/snapshots/index.mdx @@ -15,7 +15,7 @@ TODO: some sort of image ## How It Works -1. **Generate snapshots** — Your CI job produces PNG screenshots however you like: Playwright, Storybook, simulator captures, or any tool that outputs PNGs. +1. **Generate snapshots** — Your CI job produces PNG screenshots however you like: Playwright, Paparazzi, or any tool that outputs PNGs. 2. **Upload to Sentry** — `sentry-cli` uploads the snapshot directory along with Git metadata so Sentry can associate each upload with a commit. 3. **Sentry diffs against the baseline** — Sentry compares uploaded snapshots against snapshots corresponding to the upload's `base_sha`. With Sentry, you do not have to manage "Golden" images and everything is determined via git metadata. 4. **Results post to your PR** — Snapshot results post to your PR\*. You can configure settings to control status check and comment behavior. diff --git a/docs/product/snapshots/uploading-snapshots/index.mdx b/docs/product/snapshots/uploading-snapshots/index.mdx index de25f85aade84..ccd16763f8752 100644 --- a/docs/product/snapshots/uploading-snapshots/index.mdx +++ b/docs/product/snapshots/uploading-snapshots/index.mdx @@ -73,10 +73,6 @@ on: branches: [main] pull_request: -concurrency: - group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }} - cancel-in-progress: true - env: SNAPSHOT_OUTPUT_DIR: .artifacts/snapshots @@ -110,7 +106,7 @@ jobs: - name: Upload snapshots if: ${{ !cancelled() }} env: - SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_SNAPSHOTS_AUTH_TOKEN }} + SENTRY_AUTH_TOKEN: ${{ secrets.SENTRY_AUTH_TOKEN }} run: | ARGS=( --auth-token "$SENTRY_AUTH_TOKEN" @@ -135,14 +131,6 @@ jobs: sentry-cli "${ARGS[@]}" ``` -A few things to note about this workflow: - -- **Checkout at PR head SHA** — Using `ref: ${{ github.event.pull_request.head.sha || github.sha }}` avoids phantom diffs caused by the merge commit GitHub generates by default. -- **Upload even on partial failure** — The `if: ${{ !cancelled() }}` condition ensures partial results still get uploaded if some snapshot tests fail. -- **Keep `--app-id` consistent** — The `app_id` ties head and base uploads together. Sentry finds the baseline by matching the same `app_id` at the `base_sha`. Use one `app_id` per logical app or bundle. - -Other CI systems work by passing the same flags to `sentry-cli build snapshots` explicitly. - ## `sentry-cli build snapshots` Reference ```bash From 6e9a27f0d0e24f61ecb162f5d763a81b3093e4a8 Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Thu, 16 Apr 2026 11:29:16 -0400 Subject: [PATCH 5/7] edits --- docs/product/snapshots/index.mdx | 30 ++++++++++++------- .../snapshots/uploading-snapshots/index.mdx | 18 +++++++---- 2 files changed, 31 insertions(+), 17 deletions(-) diff --git a/docs/product/snapshots/index.mdx b/docs/product/snapshots/index.mdx index 25128784fc134..ad215a1f10859 100644 --- a/docs/product/snapshots/index.mdx +++ b/docs/product/snapshots/index.mdx @@ -1,25 +1,23 @@ --- title: Snapshots sidebar_order: 138 -description: Detect visual changes by comparing PNG snapshots against a baseline on every pull request. -new: true +description: Snapshot testing to catch visual changes on every pull request. +beta: true --- -Snapshots catches visual regressions before they reach users. Your CI pipeline generates PNG screenshots, uploads them to Sentry, and Sentry compares each image against a baseline from your main branch using pixel-level diffing. +Snapshots helps you catch unintended visual changes before they reach users. Sentry handles image storage, diffing, CI checks, and more. -When a snapshot changes, Sentry posts a failing GitHub Check on your pull request. You review the diff in Sentry's comparison viewer and approve or reject the changes. - -TODO: some sort of image +TODO: Arcade Walkthrough (1. status check showing diff, 2. click into sentry to see diff, 3. approve) ## How It Works -1. **Generate snapshots** — Your CI job produces PNG screenshots however you like: Playwright, Paparazzi, or any tool that outputs PNGs. -2. **Upload to Sentry** — `sentry-cli` uploads the snapshot directory along with Git metadata so Sentry can associate each upload with a commit. -3. **Sentry diffs against the baseline** — Sentry compares uploaded snapshots against snapshots corresponding to the upload's `base_sha`. With Sentry, you do not have to manage "Golden" images and everything is determined via git metadata. -4. **Results post to your PR** — Snapshot results post to your PR\*. You can configure settings to control status check and comment behavior. -5. **Review and approve** — You can view snapshot results on the Sentry UI. If the Snapshot "failed" you can approve it from either the PR or the Sentry UI. +1. **Generate snapshots** — Your CI job produces screenshots however you like: Playwright, Paparazzi, or any tool that outputs PNGs +2. **Upload to Sentry** — `sentry-cli` uploads the snapshot directory to Sentry +3. **Sentry diffs against the baseline** — Sentry compares images against corresponding base build (TODO: link to section explaining automated comparisons). With Sentry, you do not have to manage "Golden" images and everything is determined via git metadata. +4. **Results post to your PR** — Snapshot results post to your PR\*. You can configure settings(TODO: link to settings) to control status check and comment behavior. +5. **Review and approve** — View snapshot results on the Sentry UI. If the Snapshot "failed" you can approve it from either the PR or the Sentry UI. \*Note: Snapshots EA only supports Github @@ -30,4 +28,14 @@ TODO: some sort of image - **sentry-cli >= 3.3.4** — The `build snapshots` command requires version 3.3.4 or later. - **GitHub integration** — Snapshots can be used with any VCS provider, but only Github is supported for status check integration and PR comments. Install the [Sentry GitHub App](/organization/integrations/source-code-mgmt/github/) and grant it access to your repository for PR integration. +## Supported Platforms + +Snapshots works for any platform with a frontend and most platforms have a number of tools to help you generate snapshots. Sentry has a recommended worfklow for the following platforms: + +TODO: idk if we even want this, but putting for now + +- iOS +- Android +- React + diff --git a/docs/product/snapshots/uploading-snapshots/index.mdx b/docs/product/snapshots/uploading-snapshots/index.mdx index ccd16763f8752..51ea4f8121b35 100644 --- a/docs/product/snapshots/uploading-snapshots/index.mdx +++ b/docs/product/snapshots/uploading-snapshots/index.mdx @@ -6,7 +6,7 @@ description: Structure your snapshot directory and upload from CI with sentry-cl -Snapshots can be used with any frontend screenshot framework. We have examples in different platform documentaiton pages (TODO: EXAMPLES). This page covers the general upload structure and metadata schema. +Snapshots works for any platform with a frontend. You can view specific platform examples [here](/product/snapshots#supported-platforms). This page covers the general upload structure and metadata schema. ## Upload command @@ -26,7 +26,7 @@ You can reference our [example workflow](#upload-with-ci) and [full flag referen ### Upload Structure -Each snapshot consists of two files: a `.png` image and an optional `.json` metadata file with the same base name and path. You can organize snapshots into subdirectories, but is not required and will not affect the UX. +Each snapshot consists of two files: a `.png` image and an optional `.json` metadata file with the same base name and path. You can optionally organize snapshots into subdirectories. If using subdirectories, the filename property in the Sentry UX will include the subdirectory path. ``` snapshots/ @@ -43,7 +43,7 @@ Filenames are the identity key for each snapshot. Keep them stable across runs s ### JSON Metadata -You can optionally include a JSON file to add metadata to each image: +You can include an optional JSON file to add metadata to each image: ```json { @@ -58,12 +58,18 @@ You can optionally include a JSON file to add metadata to each image: | `group` | string | Groups related snapshots in the comparison viewer sidebar. | TODO: IMAGE OF DISPLAY NAME AND GROUP +TODO: if diff_threshold makes it in, add -## Upload With CI +### Supported Formats + +Snapshots supports the following image formats: -To see the workflow Sentry uses on its own codebase, view the [frontend snapshots workflow](https://github.com/getsentry/sentry/blob/master/.github/workflows/frontend-snapshots.yml). +- PNG +- JPEG + +## Upload With CI -Below is an example GitHub Actions workflow you can use as a starting point. Replace the placeholder values with your own snapshot generation command, app ID, and Sentry project slug. +For a production example, Sentry's Github action is available [here](https://github.com/getsentry/sentry/blob/master/.github/workflows/frontend-snapshots.yml). Below is an example GitHub Actions workflow you can use as a starting point. Replace the placeholder values with your own snapshot generation command, app ID, and Sentry project slug. ```yml {filename:.github/workflows/snapshots.yml} name: Snapshots From 73a2f74430762f88a4c8506504692257c2fafd3b Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Mon, 20 Apr 2026 09:51:23 -0400 Subject: [PATCH 6/7] Update docs/product/snapshots/uploading-snapshots/index.mdx Co-authored-by: Nelson Osacky --- docs/product/snapshots/uploading-snapshots/index.mdx | 3 --- 1 file changed, 3 deletions(-) diff --git a/docs/product/snapshots/uploading-snapshots/index.mdx b/docs/product/snapshots/uploading-snapshots/index.mdx index 51ea4f8121b35..f69c948fe962a 100644 --- a/docs/product/snapshots/uploading-snapshots/index.mdx +++ b/docs/product/snapshots/uploading-snapshots/index.mdx @@ -17,9 +17,6 @@ sentry-cli build snapshots \ --auth-token "$SENTRY_SNAPSHOTS_AUTH_TOKEN" \ --app-id \ --project \ - --head-sha \ - --vcs-provider github \ - --head-repo-name ``` You can reference our [example workflow](#upload-with-ci) and [full flag reference](#sentry-cli-build-snapshots-reference) below. From bc58655b67db4e572c61f5d5358b820a6e3333fc Mon Sep 17 00:00:00 2001 From: Max Topolsky <30879163+mtopo27@users.noreply.github.com> Date: Mon, 20 Apr 2026 09:54:06 -0400 Subject: [PATCH 7/7] Apply suggestions from code review Co-authored-by: Nelson Osacky --- docs/product/snapshots/index.mdx | 2 +- .../snapshots/uploading-snapshots/index.mdx | 14 +------------- 2 files changed, 2 insertions(+), 14 deletions(-) diff --git a/docs/product/snapshots/index.mdx b/docs/product/snapshots/index.mdx index ad215a1f10859..913878e394e66 100644 --- a/docs/product/snapshots/index.mdx +++ b/docs/product/snapshots/index.mdx @@ -25,7 +25,7 @@ TODO: Arcade Walkthrough (1. status check showing diff, 2. click into sentry to - **Early Adopter access** — Enable the Early Adopter toggle in your [organization settings](/organization/early-adopter-features/). - **Auth token** — A Sentry auth token with `project:write` scope (personal token) or `org:ci` scope (org-level token). -- **sentry-cli >= 3.3.4** — The `build snapshots` command requires version 3.3.4 or later. +- **sentry-cli >= 3.3.5** — The `build snapshots` command requires version 3.3.5 or later. - **GitHub integration** — Snapshots can be used with any VCS provider, but only Github is supported for status check integration and PR comments. Install the [Sentry GitHub App](/organization/integrations/source-code-mgmt/github/) and grant it access to your repository for PR integration. ## Supported Platforms diff --git a/docs/product/snapshots/uploading-snapshots/index.mdx b/docs/product/snapshots/uploading-snapshots/index.mdx index f69c948fe962a..0a431f3689789 100644 --- a/docs/product/snapshots/uploading-snapshots/index.mdx +++ b/docs/product/snapshots/uploading-snapshots/index.mdx @@ -14,7 +14,7 @@ You upload snapshots with the `sentry-cli build snapshots` command, which takes ```bash sentry-cli build snapshots \ - --auth-token "$SENTRY_SNAPSHOTS_AUTH_TOKEN" \ + --auth-token "$SENTRY_AUTH_TOKEN" \ --app-id \ --project \ ``` @@ -116,20 +116,8 @@ jobs: build snapshots "${{ env.SNAPSHOT_OUTPUT_DIR }}" --app-id --project - --head-sha "${{ github.event.pull_request.head.sha || github.sha }}" - --vcs-provider github - --head-repo-name "${{ github.repository }}" ) - if [[ "${{ github.event_name }}" == "pull_request" ]]; then - ARGS+=( - --base-sha "${{ github.event.pull_request.base.sha }}" - --base-repo-name "${{ github.repository }}" - --head-ref "${{ github.head_ref }}" - --base-ref "${{ github.base_ref }}" - --pr-number "${{ github.event.number }}" - ) - fi sentry-cli "${ARGS[@]}" ```