@storystick/preview 0.0.0-stage → 0.2.0-rc.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (245) hide show
  1. package/LICENSE +112 -0
  2. package/PUBLIC-API.md +55 -0
  3. package/README.md +42 -2
  4. package/dist/.source-hash +1 -0
  5. package/dist/authoring/runtime-contract.d.ts +89 -0
  6. package/dist/authoring/runtime-contract.js +28 -0
  7. package/dist/channel-taxonomy.d.ts +17 -0
  8. package/dist/channel-taxonomy.js +46 -0
  9. package/dist/context-command.d.ts +18 -0
  10. package/dist/context-command.js +38 -0
  11. package/dist/dev/suspicious-codeword-detector.d.ts +15 -0
  12. package/dist/dev/suspicious-codeword-detector.js +220 -0
  13. package/dist/dev/suspicious-codeword-detector.noop.d.ts +3 -0
  14. package/dist/dev/suspicious-codeword-detector.noop.js +4 -0
  15. package/dist/framework/browser-context.d.ts +2 -0
  16. package/dist/framework/browser-context.js +2 -0
  17. package/dist/framework/generation-refresh.d.ts +23 -0
  18. package/dist/framework/generation-refresh.js +82 -0
  19. package/dist/framework/generation-signal.d.ts +8 -0
  20. package/dist/framework/generation-signal.js +17 -0
  21. package/dist/framework/projection-generation-watch.d.ts +5 -0
  22. package/dist/framework/projection-generation-watch.js +53 -0
  23. package/dist/framework/render-receipt.d.ts +8 -0
  24. package/dist/framework/render-receipt.js +10 -0
  25. package/dist/framework/runtime-adapter-store.d.ts +30 -0
  26. package/dist/framework/runtime-adapter-store.js +81 -0
  27. package/dist/grant-coordinator.d.ts +53 -0
  28. package/dist/grant-coordinator.js +329 -0
  29. package/dist/grant-lifecycle.d.ts +52 -0
  30. package/dist/grant-lifecycle.js +74 -0
  31. package/dist/identity/__test-adapter.d.ts +34 -0
  32. package/dist/identity/__test-adapter.js +59 -0
  33. package/dist/identity/browser-context-gate.d.ts +4 -0
  34. package/dist/identity/browser-context-gate.js +22 -0
  35. package/dist/identity/browser-context.d.ts +13 -0
  36. package/dist/identity/browser-context.js +22 -0
  37. package/dist/identity/carriers/postmessage.d.ts +84 -0
  38. package/dist/identity/carriers/postmessage.js +177 -0
  39. package/dist/identity/carriers/storage-state.d.ts +41 -0
  40. package/dist/identity/carriers/storage-state.js +99 -0
  41. package/dist/identity/carriers/storage.d.ts +39 -0
  42. package/dist/identity/carriers/storage.js +182 -0
  43. package/dist/identity/carriers/url.d.ts +19 -0
  44. package/dist/identity/carriers/url.js +38 -0
  45. package/dist/identity/identity-state-machine.d.ts +70 -0
  46. package/dist/identity/identity-state-machine.js +244 -0
  47. package/dist/identity/identity-types.d.ts +192 -0
  48. package/dist/identity/identity-types.js +22 -0
  49. package/dist/identity/index.d.ts +18 -0
  50. package/dist/identity/index.js +16 -0
  51. package/dist/identity/preview-cookie.d.ts +9 -0
  52. package/dist/identity/preview-cookie.js +12 -0
  53. package/dist/identity/preview-draft.d.ts +6 -0
  54. package/dist/identity/preview-draft.js +25 -0
  55. package/dist/identity/preview-identity.d.ts +28 -0
  56. package/dist/identity/preview-identity.js +84 -0
  57. package/dist/identity/preview-scope.d.ts +28 -0
  58. package/dist/identity/preview-scope.js +47 -0
  59. package/dist/identity/resolver.d.ts +110 -0
  60. package/dist/identity/resolver.js +334 -0
  61. package/dist/identity/session-query.d.ts +4 -0
  62. package/dist/identity/session-query.js +19 -0
  63. package/dist/index.d.ts +90 -0
  64. package/dist/index.js +788 -0
  65. package/dist/interaction-mode.d.ts +58 -0
  66. package/dist/interaction-mode.js +93 -0
  67. package/dist/nav-handler.d.ts +95 -0
  68. package/dist/nav-handler.js +84 -0
  69. package/dist/overlay-label.d.ts +79 -0
  70. package/dist/overlay-label.js +73 -0
  71. package/dist/provenance/anchor-map.d.ts +95 -0
  72. package/dist/provenance/anchor-map.js +177 -0
  73. package/dist/provenance/carrier-plan.d.ts +51 -0
  74. package/dist/provenance/carrier-plan.js +90 -0
  75. package/dist/provenance/coded-text.d.ts +20 -0
  76. package/dist/provenance/coded-text.js +302 -0
  77. package/dist/provenance/direct-edit-locator.d.ts +29 -0
  78. package/dist/provenance/direct-edit-locator.js +218 -0
  79. package/dist/provenance/editable-leaf.d.ts +134 -0
  80. package/dist/provenance/editable-leaf.js +483 -0
  81. package/dist/provenance/editor-target.d.ts +29 -0
  82. package/dist/provenance/editor-target.js +46 -0
  83. package/dist/provenance/field-leaf-walker.d.ts +21 -0
  84. package/dist/provenance/field-leaf-walker.js +98 -0
  85. package/dist/provenance/frame-dependencies.d.ts +212 -0
  86. package/dist/provenance/frame-dependencies.js +550 -0
  87. package/dist/provenance/index.d.ts +26 -0
  88. package/dist/provenance/index.js +26 -0
  89. package/dist/provenance/local-events.d.ts +1 -0
  90. package/dist/provenance/local-events.js +1 -0
  91. package/dist/provenance/markers.d.ts +21 -0
  92. package/dist/provenance/markers.js +70 -0
  93. package/dist/provenance/multi-frame-anchor-map.d.ts +54 -0
  94. package/dist/provenance/multi-frame-anchor-map.js +109 -0
  95. package/dist/provenance/normalize.d.ts +2 -0
  96. package/dist/provenance/normalize.js +19 -0
  97. package/dist/provenance/overlay-focus-echo.d.ts +17 -0
  98. package/dist/provenance/overlay-focus-echo.js +16 -0
  99. package/dist/provenance/overlay-projection.d.ts +65 -0
  100. package/dist/provenance/overlay-projection.js +201 -0
  101. package/dist/provenance/owner-map.d.ts +55 -0
  102. package/dist/provenance/owner-map.js +239 -0
  103. package/dist/provenance/read-carrier.d.ts +22 -0
  104. package/dist/provenance/read-carrier.js +92 -0
  105. package/dist/provenance/recorder.d.ts +38 -0
  106. package/dist/provenance/recorder.js +82 -0
  107. package/dist/provenance/render-context.d.ts +106 -0
  108. package/dist/provenance/render-context.js +338 -0
  109. package/dist/provenance/reveal-contract.d.ts +44 -0
  110. package/dist/provenance/reveal-contract.js +1 -0
  111. package/dist/provenance/richtext-slice-embed-address.d.ts +20 -0
  112. package/dist/provenance/richtext-slice-embed-address.js +35 -0
  113. package/dist/provenance/runtime-script.d.ts +1 -0
  114. package/dist/provenance/runtime-script.js +2217 -0
  115. package/dist/provenance/sidecar-store.d.ts +63 -0
  116. package/dist/provenance/sidecar-store.js +151 -0
  117. package/dist/provenance/sidecar.d.ts +34 -0
  118. package/dist/provenance/sidecar.js +227 -0
  119. package/dist/provenance/slice-model.d.ts +28 -0
  120. package/dist/provenance/slice-model.js +86 -0
  121. package/dist/provenance/source-identity.d.ts +3 -0
  122. package/dist/provenance/source-identity.js +7 -0
  123. package/dist/provenance/source-map-materializer.d.ts +76 -0
  124. package/dist/provenance/source-map-materializer.js +286 -0
  125. package/dist/provenance/source-registry.d.ts +103 -0
  126. package/dist/provenance/source-registry.js +562 -0
  127. package/dist/provenance/transformed-output-gate.d.ts +161 -0
  128. package/dist/provenance/transformed-output-gate.js +171 -0
  129. package/dist/provenance/types.d.ts +102 -0
  130. package/dist/provenance/types.js +1 -0
  131. package/dist/refresh-policy.d.ts +11 -0
  132. package/dist/refresh-policy.js +14 -0
  133. package/dist/reveal-target.d.ts +8 -0
  134. package/dist/reveal-target.js +47 -0
  135. package/dist/route-paths.d.ts +11 -0
  136. package/dist/route-paths.js +14 -0
  137. package/dist/router-subscriber.d.ts +92 -0
  138. package/dist/router-subscriber.js +44 -0
  139. package/dist/runtime/anchor-types.d.ts +5 -0
  140. package/dist/runtime/anchor-types.js +1 -0
  141. package/dist/runtime/authority-store.d.ts +31 -0
  142. package/dist/runtime/authority-store.js +56 -0
  143. package/dist/runtime/boot.d.ts +52 -0
  144. package/dist/runtime/boot.js +379 -0
  145. package/dist/runtime/content-refresh.d.ts +30 -0
  146. package/dist/runtime/content-refresh.js +68 -0
  147. package/dist/runtime/emit-runtime-error.d.ts +51 -0
  148. package/dist/runtime/emit-runtime-error.js +64 -0
  149. package/dist/runtime/field-proxy.d.ts +112 -0
  150. package/dist/runtime/field-proxy.js +471 -0
  151. package/dist/runtime/form-contract-reporter.d.ts +99 -0
  152. package/dist/runtime/form-contract-reporter.js +391 -0
  153. package/dist/runtime/invalidation-adapter.d.ts +17 -0
  154. package/dist/runtime/invalidation-adapter.js +42 -0
  155. package/dist/runtime/live-query-overlay.d.ts +39 -0
  156. package/dist/runtime/live-query-overlay.js +345 -0
  157. package/dist/runtime/momentary-navigate.d.ts +16 -0
  158. package/dist/runtime/momentary-navigate.js +106 -0
  159. package/dist/runtime/observation-scheduler.d.ts +15 -0
  160. package/dist/runtime/observation-scheduler.js +42 -0
  161. package/dist/runtime/perf-metrics.d.ts +28 -0
  162. package/dist/runtime/perf-metrics.js +90 -0
  163. package/dist/runtime/preview-interaction-policy.d.ts +1 -0
  164. package/dist/runtime/preview-interaction-policy.js +103 -0
  165. package/dist/runtime/preview-overlay-painter.d.ts +27 -0
  166. package/dist/runtime/preview-overlay-painter.js +1732 -0
  167. package/dist/runtime/preview-overlay-sidecar.d.ts +26 -0
  168. package/dist/runtime/preview-overlay-sidecar.js +45 -0
  169. package/dist/runtime/preview-perspective-alignment.d.ts +15 -0
  170. package/dist/runtime/preview-perspective-alignment.js +40 -0
  171. package/dist/runtime/preview-perspective-intent-state.d.ts +23 -0
  172. package/dist/runtime/preview-perspective-intent-state.js +5 -0
  173. package/dist/runtime/preview-transition-state.d.ts +142 -0
  174. package/dist/runtime/preview-transition-state.js +257 -0
  175. package/dist/runtime/render-mode-state.d.ts +51 -0
  176. package/dist/runtime/render-mode-state.js +76 -0
  177. package/dist/runtime/request-id.d.ts +4 -0
  178. package/dist/runtime/request-id.js +8 -0
  179. package/dist/runtime/resolve-schema-field.d.ts +99 -0
  180. package/dist/runtime/resolve-schema-field.js +356 -0
  181. package/dist/runtime/runtime-error-dispatch.d.ts +23 -0
  182. package/dist/runtime/runtime-error-dispatch.js +75 -0
  183. package/dist/runtime/schema-store.d.ts +121 -0
  184. package/dist/runtime/schema-store.js +667 -0
  185. package/dist/runtime/snapshot-assembly.d.ts +104 -0
  186. package/dist/runtime/snapshot-assembly.js +553 -0
  187. package/dist/runtime/snapshot-reporter.d.ts +55 -0
  188. package/dist/runtime/snapshot-reporter.js +375 -0
  189. package/dist/runtime/standalone-overlay-controller.d.ts +33 -0
  190. package/dist/runtime/standalone-overlay-controller.js +281 -0
  191. package/dist/runtime/store.d.ts +307 -0
  192. package/dist/runtime/store.js +1026 -0
  193. package/dist/runtime/windowed-minimap-projection.d.ts +28 -0
  194. package/dist/runtime/windowed-minimap-projection.js +189 -0
  195. package/dist/runtime/workspace-shortcuts.d.ts +30 -0
  196. package/dist/runtime/workspace-shortcuts.js +188 -0
  197. package/dist/sdk-error-copy.d.ts +48 -0
  198. package/dist/sdk-error-copy.js +182 -0
  199. package/dist/select-cursor.d.ts +2 -0
  200. package/dist/select-cursor.js +23 -0
  201. package/dist/server/admission-cookie.d.ts +38 -0
  202. package/dist/server/admission-cookie.js +122 -0
  203. package/dist/server/control-client.d.ts +29 -0
  204. package/dist/server/control-client.js +22 -0
  205. package/dist/server/control-errors.d.ts +22 -0
  206. package/dist/server/control-errors.js +165 -0
  207. package/dist/server/draft-route.d.ts +12 -0
  208. package/dist/server/draft-route.js +45 -0
  209. package/dist/server/extract-token.d.ts +30 -0
  210. package/dist/server/extract-token.js +98 -0
  211. package/dist/server/grant.d.ts +128 -0
  212. package/dist/server/grant.js +395 -0
  213. package/dist/server/ordinary-read-provenance.d.ts +11 -0
  214. package/dist/server/ordinary-read-provenance.js +124 -0
  215. package/dist/server/preview-read-metadata.d.ts +10 -0
  216. package/dist/server/preview-read-metadata.js +27 -0
  217. package/dist/server/provenance-frame-builder.d.ts +53 -0
  218. package/dist/server/provenance-frame-builder.js +102 -0
  219. package/dist/server/provenance-runtime.d.ts +70 -0
  220. package/dist/server/provenance-runtime.js +46 -0
  221. package/dist/server/read-context-command.d.ts +11 -0
  222. package/dist/server/read-context-command.js +53 -0
  223. package/dist/server/read-identity.d.ts +3 -0
  224. package/dist/server/read-identity.js +63 -0
  225. package/dist/server/read-lifecycle.d.ts +17 -0
  226. package/dist/server/read-lifecycle.js +52 -0
  227. package/dist/server/render-frame-provenance.d.ts +133 -0
  228. package/dist/server/render-frame-provenance.js +676 -0
  229. package/dist/server/render-id.d.ts +15 -0
  230. package/dist/server/render-id.js +22 -0
  231. package/dist/server/route-document-provenance.d.ts +77 -0
  232. package/dist/server/route-document-provenance.js +1327 -0
  233. package/dist/server/route-session-cookie.d.ts +33 -0
  234. package/dist/server/route-session-cookie.js +54 -0
  235. package/dist/session-projections.d.ts +33 -0
  236. package/dist/session-projections.js +43 -0
  237. package/dist/session-subscriber.d.ts +124 -0
  238. package/dist/session-subscriber.js +79 -0
  239. package/dist/sha256-fallback.d.ts +30 -0
  240. package/dist/sha256-fallback.js +126 -0
  241. package/dist/types.d.ts +446 -0
  242. package/dist/types.js +85 -0
  243. package/dist/validators.d.ts +61 -0
  244. package/dist/validators.js +110 -0
  245. package/package.json +206 -3
