From 61ce4082b582ecc725a38b357ba1c404b09d6e1a Mon Sep 17 00:00:00 2001 From: Shivanshu07 Date: Fri, 7 Aug 2026 11:12:24 +0530 Subject: [PATCH] feat(client): carry per-snapshot storybook story metadata to the API Adds an optional snapshot property storybook {id, args, globals} to the snapshot schema (so SDK-attached story identity survives validation) and sends it as a snapshot attribute from client.createSnapshot. Attached by @percy/storybook so the review UI can deep-link the hosted bundle to the exact captured variant. Co-Authored-By: Claude Fable 5 --- packages/client/src/client.js | 4 +++- packages/client/test/client.test.js | 16 +++++++++++----- packages/core/src/config.js | 13 +++++++++++++ 3 files changed, 27 insertions(+), 6 deletions(-) diff --git a/packages/client/src/client.js b/packages/client/src/client.js index 51dfaad8d..342daacab 100644 --- a/packages/client/src/client.js +++ b/packages/client/src/client.js @@ -616,6 +616,7 @@ export class PercyClient { regions, algorithm, algorithmConfiguration, + storybook, resources = [], meta } = {}) { @@ -654,7 +655,8 @@ export class PercyClient { 'enable-javascript': enableJavaScript || null, 'enable-layout': enableLayout || false, 'th-test-case-execution-id': thTestCaseExecutionId || null, - browsers: normalizeBrowsers(browsers) || null + browsers: normalizeBrowsers(browsers) || null, + storybook: storybook || null }, relationships: { resources: { diff --git a/packages/client/test/client.test.js b/packages/client/test/client.test.js index d5149b8da..41e8041af 100644 --- a/packages/client/test/client.test.js +++ b/packages/client/test/client.test.js @@ -1247,6 +1247,7 @@ describe('PercyClient', () => { clientInfo: 'sdk/info', environmentInfo: 'sdk/env', thTestCaseExecutionId: 'random-uuid', + storybook: { id: 'example-button--primary', args: 'primary:!false' }, resources: [{ url: '/foo', content: 'foo', @@ -1288,7 +1289,8 @@ describe('PercyClient', () => { 'enable-javascript': true, 'enable-layout': true, 'th-test-case-execution-id': 'random-uuid', - browsers: null + browsers: null, + storybook: { id: 'example-button--primary', args: 'primary:!false' } }, relationships: { resources: { @@ -1380,7 +1382,8 @@ describe('PercyClient', () => { 'enable-javascript': true, 'enable-layout': true, 'th-test-case-execution-id': 'random-uuid', - browsers: ['chrome', 'firefox', 'safari_on_iphone'] + browsers: ['chrome', 'firefox', 'safari_on_iphone'], + storybook: null }, relationships: { resources: { @@ -1431,7 +1434,8 @@ describe('PercyClient', () => { 'enable-layout': false, regions: null, 'th-test-case-execution-id': null, - browsers: null + browsers: null, + storybook: null }, relationships: { resources: { @@ -1504,7 +1508,8 @@ describe('PercyClient', () => { regions: null, 'enable-layout': false, 'th-test-case-execution-id': null, - browsers: null + browsers: null, + storybook: null }, relationships: { resources: { @@ -2282,7 +2287,8 @@ describe('PercyClient', () => { regions: null, 'enable-layout': false, 'th-test-case-execution-id': null, - browsers: null + browsers: null, + storybook: null }, relationships: { resources: { diff --git a/packages/core/src/config.js b/packages/core/src/config.js index 167d028ba..263c3a87d 100644 --- a/packages/core/src/config.js +++ b/packages/core/src/config.js @@ -567,6 +567,19 @@ export const snapshotSchema = { ignoreStyleSheetSerializationErrors: { $ref: '/config/snapshot#/properties/ignoreStyleSheetSerializationErrors' }, ignoreIframeSelectors: { $ref: '/config/snapshot#/properties/ignoreIframeSelectors' }, pseudoClassEnabledElements: { $ref: '/config/snapshot#/properties/pseudoClassEnabledElements' }, + // Storybook story identity the snapshot was captured with. Attached by + // @percy/storybook and persisted by the API so the review UI can deep-link + // the hosted bundle to the exact captured variant (args/globals are the + // Storybook-encoded query values, e.g. "primary:!false"). + storybook: { + type: 'object', + additionalProperties: false, + properties: { + id: { type: 'string' }, + args: { type: 'string' }, + globals: { type: 'string' } + } + }, discovery: { type: 'object', additionalProperties: false,