@@ -0,0 +1,27 @@
1
+ import { collectPreviewReadObservations, conservativePreviewRenderWatermark, } from '@storystick/client/internal';
2
+ export function resolvePreviewFrameReadMetadata(codeVersion, ...roots) {
3
+ return resolvePreviewFrameReadMetadataFromObservations(codeVersion, collectPreviewReadObservations(...roots));
4
+ }
5
+ export function resolvePreviewFrameReadMetadataFromObservations(codeVersion, observations) {
6
+ const compatible = observations.filter((observation) => observation.codeVersion === codeVersion);
7
+ const contexts = compatible.flatMap((observation) => observation.readContext ? [observation.readContext] : []);
8
+ const readContext = contexts[0];
9
+ // An independent read cannot lend its receipt to another document. Every
10
+ // observation in a shared-context frame must carry its own query proof.
11
+ if (readContext && compatible.some((read) => !read.receiptId))
12
+ return null;
13
+ if (readContext && (contexts.length !== compatible.length || contexts.some((context) => context.contextId !== readContext.contextId || context.revision !== readContext.revision)))
14
+ return null;
15
+ const observationIds = new Set(compatible.map((observation) => observation.observationId));
16
+ if (observationIds.size !== 1)
17
+ return null;
18
+ const renderWatermark = conservativePreviewRenderWatermark(compatible);
19
+ if (renderWatermark === undefined)
20
+ return null;
21
+ return {
22
+ ...(readContext ? { readContext } : {}),
23
+ receiptIds: [...new Set(compatible.flatMap((observation) => observation.receiptId ? [observation.receiptId] : []))],
24
+ observationId: [...observationIds][0],
25
+ renderWatermark,
26
+ };
27
+ }
@@ -0,0 +1,53 @@
1
+ import { type PreviewReadScopeEcho } from '@storystick/client/internal';
2
+ import type { PreviewReadContext } from '@storystick/types/preview-query-targeting';
3
+ import { type PreviewFrameDependency, type PreviewFrameDependencySet, type PreviewProvenanceCodedTextRootsByDocumentId, type PreviewProvenanceCodedTextWriteSummary, type PreviewProvenanceEditableLeaf, type ProvenanceFrame, type PublicProvenanceSidecar } from '@storystick/preview/provenance';
4
+ import { type PreviewProvenanceRuntime } from './provenance-runtime.js';
5
+ export type PreviewProvenanceAttrs = Readonly<Record<string, string>>;
6
+ export type PreviewProvenanceAttrsByKey = Readonly<Record<string, PreviewProvenanceAttrs>>;
7
+ export interface BuildPreviewProvenanceFrameOptions {
8
+ /**
9
+ * Temporary runtime preview gate. Omit to use
10
+ * `STORYSTICK_PREVIEW_PROVENANCE === '1'`; pass explicitly in tests or
11
+ * trusted preview runtime wiring.
12
+ */
13
+ readonly enabled?: boolean;
14
+ readonly frameId: string;
15
+ readonly readContext?: PreviewReadContext;
16
+ readonly receiptIds?: readonly string[];
17
+ readonly sessionId?: string | null;
18
+ readonly routeHash?: string;
19
+ readonly variantId?: string | null;
20
+ readonly previewScope?: PreviewReadScopeEcho;
21
+ readonly fallbackPathname?: string;
22
+ readonly codeVersion?: string;
23
+ readonly renderId?: string;
24
+ readonly generation?: number;
25
+ readonly observationId?: string;
26
+ readonly renderWatermark?: number;
27
+ readonly renderNonce?: string;
28
+ readonly emissionRevision?: number;
29
+ readonly authoritativeDocumentIds: readonly string[];
30
+ readonly dependencies?: readonly PreviewFrameDependency[];
31
+ readonly leaves: readonly PreviewProvenanceEditableLeaf[];
32
+ readonly codedTextRoot?: unknown;
33
+ readonly codedTextRootPrefix?: readonly (string | number)[];
34
+ readonly codedTextRootsByDocumentId?: PreviewProvenanceCodedTextRootsByDocumentId;
35
+ readonly projectId?: string;
36
+ readonly endpoint?: string;
37
+ readonly convexUrl?: string;
38
+ }
39
+ export interface BuildPreviewProvenanceFrameResult {
40
+ readonly frameId: string;
41
+ readonly sessionId?: string;
42
+ readonly routeHash: string;
43
+ readonly variantId: string | null;
44
+ readonly codeVersion: string;
45
+ readonly renderId: string;
46
+ readonly attrsByKey: PreviewProvenanceAttrsByKey;
47
+ readonly renderFrame: ProvenanceFrame;
48
+ readonly dependencySet: PreviewFrameDependencySet;
49
+ readonly publicSidecar: PublicProvenanceSidecar | null;
50
+ readonly codedTextWrites: PreviewProvenanceCodedTextWriteSummary;
51
+ readonly validationOk: boolean;
52
+ }
53
+ export declare function buildPreviewProvenanceFrameWithRuntime(options: BuildPreviewProvenanceFrameOptions, runtime: PreviewProvenanceRuntime): Promise<BuildPreviewProvenanceFrameResult | null>;
@@ -0,0 +1,102 @@
1
+ import { createPreviewFrameDependencySet, createPublicSidecar, recordPreviewProvenanceEditableLeaves, validateProvenanceFrame, } from '@storystick/preview/provenance';
2
+ import { normalizePreviewVariantId } from '@storystick/preview/identity';
3
+ import { defaultPreviewProvenanceRenderId } from './render-id.js';
4
+ import { createPreviewProvenanceTemporalIdentity, } from './provenance-runtime.js';
5
+ export async function buildPreviewProvenanceFrameWithRuntime(options, runtime) {
6
+ const enabled = options.enabled ?? runtime.config.isEnabled();
7
+ if (!enabled)
8
+ return null;
9
+ // A native layout has a read context before there is a view to bind it to.
10
+ const readContext = options.readContext;
11
+ const sessionId = options.sessionId ?? (readContext ? undefined : await runtime.recorder.readSessionId()) ?? undefined;
12
+ if (!readContext && !sessionId)
13
+ return null;
14
+ if (readContext && !options.receiptIds?.length)
15
+ return null;
16
+ const codeVersion = runtime.config.resolveCodeVersion({ codeVersion: options.codeVersion });
17
+ const routeIdentity = !readContext && sessionId &&
18
+ (options.routeHash === undefined || options.variantId === undefined)
19
+ ? await runtime.recorder.resolveRouteIdentity({
20
+ sessionId, fallbackPathname: options.fallbackPathname,
21
+ projectId: options.projectId, endpoint: options.endpoint, convexUrl: options.convexUrl,
22
+ })
23
+ : null;
24
+ const routeHash = options.routeHash ?? routeIdentity?.routeHash ?? `occurrence:${options.frameId}`;
25
+ const variantId = readContext
26
+ ? readContext.perspective.kind === 'variant' ? readContext.perspective.variantId : null
27
+ : options.variantId === undefined ? routeIdentity?.variantId ?? null : normalizePreviewVariantId(options.variantId);
28
+ const renderId = options.renderId ??
29
+ defaultPreviewProvenanceRenderId({
30
+ frameId: options.frameId,
31
+ routeHash,
32
+ });
33
+ const generation = options.generation ?? 1;
34
+ const generatedTemporalIdentity = createPreviewProvenanceTemporalIdentity(runtime, {
35
+ sessionId,
36
+ frameId: options.frameId,
37
+ routeHash,
38
+ codeVersion,
39
+ renderId,
40
+ generation,
41
+ });
42
+ const renderNonce = options.renderNonce ?? generatedTemporalIdentity.renderNonce;
43
+ const emissionRevision = options.emissionRevision ?? generatedTemporalIdentity.emissionRevision;
44
+ const recorded = await recordPreviewProvenanceEditableLeaves({
45
+ sessionId,
46
+ readContext,
47
+ routeHash,
48
+ variantId,
49
+ previewScope: options.previewScope,
50
+ codeVersion,
51
+ renderId,
52
+ generation,
53
+ renderNonce,
54
+ emissionRevision,
55
+ enabled,
56
+ leaves: options.leaves,
57
+ codedTextRoot: options.codedTextRoot,
58
+ codedTextRootPrefix: options.codedTextRootPrefix,
59
+ codedTextRootsByDocumentId: options.codedTextRootsByDocumentId,
60
+ });
61
+ const dependencySet = createPreviewFrameDependencySet({
62
+ sessionId,
63
+ readContext,
64
+ receiptIds: options.receiptIds,
65
+ routeHash,
66
+ variantId,
67
+ codeVersion,
68
+ frameId: options.frameId,
69
+ renderId,
70
+ generation,
71
+ observationId: options.observationId,
72
+ renderWatermark: options.renderWatermark,
73
+ dependencies: options.dependencies ?? options.authoritativeDocumentIds.map((documentId) => ({
74
+ kind: 'document',
75
+ documentId,
76
+ reason: 'rendered-document',
77
+ })),
78
+ });
79
+ const validation = validateProvenanceFrame(recorded.renderFrame, {
80
+ documentIds: new Set(options.authoritativeDocumentIds.filter((documentId) => documentId.trim().length > 0)),
81
+ routeHash,
82
+ variantId,
83
+ codeVersion,
84
+ });
85
+ const publicSidecar = recorded.publicSidecar === null
86
+ ? null
87
+ : createPublicSidecar(recorded.renderFrame, dependencySet);
88
+ return {
89
+ frameId: options.frameId,
90
+ sessionId,
91
+ routeHash,
92
+ variantId,
93
+ codeVersion,
94
+ renderId,
95
+ attrsByKey: recorded.attrsByKey,
96
+ renderFrame: recorded.renderFrame,
97
+ dependencySet,
98
+ publicSidecar,
99
+ codedTextWrites: recorded.codedTextWrites,
100
+ validationOk: validation.ok,
101
+ };
102
+ }
@@ -0,0 +1,70 @@
1
+ import type { QuerySchemaDefinition } from '@storystick/client';
2
+ import type { PreviewProvenanceEditableTextPathManifest } from '../provenance/index.js';
3
+ import type { PreviewRenderFrameFixtureOptions } from './render-frame-provenance.js';
4
+ export interface ReadPreviewProvenanceSessionOptions {
5
+ readonly sessionId?: string | null;
6
+ }
7
+ export interface ResolvePreviewProvenanceRouteIdentityOptions {
8
+ readonly sessionId: string;
9
+ readonly fallbackPathname?: string;
10
+ readonly projectId?: string;
11
+ readonly endpoint?: string;
12
+ readonly convexUrl?: string;
13
+ }
14
+ export interface PreviewProvenanceRouteIdentity {
15
+ readonly routeUrl: string;
16
+ readonly routeHash: string;
17
+ readonly variantId: string | null;
18
+ }
19
+ export interface StorystickPreviewProvenanceConfig {
20
+ readonly enabled: boolean;
21
+ readonly fixtureEnabled: boolean;
22
+ readonly sessionId: string;
23
+ readonly codeVersion: string;
24
+ readonly fixture: PreviewRenderFrameFixtureOptions | null;
25
+ }
26
+ export interface ResolvePreviewRuntimeCodeVersionOptions {
27
+ readonly codeVersion?: string;
28
+ }
29
+ export interface PreviewProvenanceTemporalIdentityInput {
30
+ readonly sessionId?: string;
31
+ readonly frameId: string;
32
+ readonly routeHash: string;
33
+ readonly codeVersion: string;
34
+ readonly renderId: string;
35
+ readonly generation: number;
36
+ }
37
+ export interface PreviewProvenanceTemporalIdentity {
38
+ readonly renderNonce: string;
39
+ readonly emissionRevision: number;
40
+ }
41
+ export interface PreviewProvenanceRuntimeConfig {
42
+ readonly isEnabled: () => boolean;
43
+ readonly isProduction: () => boolean;
44
+ readonly resolveCodeVersion: (options?: ResolvePreviewRuntimeCodeVersionOptions) => string;
45
+ readonly resolveSemanticConfig: () => StorystickPreviewProvenanceConfig;
46
+ readonly resolveSemanticManifest: () => Promise<PreviewProvenanceEditableTextPathManifest>;
47
+ }
48
+ export interface PreviewProvenanceRuntimeRecorder {
49
+ readonly markNoStore: (input: {
50
+ readonly enabled: boolean;
51
+ }) => void;
52
+ readonly readSessionId: (options?: ReadPreviewProvenanceSessionOptions) => Promise<string | null>;
53
+ readonly resolveRouteIdentity: (options: ResolvePreviewProvenanceRouteIdentityOptions) => Promise<PreviewProvenanceRouteIdentity>;
54
+ }
55
+ export interface PreviewProvenanceRuntime {
56
+ readonly config: PreviewProvenanceRuntimeConfig;
57
+ readonly recorder: PreviewProvenanceRuntimeRecorder;
58
+ /** Optional for V1-compatible injected runtimes; the default is V2-aware. */
59
+ readonly transport?: {
60
+ readonly createTemporalIdentity: (input: PreviewProvenanceTemporalIdentityInput) => PreviewProvenanceTemporalIdentity;
61
+ };
62
+ }
63
+ export declare function createDefaultPreviewProvenanceTemporalIdentity(): PreviewProvenanceTemporalIdentity;
64
+ export declare function createPreviewProvenanceTemporalIdentity(runtime: PreviewProvenanceRuntime, input: PreviewProvenanceTemporalIdentityInput): PreviewProvenanceTemporalIdentity;
65
+ export declare function previewRuntimeForSchema(schema: QuerySchemaDefinition): PreviewProvenanceRuntime | undefined;
66
+ export declare function bindPreviewRuntimeToReads(value: unknown, runtime: PreviewProvenanceRuntime | undefined): void;
67
+ export declare function previewRuntimeForReads(...values: readonly unknown[]): PreviewProvenanceRuntime | undefined;
68
+ export declare function bindPreviewRuntimeToSidecar(sidecar: object | null, runtime: PreviewProvenanceRuntime): void;
69
+ export declare function previewRuntimeForSidecar(sidecar: object | null | undefined): PreviewProvenanceRuntime | undefined;
70
+ export declare function bindPreviewRuntimeToSchema(schema: QuerySchemaDefinition, runtime: PreviewProvenanceRuntime): void;
@@ -0,0 +1,46 @@
1
+ import { collectPreviewReadObservations } from '@storystick/client/internal';
2
+ let lastEmissionRevision = 0;
3
+ export function createDefaultPreviewProvenanceTemporalIdentity() {
4
+ const wallClockRevision = Date.now() * 1_000;
5
+ lastEmissionRevision = Math.max(wallClockRevision, lastEmissionRevision + 1);
6
+ return {
7
+ renderNonce: typeof globalThis.crypto?.randomUUID === 'function'
8
+ ? globalThis.crypto.randomUUID()
9
+ : `${wallClockRevision.toString(36)}-${Math.random().toString(36).slice(2)}`,
10
+ emissionRevision: lastEmissionRevision,
11
+ };
12
+ }
13
+ export function createPreviewProvenanceTemporalIdentity(runtime, input) {
14
+ return runtime.transport?.createTemporalIdentity(input) ?? createDefaultPreviewProvenanceTemporalIdentity();
15
+ }
16
+ // Immutable site bindings and read ownership. No request/session is stored here,
17
+ // and nothing is serialized onto customer data across an RSC boundary.
18
+ const runtimeBySchema = new WeakMap();
19
+ const runtimeByRead = new WeakMap();
20
+ const runtimeBySidecar = new WeakMap();
21
+ export function previewRuntimeForSchema(schema) {
22
+ return runtimeBySchema.get(schema);
23
+ }
24
+ export function bindPreviewRuntimeToReads(value, runtime) {
25
+ if (runtime)
26
+ for (const read of collectPreviewReadObservations(value))
27
+ runtimeByRead.set(read, runtime);
28
+ }
29
+ export function previewRuntimeForReads(...values) {
30
+ let runtime;
31
+ for (const read of collectPreviewReadObservations(...values)) {
32
+ const owner = runtimeByRead.get(read);
33
+ if (runtime && owner && runtime !== owner)
34
+ throw new Error('A document boundary cannot mix different Storystick site definitions.');
35
+ runtime ??= owner;
36
+ }
37
+ return runtime;
38
+ }
39
+ export function bindPreviewRuntimeToSidecar(sidecar, runtime) {
40
+ if (sidecar)
41
+ runtimeBySidecar.set(sidecar, runtime);
42
+ }
43
+ export function previewRuntimeForSidecar(sidecar) {
44
+ return sidecar ? runtimeBySidecar.get(sidecar) : undefined;
45
+ }
46
+ export function bindPreviewRuntimeToSchema(schema, runtime) { runtimeBySchema.set(schema, runtime); }
@@ -0,0 +1,11 @@
1
+ import { type PreviewPerspective } from '@storystick/types/preview-query-targeting';
2
+ export interface PreviewContextCommand {
3
+ commandId: string;
4
+ expectedContextId: string;
5
+ expectedRevision: number;
6
+ perspective: PreviewPerspective | null;
7
+ }
8
+ /** Bounded JSON command reader, shared by context changes and explicit exit. */
9
+ export declare function readPreviewContextCommand(request: Request): Promise<PreviewContextCommand | null>;
10
+ /** Small shared command transport; never buffer an unbounded request. */
11
+ export declare function readBoundedPreviewJson(request: Request, limit?: number): Promise<unknown>;
@@ -0,0 +1,53 @@
1
+ import { isPreviewPerspective } from '@storystick/types/preview-query-targeting';
2
+ /** Bounded JSON command reader, shared by context changes and explicit exit. */
3
+ export async function readPreviewContextCommand(request) {
4
+ const raw = await readBoundedPreviewJson(request);
5
+ if (!raw || typeof raw !== 'object' || Array.isArray(raw)) {
6
+ return null;
7
+ }
8
+ const command = raw;
9
+ if (Object.keys(command).some((key) => !['commandId', 'expectedContextId', 'expectedRevision', 'perspective'].includes(key)) ||
10
+ typeof command.expectedContextId !== 'string' || !command.expectedContextId.trim() || command.expectedContextId.length > 256 ||
11
+ typeof command.commandId !== 'string' || !command.commandId.trim() || command.commandId.length > 128 ||
12
+ !Number.isSafeInteger(command.expectedRevision) || command.expectedRevision < 1 ||
13
+ !(command.perspective === null || isPreviewPerspective(command.perspective))) {
14
+ return null;
15
+ }
16
+ return command;
17
+ }
18
+ /** Small shared command transport; never buffer an unbounded request. */
19
+ export async function readBoundedPreviewJson(request, limit = 4096) {
20
+ try {
21
+ const reader = request.body?.getReader();
22
+ if (!reader)
23
+ throw new Error('missing body');
24
+ const chunks = [];
25
+ let bytes = 0;
26
+ try {
27
+ while (true) {
28
+ const part = await reader.read();
29
+ if (part.done)
30
+ break;
31
+ bytes += part.value.byteLength;
32
+ if (bytes > limit) {
33
+ await reader.cancel();
34
+ throw new Error('body too large');
35
+ }
36
+ chunks.push(part.value);
37
+ }
38
+ }
39
+ finally {
40
+ reader.releaseLock();
41
+ }
42
+ const body = new Uint8Array(bytes);
43
+ let offset = 0;
44
+ for (const chunk of chunks) {
45
+ body.set(chunk, offset);
46
+ offset += chunk.byteLength;
47
+ }
48
+ return JSON.parse(new TextDecoder().decode(body));
49
+ }
50
+ catch {
51
+ return null;
52
+ }
53
+ }
@@ -0,0 +1,3 @@
1
+ import type { Transport } from '@storystick/client/internal';
2
+ export declare function unstable_createPreviewReadIdentityTransport(transport: Transport): Transport;
3
+ export declare function unstable_attachPreviewReadIdentity<T>(value: T): T;
@@ -0,0 +1,63 @@
1
+ import { isContentRenderPlan, mergeContentFields } from '@storystick/types';
2
+ import { attachPreviewProvenanceSourceMap, createPreviewProvenanceQueryResultSourceMap, getPreviewProvenanceSourceMap, } from '@storystick/preview/provenance';
3
+ export function unstable_createPreviewReadIdentityTransport(transport) {
4
+ return {
5
+ async request(input) {
6
+ const response = await transport.request(input);
7
+ if (shouldAttachPreviewReadIdentity(input.requestContext)) {
8
+ return {
9
+ ...response,
10
+ data: unstable_attachPreviewReadIdentity(response.data),
11
+ };
12
+ }
13
+ return response;
14
+ },
15
+ };
16
+ }
17
+ export function unstable_attachPreviewReadIdentity(value) {
18
+ const seen = new WeakSet();
19
+ const visit = (candidate) => {
20
+ if (!isObject(candidate))
21
+ return;
22
+ if (seen.has(candidate))
23
+ return;
24
+ seen.add(candidate);
25
+ if (isQueryResultLike(candidate)) {
26
+ attachReadSourceMap(candidate);
27
+ visit(candidate.resolved);
28
+ return;
29
+ }
30
+ if (Array.isArray(candidate)) {
31
+ for (const item of candidate)
32
+ visit(item);
33
+ return;
34
+ }
35
+ for (const child of Object.values(candidate))
36
+ visit(child);
37
+ };
38
+ visit(value);
39
+ return value;
40
+ }
41
+ function shouldAttachPreviewReadIdentity(requestContext) {
42
+ return (process.env.STORYSTICK_PREVIEW_PROVENANCE === '1' ||
43
+ (typeof requestContext?.previewToken === 'string' &&
44
+ requestContext.previewToken.length > 0));
45
+ }
46
+ function attachReadSourceMap(document) {
47
+ if (getPreviewProvenanceSourceMap(document) !== null)
48
+ return;
49
+ const plan = document._render;
50
+ const fields = isContentRenderPlan(plan) && plan.dependencies
51
+ ? mergeContentFields(plan.dependencies, document.fields)
52
+ : document.fields;
53
+ attachPreviewProvenanceSourceMap(document, createPreviewProvenanceQueryResultSourceMap({ ...document, fields }));
54
+ }
55
+ function isQueryResultLike(value) {
56
+ return (isObject(value) &&
57
+ typeof value.documentId === 'string' &&
58
+ typeof value.storyType === 'string' &&
59
+ isObject(value.fields));
60
+ }
61
+ function isObject(value) {
62
+ return typeof value === 'object' && value !== null;
63
+ }
@@ -0,0 +1,17 @@
1
+ import { type PreviewProvenanceReadLifecycle } from '@storystick/client/internal';
2
+ import type { PreviewPrimaryPage } from '@storystick/preview/provenance';
3
+ import type { PreviewProvenanceRuntime } from './provenance-runtime.js';
4
+ export interface PreviewReadLifecycleOptions {
5
+ /** Routes infer their page; a request-owned draft supplies its explicit destination. */
6
+ readonly primaryPage?: boolean | PreviewPrimaryPage;
7
+ readonly projectId: string;
8
+ readonly endpoint: string;
9
+ readonly runtime?: PreviewProvenanceRuntime;
10
+ readonly previewObservationId?: string | null;
11
+ readonly variantId?: string | null;
12
+ readonly releaseId?: string | null;
13
+ readonly previewCodeVersion?: string | null;
14
+ readonly rawReadCache: Map<string, Promise<unknown>>;
15
+ }
16
+ /** Request-local raw cache. Each consumer gets its own portable Preview values. */
17
+ export declare function createPreviewReadLifecycle(options: PreviewReadLifecycleOptions): PreviewProvenanceReadLifecycle;
@@ -0,0 +1,52 @@
1
+ import { prepareOrdinaryPreviewRead } from './ordinary-read-provenance.js';
2
+ /** Request-local raw cache. Each consumer gets its own portable Preview values. */
3
+ export function createPreviewReadLifecycle(options) {
4
+ return async (input) => {
5
+ const key = JSON.stringify([options.projectId, options.endpoint, options.previewObservationId,
6
+ options.variantId, options.releaseId, options.previewCodeVersion, input.cacheKey]);
7
+ // An abort signal owns its request; it must never cancel a sibling's read.
8
+ let raw = input.signal ? undefined : options.rawReadCache.get(key);
9
+ if (!raw) {
10
+ raw = readProjected(input);
11
+ if (!input.signal)
12
+ options.rawReadCache.set(key, raw);
13
+ }
14
+ const value = await raw;
15
+ const route = value;
16
+ const query = value;
17
+ const primaryPage = typeof options.primaryPage === 'object' && input.kind === 'query-single' &&
18
+ query?.data?.documentId === options.primaryPage.documentId
19
+ ? { document: query.data, identity: options.primaryPage }
20
+ : options.primaryPage === true && input.kind === 'resolved-route' && route?.type === 'document' &&
21
+ typeof route.document?.documentId === 'string' && typeof route.localeContext?.locale === 'string' && typeof route.publicPathname === 'string'
22
+ ? { document: route.document, identity: { documentId: route.document.documentId, locale: route.localeContext.locale, publicPathname: route.publicPathname } }
23
+ : undefined;
24
+ return options.runtime ? prepareOrdinaryPreviewRead(value, options.runtime, { primaryPage }) : value;
25
+ };
26
+ }
27
+ async function readProjected(input) {
28
+ // Projection may advance between the ready notification and this server read.
29
+ // Only the two explicit freshness outcomes are retried, within 750ms total.
30
+ // Exhaustion preserves the blocked result/error; never turn it into absence.
31
+ let value = await input.executeRaw();
32
+ for (const delay of [50, 100, 200, 400]) {
33
+ if (!projectionCatchingUp(value))
34
+ break;
35
+ input.signal?.throwIfAborted();
36
+ await new Promise((resolve, reject) => {
37
+ const abort = () => { clearTimeout(timer); reject(input.signal.reason); };
38
+ const timer = setTimeout(() => { input.signal?.removeEventListener('abort', abort); resolve(); }, delay);
39
+ input.signal?.addEventListener('abort', abort, { once: true });
40
+ });
41
+ input.signal?.throwIfAborted();
42
+ value = await input.executeRaw();
43
+ }
44
+ return value;
45
+ }
46
+ function projectionCatchingUp(value) {
47
+ if (!value || typeof value !== 'object')
48
+ return false;
49
+ const result = value;
50
+ return result.exactness === 'blocked' && result.reason?.retryable === true &&
51
+ (result.reason.code === 'projection-stale' || result.reason.code === 'projection-indexing');
52
+ }
@@ -0,0 +1,133 @@
1
+ import { type PreviewReadScopeEcho } from '@storystick/client/internal';
2
+ import type { PreviewReadContext } from '@storystick/types/preview-query-targeting';
3
+ import { type PreviewFrameDependency, type PreviewFrameDependencySet, type PreviewProvenanceCodedTextRootsByDocumentId, type PreviewProvenanceEditableLeaf, type PreviewProvenanceEditableTextPathManifest, type PreviewProvenancePathPart, type PreviewProvenanceQueryResultLike, type ProvenanceFrame, type PublicProvenanceSidecar } from '@storystick/preview/provenance';
4
+ import { type PreviewProvenanceAttrsByKey } from '../provenance/render-context.js';
5
+ import { type PreviewProvenanceRuntime } from './provenance-runtime.js';
6
+ export interface PreviewRenderFrameFixtureOptions {
7
+ readonly enabled: boolean;
8
+ readonly sessionId: string;
9
+ readonly routeHash?: string;
10
+ readonly variantId?: string | null;
11
+ }
12
+ export interface BuildPreviewRenderFrameOptions<TDocument = unknown, TContext = unknown> {
13
+ /**
14
+ * Temporary runtime preview gate. Omit to use
15
+ * `STORYSTICK_PREVIEW_PROVENANCE === '1'`; pass explicitly in tests or
16
+ * trusted preview runtime wiring.
17
+ */
18
+ readonly enabled?: boolean;
19
+ readonly frameId: string;
20
+ readonly pathname?: string;
21
+ readonly fallbackPathname?: string;
22
+ readonly routeHash?: string;
23
+ readonly variantId?: string | null;
24
+ readonly previewScope?: PreviewReadScopeEcho;
25
+ readonly sessionId?: string | null;
26
+ readonly codeVersion?: string;
27
+ readonly renderId?: string;
28
+ readonly generation?: number;
29
+ readonly renderNonce?: string;
30
+ readonly emissionRevision?: number;
31
+ /** @internal Authenticated read proof, copied before JSON cloning. */
32
+ readonly readContext?: PreviewReadContext;
33
+ readonly receiptIds?: readonly string[];
34
+ /** @internal Transport-derived render clock metadata. */
35
+ readonly observationId?: string;
36
+ /** @internal Transport-derived render clock metadata. */
37
+ readonly renderWatermark?: number;
38
+ readonly authoritativeDocumentIds: readonly string[];
39
+ readonly dependencies?: readonly PreviewFrameDependency[];
40
+ readonly leaves: readonly PreviewProvenanceEditableLeaf[];
41
+ readonly sourceMapDiagnostics?: PreviewRenderFrameSourceMapDiagnostics;
42
+ readonly codedDocument?: TDocument;
43
+ readonly codedContext?: TContext;
44
+ readonly codedTextRoot?: unknown;
45
+ readonly codedTextRootPrefix?: readonly (string | number)[];
46
+ readonly codedTextRootsByDocumentId?: PreviewProvenanceCodedTextRootsByDocumentId;
47
+ readonly fixture?: PreviewRenderFrameFixtureOptions | null;
48
+ readonly projectId?: string;
49
+ readonly endpoint?: string;
50
+ readonly convexUrl?: string;
51
+ }
52
+ export interface PreviewRenderFrame<TDocument = unknown, TContext = unknown> {
53
+ readonly frameId: string;
54
+ readonly sessionId?: string;
55
+ readonly routeHash: string;
56
+ readonly variantId: string | null;
57
+ readonly attrsByKey: PreviewProvenanceAttrsByKey;
58
+ readonly codedDocument?: TDocument;
59
+ readonly codedContext?: TContext;
60
+ readonly renderFrame: ProvenanceFrame;
61
+ readonly dependencySet: PreviewFrameDependencySet;
62
+ readonly publicSidecar: PublicProvenanceSidecar | null;
63
+ readonly validationOk: boolean;
64
+ readonly diagnostics: PreviewRenderFrameDiagnostics;
65
+ }
66
+ export interface PreviewDocumentRenderFrame<TContext = unknown> extends PreviewRenderFrame<undefined, TContext> {
67
+ }
68
+ export interface PreviewRenderFrameSourceMapDiagnostics {
69
+ readonly entries: number;
70
+ readonly manifestIneligible: number;
71
+ readonly nonIdentityDerivation: number;
72
+ readonly carrierSkipped: number;
73
+ }
74
+ export interface PreviewRenderFrameDiagnostics {
75
+ readonly sourceMapEntries: number;
76
+ readonly carriersWritten: number;
77
+ readonly carrierSkipped: number;
78
+ readonly frameBytes: number;
79
+ readonly frameCapped: boolean;
80
+ readonly skipped: {
81
+ readonly manifestIneligible: number;
82
+ readonly nonIdentityDerivation: number;
83
+ readonly cap: number;
84
+ readonly codedTextWriteFailures: number;
85
+ };
86
+ }
87
+ export interface PreviewDocumentRenderFrameLeafPolicyInput<TFields = unknown> {
88
+ readonly document: PreviewProvenanceQueryResultLike;
89
+ readonly storyType: string;
90
+ readonly fields: TFields;
91
+ readonly canonicalPath: string;
92
+ readonly leaf: PreviewProvenanceEditableLeaf;
93
+ }
94
+ export type PreviewDocumentRenderFrameLeafPolicy<TFields = unknown> = (input: PreviewDocumentRenderFrameLeafPolicyInput<TFields>) => boolean;
95
+ export interface PreviewDocumentRenderFrameRead<TFields = unknown> {
96
+ readonly document: PreviewProvenanceQueryResultLike | null | undefined;
97
+ readonly fields?: TFields | null | undefined;
98
+ readonly storyType?: string;
99
+ readonly keyPrefix?: string;
100
+ readonly sourceSetPrefix?: string;
101
+ readonly codedTextRootPath?: readonly PreviewProvenancePathPart[];
102
+ readonly dependencies?: readonly PreviewFrameDependency[];
103
+ readonly renderedLeavesPolicy?: PreviewDocumentRenderFrameLeafPolicy<TFields>;
104
+ }
105
+ export interface BuildPreviewDocumentRenderFrameFromReadsOptions<TContext = unknown> {
106
+ /**
107
+ * Temporary runtime preview gate. Omit to use
108
+ * `STORYSTICK_PREVIEW_PROVENANCE === '1'`.
109
+ */
110
+ readonly enabled?: boolean;
111
+ readonly frameId: string;
112
+ readonly routeHash: string;
113
+ readonly variantId?: string | null;
114
+ readonly sessionId?: string | null;
115
+ readonly codeVersion?: string;
116
+ readonly renderId?: string;
117
+ readonly generation?: number;
118
+ readonly renderNonce?: string;
119
+ readonly emissionRevision?: number;
120
+ readonly documents?: readonly PreviewDocumentRenderFrameRead[];
121
+ readonly context?: TContext;
122
+ readonly manifest: PreviewProvenanceEditableTextPathManifest;
123
+ readonly codedTextRootPrefix?: readonly PreviewProvenancePathPart[];
124
+ readonly authoritativeDocumentIds?: readonly string[];
125
+ readonly dependencies?: readonly PreviewFrameDependency[];
126
+ readonly fixture?: PreviewRenderFrameFixtureOptions | null;
127
+ readonly projectId?: string;
128
+ readonly endpoint?: string;
129
+ readonly convexUrl?: string;
130
+ }
131
+ export declare function unstable_previewRenderFrameRootAttrs(frame: Pick<PreviewRenderFrame, 'sessionId'> | null | undefined): Readonly<Record<string, string>>;
132
+ export declare function unstable_buildPreviewRenderFrameWithRuntime<TDocument = unknown, TContext = unknown>(options: BuildPreviewRenderFrameOptions<TDocument, TContext>, runtime: PreviewProvenanceRuntime): Promise<PreviewRenderFrame<TDocument, TContext> | null>;
133
+ export declare function unstable_buildPreviewDocumentRenderFrameFromReadsWithRuntime<TContext = unknown>(options: BuildPreviewDocumentRenderFrameFromReadsOptions<TContext>, runtime: PreviewProvenanceRuntime): Promise<PreviewDocumentRenderFrame<TContext> | null>;