@rangojs/router 0.27.0 → 0.29.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 (243) hide show
  1. package/dist/bin/rango.js +1 -1
  2. package/dist/types/__internal.d.ts +7 -1
  3. package/dist/types/browser/action-fence.d.ts +2 -1
  4. package/dist/types/browser/event-controller.d.ts +8 -2
  5. package/dist/types/browser/history-state.d.ts +3 -9
  6. package/dist/types/browser/navigation-store.d.ts +8 -6
  7. package/dist/types/browser/partial-update.d.ts +11 -0
  8. package/dist/types/browser/react/filter-segment-order.d.ts +2 -2
  9. package/dist/types/browser/react/use-action.d.ts +7 -2
  10. package/dist/types/browser/react/use-handle.d.ts +19 -16
  11. package/dist/types/browser/react/use-link-status.d.ts +5 -2
  12. package/dist/types/browser/segment-reconciler.d.ts +32 -4
  13. package/dist/types/browser/types.d.ts +24 -5
  14. package/dist/types/browser/wire-protocol.d.ts +26 -0
  15. package/dist/types/cache/cache-key-utils.d.ts +11 -5
  16. package/dist/types/cache/cache-scope.d.ts +34 -22
  17. package/dist/types/cache/cf/cf-cache-constants.d.ts +2 -2
  18. package/dist/types/cache/cf/cf-cache-store.d.ts +47 -65
  19. package/dist/types/cache/cf/cf-kv-utils.d.ts +1 -1
  20. package/dist/types/cache/handle-snapshot.d.ts +9 -4
  21. package/dist/types/cache/segment-codec.d.ts +14 -0
  22. package/dist/types/cache/shell-snapshot.d.ts +1 -1
  23. package/dist/types/cache/taint.d.ts +5 -3
  24. package/dist/types/cache/types.d.ts +7 -3
  25. package/dist/types/cache/vercel/vercel-cache-store.d.ts +8 -6
  26. package/dist/types/prefetch-markers.d.ts +5 -14
  27. package/dist/types/prerender/store.d.ts +31 -0
  28. package/dist/types/prerender/warm-request.d.ts +3 -3
  29. package/dist/types/prerender.d.ts +2 -2
  30. package/dist/types/route-name.d.ts +5 -0
  31. package/dist/types/router/error-handling.d.ts +11 -5
  32. package/dist/types/router/instrument.d.ts +4 -3
  33. package/dist/types/router/intercept-resolution.d.ts +25 -9
  34. package/dist/types/router/match-context.d.ts +6 -11
  35. package/dist/types/router/match-handlers.d.ts +2 -6
  36. package/dist/types/router/match-middleware/background-revalidation.d.ts +13 -22
  37. package/dist/types/router/match-middleware/cache-lookup.d.ts +34 -86
  38. package/dist/types/router/match-middleware/segment-resolution.d.ts +8 -6
  39. package/dist/types/router/navigation-snapshot.d.ts +7 -0
  40. package/dist/types/router/prerender-match.d.ts +21 -6
  41. package/dist/types/router/preview-match.d.ts +2 -7
  42. package/dist/types/router/request-classification.d.ts +5 -0
  43. package/dist/types/router/router-context.d.ts +7 -46
  44. package/dist/types/router/router-interfaces.d.ts +8 -14
  45. package/dist/types/router/segment-resolution/helpers.d.ts +19 -3
  46. package/dist/types/router/segment-resolution/loader-cache.d.ts +3 -3
  47. package/dist/types/router/segment-resolution/loader-mask.d.ts +4 -4
  48. package/dist/types/router/segment-resolution/prefetch-deferral.d.ts +20 -18
  49. package/dist/types/router/segment-resolution/resolution-pass.d.ts +95 -0
  50. package/dist/types/router/segment-resolution/revalidation.d.ts +82 -31
  51. package/dist/types/router/segment-resolution/streamed-handler-boundary.d.ts +2 -0
  52. package/dist/types/router/segment-resolution.d.ts +1 -2
  53. package/dist/types/router/segment-wrappers.d.ts +11 -48
  54. package/dist/types/router/telemetry.d.ts +2 -0
  55. package/dist/types/router/types.d.ts +11 -1
  56. package/dist/types/rsc/full-payload.d.ts +2 -2
  57. package/dist/types/rsc/handler-context.d.ts +6 -6
  58. package/dist/types/rsc/json-route-result.d.ts +5 -9
  59. package/dist/types/rsc/request-stages.d.ts +203 -0
  60. package/dist/types/rsc/response-cache-serve.d.ts +7 -12
  61. package/dist/types/rsc/response-route-handler.d.ts +2 -2
  62. package/dist/types/rsc/routine-plan.d.ts +1 -1
  63. package/dist/types/rsc/server-action.d.ts +2 -2
  64. package/dist/types/rsc/shell-capture-constants.d.ts +1 -1
  65. package/dist/types/rsc/shell-capture.d.ts +132 -15
  66. package/dist/types/rsc/shell-serve.d.ts +37 -12
  67. package/dist/types/server/context.d.ts +9 -8
  68. package/dist/types/server/handle-store.d.ts +16 -0
  69. package/dist/types/server/render-pass.d.ts +72 -0
  70. package/dist/types/server/request-context.d.ts +53 -104
  71. package/dist/types/server/rewrite-trail.d.ts +2 -2
  72. package/dist/types/testing/dispatch.d.ts +35 -18
  73. package/dist/types/testing/render-route.d.ts +43 -8
  74. package/dist/types/testing/serve-shell-request.d.ts +8 -1
  75. package/dist/types/types/cache-types.d.ts +6 -3
  76. package/dist/types/types/error-types.d.ts +30 -3
  77. package/dist/types/types/handler-context.d.ts +9 -1
  78. package/dist/types/types/segments.d.ts +1 -1
  79. package/dist/types/vite/discovery/build-discovery-phase.d.ts +40 -0
  80. package/dist/types/vite/discovery/build-env.d.ts +22 -0
  81. package/dist/types/vite/discovery/bundle-scan-phase.d.ts +12 -0
  82. package/dist/types/vite/discovery/dev-prerender-cache.d.ts +3 -2
  83. package/dist/types/vite/discovery/dev-server-phase.d.ts +26 -0
  84. package/dist/types/vite/discovery/discovery-errors.d.ts +1 -1
  85. package/dist/types/vite/discovery/state.d.ts +12 -0
  86. package/dist/types/vite/plugins/version-plugin.d.ts +1 -1
  87. package/dist/types/vite/plugins/virtual-entries.d.ts +1 -1
  88. package/dist/types/vite/router-discovery.d.ts +8 -47
  89. package/dist/types/vite/temp-rsc-server.d.ts +39 -0
  90. package/dist/types/vite/utils/prerender-utils.d.ts +9 -0
  91. package/dist/types/wire-params.d.ts +39 -0
  92. package/dist/vite/index.js +3822 -3727
  93. package/package.json +1 -1
  94. package/skills/cache-guide/SKILL.md +8 -5
  95. package/skills/caching/SKILL.md +37 -18
  96. package/skills/client-urls/SKILL.md +4 -2
  97. package/skills/document-cache/SKILL.md +13 -1
  98. package/skills/handler-use/SKILL.md +1 -1
  99. package/skills/hooks/SKILL.md +1 -1
  100. package/skills/hooks/data.md +8 -1
  101. package/skills/hooks/handle-and-actions.md +33 -2
  102. package/skills/hooks/navigation.md +121 -15
  103. package/skills/hooks/state.md +6 -4
  104. package/skills/hooks/urls.md +16 -5
  105. package/skills/intercept/SKILL.md +23 -7
  106. package/skills/middleware/SKILL.md +18 -0
  107. package/skills/observability/SKILL.md +30 -0
  108. package/skills/ppr/SKILL.md +18 -3
  109. package/skills/prerender/SKILL.md +39 -15
  110. package/skills/rango/SKILL.md +5 -1
  111. package/skills/server-actions/SKILL.md +15 -1
  112. package/skills/testing/client-components.md +25 -18
  113. package/skills/testing/response-routes.md +6 -4
  114. package/skills/testing/serve-shell-request.md +7 -7
  115. package/skills/use-cache/SKILL.md +46 -8
  116. package/skills/view-transitions/SKILL.md +1 -1
  117. package/src/__internal.ts +7 -1
  118. package/src/browser/action-fence.ts +2 -1
  119. package/src/browser/connection-warmup.ts +3 -1
  120. package/src/browser/event-controller.ts +37 -13
  121. package/src/browser/history-state.ts +6 -12
  122. package/src/browser/navigation-bridge.ts +59 -26
  123. package/src/browser/navigation-client.ts +20 -25
  124. package/src/browser/navigation-store.ts +25 -27
  125. package/src/browser/navigation-transaction.ts +4 -1
  126. package/src/browser/network-error-handler.ts +4 -0
  127. package/src/browser/partial-update.ts +33 -6
  128. package/src/browser/prefetch/cache.ts +2 -1
  129. package/src/browser/prefetch/fetch.ts +8 -16
  130. package/src/browser/prefetch/queue.ts +4 -4
  131. package/src/browser/react/NavigationProvider.tsx +2 -1
  132. package/src/browser/react/filter-segment-order.ts +2 -2
  133. package/src/browser/react/use-action.ts +24 -48
  134. package/src/browser/react/use-handle.ts +22 -18
  135. package/src/browser/react/use-link-status.ts +48 -60
  136. package/src/browser/react/use-navigation.ts +92 -41
  137. package/src/browser/rsc-router.tsx +1 -0
  138. package/src/browser/segment-reconciler.ts +109 -53
  139. package/src/browser/server-action-bridge.ts +81 -61
  140. package/src/browser/types.ts +25 -5
  141. package/src/browser/wire-protocol.ts +43 -0
  142. package/src/cache/cache-key-utils.ts +11 -5
  143. package/src/cache/cache-runtime.ts +132 -75
  144. package/src/cache/cache-scope.ts +110 -64
  145. package/src/cache/cf/cf-cache-constants.ts +2 -2
  146. package/src/cache/cf/cf-cache-store.ts +486 -874
  147. package/src/cache/cf/cf-kv-utils.ts +1 -1
  148. package/src/cache/document-cache.ts +64 -46
  149. package/src/cache/handle-snapshot.ts +19 -7
  150. package/src/cache/read-through-swr.ts +20 -18
  151. package/src/cache/segment-codec.ts +55 -0
  152. package/src/cache/shell-snapshot.ts +2 -2
  153. package/src/cache/tag-invalidation.ts +6 -2
  154. package/src/cache/taint.ts +5 -3
  155. package/src/cache/types.ts +7 -3
  156. package/src/cache/vercel/vercel-cache-store.ts +243 -310
  157. package/src/handles/pushed-by.ts +1 -1
  158. package/src/prefetch-markers.ts +5 -16
  159. package/src/prerender/store.ts +76 -0
  160. package/src/prerender/warm-request.ts +8 -4
  161. package/src/prerender.ts +2 -2
  162. package/src/route-name.ts +8 -0
  163. package/src/router/error-handling.ts +22 -10
  164. package/src/router/instrument.ts +4 -3
  165. package/src/router/intercept-resolution.ts +82 -75
  166. package/src/router/loader-resolution.ts +5 -4
  167. package/src/router/match-api.ts +5 -5
  168. package/src/router/match-context.ts +23 -12
  169. package/src/router/match-handlers.ts +8 -20
  170. package/src/router/match-middleware/background-revalidation.ts +46 -57
  171. package/src/router/match-middleware/cache-lookup.ts +677 -726
  172. package/src/router/match-middleware/cache-store.ts +4 -8
  173. package/src/router/match-middleware/intercept-resolution.ts +3 -23
  174. package/src/router/match-middleware/segment-resolution.ts +34 -61
  175. package/src/router/middleware.ts +69 -11
  176. package/src/router/navigation-snapshot.ts +14 -4
  177. package/src/router/prerender-match.ts +100 -44
  178. package/src/router/preview-match.ts +6 -41
  179. package/src/router/request-classification.ts +13 -7
  180. package/src/router/route-snapshot.ts +2 -5
  181. package/src/router/router-context.ts +10 -95
  182. package/src/router/router-interfaces.ts +8 -14
  183. package/src/router/segment-resolution/helpers.ts +49 -13
  184. package/src/router/segment-resolution/loader-cache.ts +15 -9
  185. package/src/router/segment-resolution/loader-mask.ts +5 -5
  186. package/src/router/segment-resolution/prefetch-deferral.ts +30 -27
  187. package/src/router/segment-resolution/resolution-pass.ts +139 -0
  188. package/src/router/segment-resolution/revalidation.ts +939 -789
  189. package/src/router/segment-resolution/streamed-handler-boundary.ts +3 -0
  190. package/src/router/segment-resolution.ts +4 -13
  191. package/src/router/segment-wrappers.ts +51 -269
  192. package/src/router/telemetry.ts +5 -0
  193. package/src/router/types.ts +11 -1
  194. package/src/router.ts +19 -17
  195. package/src/rsc/full-payload.ts +6 -5
  196. package/src/rsc/handler-context.ts +8 -14
  197. package/src/rsc/handler.ts +126 -507
  198. package/src/rsc/json-route-result.ts +5 -9
  199. package/src/rsc/loader-fetch.ts +6 -5
  200. package/src/rsc/progressive-enhancement.ts +5 -0
  201. package/src/rsc/request-stages.ts +759 -0
  202. package/src/rsc/response-cache-serve.ts +10 -14
  203. package/src/rsc/response-route-handler.ts +13 -5
  204. package/src/rsc/rewrite-passes.ts +2 -1
  205. package/src/rsc/routine-plan.ts +1 -1
  206. package/src/rsc/rsc-rendering.ts +164 -349
  207. package/src/rsc/server-action.ts +87 -113
  208. package/src/rsc/shell-capture-constants.ts +1 -1
  209. package/src/rsc/shell-capture.ts +275 -227
  210. package/src/rsc/shell-serve.ts +121 -18
  211. package/src/rsc/ssr-setup.ts +5 -4
  212. package/src/segment-system.tsx +3 -3
  213. package/src/server/context.ts +22 -25
  214. package/src/server/handle-store.ts +55 -0
  215. package/src/server/render-pass.ts +291 -0
  216. package/src/server/request-context.ts +75 -115
  217. package/src/server/rewrite-trail.ts +6 -4
  218. package/src/ssr/index.tsx +1 -1
  219. package/src/testing/dispatch.ts +226 -710
  220. package/src/testing/e2e/page-helpers.ts +2 -2
  221. package/src/testing/render-route.tsx +199 -13
  222. package/src/testing/serve-shell-request.ts +36 -40
  223. package/src/types/cache-types.ts +6 -3
  224. package/src/types/error-types.ts +30 -3
  225. package/src/types/handler-context.ts +12 -1
  226. package/src/types/segments.ts +1 -1
  227. package/src/vite/discovery/build-discovery-phase.ts +204 -0
  228. package/src/vite/discovery/build-env.ts +148 -0
  229. package/src/vite/discovery/bundle-scan-phase.ts +128 -0
  230. package/src/vite/discovery/dev-prerender-cache.ts +8 -3
  231. package/src/vite/discovery/dev-server-phase.ts +1776 -0
  232. package/src/vite/discovery/discover-routers.ts +1 -1
  233. package/src/vite/discovery/discovery-errors.ts +1 -1
  234. package/src/vite/discovery/prerender-collection.ts +24 -39
  235. package/src/vite/discovery/state.ts +15 -0
  236. package/src/vite/plugins/version-plugin.ts +1 -1
  237. package/src/vite/plugins/virtual-entries.ts +1 -1
  238. package/src/vite/router-discovery.ts +29 -2428
  239. package/src/vite/temp-rsc-server.ts +223 -0
  240. package/src/vite/utils/prerender-utils.ts +47 -0
  241. package/src/wire-params.ts +40 -0
  242. package/dist/types/router/segment-resolution/fresh.d.ts +0 -72
  243. package/src/router/segment-resolution/fresh.ts +0 -945
@@ -93,14 +93,6 @@ export interface PrefetchDeferral {
93
93
  * a navigation to the page lists.
94
94
  */
95
95
  below?: true;
96
- /**
97
- * The loaders this prefetch deferred, by `$$id` (registerDeferredLoader).
98
- * A deferred loader runs only if something reads it: a handler's or another
99
- * loader's ctx.use() starts it through its registration
100
- * (startDeferredLoader), and revalidation.ts deliverStartedLoaders delivers
101
- * what was started by the end of resolution.
102
- */
103
- deferredLoaders?: Map<string, DeferredLoader>;
104
96
  }
105
97
  /**
106
98
  * How a request may use the route's cache() record, decided once per match
@@ -126,7 +118,14 @@ export interface RecordUse {
126
118
  */
127
119
  readonly refresh: boolean;
128
120
  }
129
- /** A loader this prefetch deferred: PrefetchDeferral.deferredLoaders. */
121
+ /**
122
+ * A DSL loader registered and not started (InternalHandlerContext
123
+ * ._deferredLoaders): a prefetch deferred it, or a pass that skips loaders
124
+ * (`skipLoaders`) did not run it. It runs only if something reads it: a
125
+ * handler's or another loader's ctx.use() starts it through its registration
126
+ * (startDeferredLoader), and revalidation.ts deliverStartedLoaders delivers
127
+ * what a prefetch started by the end of resolution.
128
+ */
130
129
  export interface DeferredLoader {
131
130
  /**
132
131
  * The segment that registers it. Its run files its handle pushes there,
@@ -212,17 +211,20 @@ export declare function interceptFillSkips(match: {
212
211
  /** PrefetchDeferral.record, or all of it open when the match has no plan. */
213
212
  export declare function recordUse(ctx: HandlerContext<any, any> | undefined): RecordUse;
214
213
  /**
215
- * Register a loader this prefetch deferred, with the segment that registers
216
- * it and how to start it there (PrefetchDeferral.deferredLoaders). The first
214
+ * Register a loader resolution does not start, with the segment that
215
+ * registers it and how to start it there (DeferredLoader). The first
217
216
  * registration wins, as the loader's one run per request does.
218
217
  */
219
218
  export declare function registerDeferredLoader(ctx: HandlerContext<any, any>, loaderId: string, owner: string, start: () => Promise<unknown>): void;
220
219
  /**
221
- * A reader asks for a loader this prefetch deferred and nothing has started:
222
- * start it through its registration and return the run, or undefined when
223
- * the read takes the ordinary path. Without this the reader ran the loader
224
- * bare, without its cache() binding, and the segment delivered afterwards
225
- * read the binding: two values on one page and an extra run on a HIT.
220
+ * A reader asks for a registered loader (registerDeferredLoader) and nothing
221
+ * has started it: start it through its registration and return the run, or
222
+ * undefined when the read takes the ordinary path. Without this the reader
223
+ * ran the loader bare, as a handler-invoked loader: in a prefetch without its
224
+ * cache() binding, so the segment delivered afterwards read the binding (two
225
+ * values on one page, an extra run on a HIT); in a route record's background
226
+ * re-render outside its DSL scope, so the record kept its handle pushes and
227
+ * every HIT showed them twice.
226
228
  *
227
229
  * A started cache() binding of the loader (`_loaderCacheOverrides`) is never
228
230
  * redirected here: the read is that binding's own MISS execution, and
@@ -231,8 +233,8 @@ export declare function registerDeferredLoader(ctx: HandlerContext<any, any>, lo
231
233
  export declare function startDeferredLoader(ctx: HandlerContext<any, any>, loaderId: string): Promise<unknown> | undefined;
232
234
  /**
233
235
  * The segment a run of `loaderId` files its handle pushes under: the one
234
- * that registers it when this prefetch deferred it, else the segment being
235
- * resolved.
236
+ * that registers it when it is registered (registerDeferredLoader), else the
237
+ * segment being resolved.
236
238
  */
237
239
  export declare function loaderOwner(ctx: HandlerContext<any, any>, loaderId: string): string | undefined;
238
240
  /**
@@ -0,0 +1,95 @@
1
+ /**
2
+ * ResolutionPass: what one walk over a matched chain reads.
3
+ *
4
+ * Every function of the segment walker (revalidation.ts, intercept-resolution.ts)
5
+ * resolves against the same request: the handler context, the segments the
6
+ * client holds, the previous and next location, the action, the staleness and
7
+ * the router's deps. They take this one object instead of threading the same
8
+ * ten values through each signature in a fixed order, where two adjacent
9
+ * `URL`s or `Record<string, string>`s could swap without a type error.
10
+ *
11
+ * A full match (a document, the background re-render of a route record, a
12
+ * build-time prerender) is a FRESH pass: see FRESH below.
13
+ */
14
+ import type { HandlerContext } from "../../types.js";
15
+ import type { ActionContext, SegmentResolutionDeps } from "../types.js";
16
+ /**
17
+ * The segment ids the client holds, the set resolution works on (match-api.ts
18
+ * may delete a route's id from the listed set to force a render). Empty on a
19
+ * full refetch.
20
+ */
21
+ export type ClientHeld = ReadonlySet<string>;
22
+ /**
23
+ * The client of a full match: it holds nothing and asks for nothing to be
24
+ * kept. Compared by identity (`pass.client === FRESH`), never by size: a
25
+ * partial request whose client holds nothing (NOTHING_HELD, an empty
26
+ * `_rsc_segments`) still asks the revalidate() rules. On a FRESH pass every
27
+ * segment is new without a decision, trace entry or `revalidation.decision`
28
+ * event, and the walker takes the full match's branches (revalidation.ts,
29
+ * each marked FRESH).
30
+ */
31
+ export declare const FRESH: ClientHeld;
32
+ /**
33
+ * A pass without the router's deps: what match middleware knows about the
34
+ * request. createSegmentWrappers (segment-wrappers.ts) binds the deps.
35
+ */
36
+ export interface ResolutionPassInput<TEnv = any> {
37
+ readonly context: HandlerContext<any, TEnv>;
38
+ readonly client: ClientHeld;
39
+ /** The matched route's params, stamped on every segment the walk emits. */
40
+ readonly params: Record<string, string>;
41
+ readonly prevParams: Record<string, string>;
42
+ /** Undefined only on a build-time FRESH pass (freshPassInput). */
43
+ readonly request: Request | undefined;
44
+ readonly prevUrl: URL;
45
+ readonly nextUrl: URL;
46
+ readonly routeKey: string;
47
+ readonly actionContext?: ActionContext;
48
+ readonly stale?: boolean;
49
+ /** NavigationSnapshot.heldBoundary: the walk cuts there, sending no segment. */
50
+ readonly heldBoundary?: string;
51
+ /**
52
+ * No loader is started and no loader segment is emitted: build time
53
+ * (prerender-match.ts) and the background re-render of a route record
54
+ * (background-revalidation.ts), whose records never hold loaders.
55
+ * resolveOwnerLoaders registers each loader instead: in the re-render a
56
+ * handler's read starts it as its declaration; at build time a read
57
+ * throws (setupBuildUse).
58
+ */
59
+ readonly skipLoaders?: boolean;
60
+ /**
61
+ * A render error rethrows instead of rendering the error boundary, and a
62
+ * streamed handler's rejection is not recovered. Build time only, so a
63
+ * failure (or `throw new Skip()`) reaches the build instead of being baked
64
+ * into a frozen 200 (issue #587).
65
+ */
66
+ readonly throwOnError?: boolean;
67
+ /**
68
+ * The request is a navigation, though the pass is FRESH: the background
69
+ * re-render of a record a navigation read stale or wrote
70
+ * (background-revalidation.ts). An entry's error reports isPartial, as the
71
+ * navigation's own pass does.
72
+ */
73
+ readonly partialRequest?: boolean;
74
+ }
75
+ export interface ResolutionPass<TEnv = any> extends ResolutionPassInput<TEnv> {
76
+ readonly deps: SegmentResolutionDeps<TEnv>;
77
+ }
78
+ /**
79
+ * The input of a full match's pass (FRESH). At build time the prerender
80
+ * context's `request` is a throwing getter (handler-context.ts
81
+ * createPrerenderContext): the pass carries undefined instead.
82
+ */
83
+ export declare function freshPassInput<TEnv>(context: HandlerContext<any, TEnv>, routeKey: string, params: Record<string, string>, options?: {
84
+ skipLoaders?: boolean;
85
+ throwOnError?: boolean;
86
+ partialRequest?: boolean;
87
+ }): ResolutionPassInput<TEnv>;
88
+ /**
89
+ * The input of a pass whose client holds nothing: every segment is new and
90
+ * renders. The background re-render of an intercept (background-revalidation.ts)
91
+ * resolves with it.
92
+ */
93
+ export declare function heldNothingPassInput<TEnv>(context: HandlerContext<any, TEnv>, routeKey: string, params: Record<string, string>, options?: {
94
+ skipLoaders?: boolean;
95
+ }): ResolutionPassInput<TEnv>;
@@ -1,13 +1,20 @@
1
1
  /**
2
- * Revalidation Path Segment Resolution
2
+ * The segment walker.
3
3
  *
4
- * Functions for resolving segments during partial (revalidation) requests.
5
- * Mirrors the fresh path but adds revalidation awareness: only re-resolves
6
- * segments whose revalidate() predicate returns true.
4
+ * Resolves a matched chain's segments (loaders, layouts, routes, parallels,
5
+ * orphan layouts, error boundaries) in handler-first order. A partial request
6
+ * re-resolves only what the client lacks and what a held segment's
7
+ * revalidate() rules ask for. A full match (a document, the background
8
+ * re-render of a route record, a build-time prerender) walks the same code
9
+ * with `pass.client === FRESH` (resolution-pass.ts): every segment is new,
10
+ * and the branches marked FRESH keep what the full match has always done
11
+ * differently.
7
12
  */
8
13
  import { type EntryData, type LoaderEntry } from "../../server/context";
9
14
  import type { HandlerContext, ResolvedSegment, ShouldRevalidateFn } from "../../types";
10
- import type { SegmentResolutionDeps, SegmentRevalidationResult, ActionContext } from "../types.js";
15
+ import type { SegmentRevalidationResult } from "../types.js";
16
+ import type { InterceptResult } from "../router-context.js";
17
+ import { type ResolutionPass } from "./resolution-pass.js";
11
18
  /**
12
19
  * A deferred loader something started in this request (a handler that awaits
13
20
  * it with ctx.use(), or another loader) ran in the prefetch whatever its flag
@@ -37,23 +44,37 @@ export interface LoaderOwner {
37
44
  * False for an intercept: never a document.
38
45
  */
39
46
  readonly bakeLane: boolean;
47
+ /**
48
+ * The owner declares loading(false). A FRESH pass then settles every loader
49
+ * before the handler runs (resolveOwnerLoaders). Unset for an intercept.
50
+ */
51
+ readonly loadingDisabled?: boolean;
40
52
  readonly traceSource: "loader" | "intercept-loader";
41
53
  }
42
54
  /** A route entry as a LoaderOwner, under `shortCodeOverride` when inherited. */
43
55
  export declare function ownerOf(entry: EntryData, shortCodeOverride?: string): LoaderOwner;
44
56
  /**
45
- * The partial lane's one loader funnel: each loader is a segment, run when
46
- * the client lacks it, asked its revalidate() when held, kept outright in a
47
- * fill (fillSends), deferred in a prefetch that defers it (defersLoader).
57
+ * The walker's one loader funnel: each loader is a segment, run when the
58
+ * client lacks it, asked its revalidate() when held, kept outright in a fill
59
+ * (fillSends), deferred in a prefetch that defers it (defersLoader).
60
+ *
61
+ * Loaders run lazily via ctx.use() and are memoized, so they run in
62
+ * parallel. A FRESH pass kicks every loader off without an await, in the
63
+ * tick the call starts: a reader's ctx.use(Loader) finds the binding only if
64
+ * it registered first (docs/design/handle-push-ownership.md).
48
65
  */
49
- export declare function resolveOwnerLoaders<TEnv>(owner: LoaderOwner, ctx: HandlerContext<any, TEnv>, belongsToRoute: boolean, clientSegmentIds: ReadonlySet<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, routeKey: string, deps: SegmentResolutionDeps<TEnv>, actionContext?: ActionContext, stale?: boolean): Promise<{
66
+ export declare function resolveOwnerLoaders<TEnv>(pass: ResolutionPass<TEnv>, owner: LoaderOwner, belongsToRoute: boolean): Promise<{
50
67
  segments: ResolvedSegment[];
51
68
  matchedIds: string[];
52
69
  }>;
53
70
  /**
54
- * Resolve only loader segments for all entries with revalidation logic.
71
+ * Resolve only loader segments for all entries: a cache() or prerender HIT
72
+ * serves the cached non-loader segments, and loaders are never cached. Under
73
+ * an intercept the route's entry, and on an intercept's fill an entry the
74
+ * client lacks, are skipped as resolveAllSegments skips them, after the ppr
75
+ * header latch below has read the chain's leaf.
55
76
  */
56
- export declare function resolveLoadersOnlyWithRevalidation<TEnv>(entries: EntryData[], context: HandlerContext<any, TEnv>, clientSegmentIds: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, routeKey: string, deps: SegmentResolutionDeps<TEnv>, actionContext?: ActionContext, stale?: boolean): Promise<{
77
+ export declare function resolveLoadersOnly<TEnv>(pass: ResolutionPass<TEnv>, entries: EntryData[], walk?: Pick<RevalidatingWalkOptions, "interceptResult">): Promise<{
57
78
  segments: ResolvedSegment[];
58
79
  matchedIds: string[];
59
80
  }>;
@@ -65,9 +86,9 @@ export declare function buildEntryRevalidateMap(entries: EntryData[]): Map<strin
65
86
  revalidate: ShouldRevalidateFn<any, any>[];
66
87
  }>;
67
88
  /**
68
- * Resolve parallel segments with revalidation.
89
+ * Resolve an entry's parallel slots: each slot's segment and its loaders.
69
90
  */
70
- export declare function resolveParallelSegmentsWithRevalidation<TEnv>(entry: EntryData, params: Record<string, string>, context: HandlerContext<any, TEnv>, belongsToRoute: boolean, clientSegmentIds: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, routeKey: string, deps: SegmentResolutionDeps<TEnv>, actionContext?: ActionContext, stale?: boolean, options?: {
91
+ export declare function resolveParallelSegments<TEnv>(pass: ResolutionPass<TEnv>, entry: EntryData, belongsToRoute: boolean, options?: {
71
92
  /**
72
93
  * Seed for an unknown parent-chain slot (slot not in clientSegmentIds) when
73
94
  * there are no deciding revalidate fns. "type-derived" (default, main path):
@@ -85,43 +106,73 @@ export declare function resolveParallelSegmentsWithRevalidation<TEnv>(entry: Ent
85
106
  * to it: loader sub-ids are filtered out and slots are re-grouped by parent).
86
107
  */
87
108
  loaderOrder?: "after" | "before";
88
- /** Matched chain entry being resolved; see ResolveSegmentOptions.boundaryEntry. */
109
+ /**
110
+ * The matched chain entry being resolved: where the sync path catches a
111
+ * handler error, so a streamed slot handler (or a slot owned by a
112
+ * routeless layout) recovers into the same boundary. Defaults to `entry`.
113
+ */
89
114
  boundaryEntry?: EntryData;
90
115
  }): Promise<SegmentRevalidationResult>;
91
116
  /**
92
- * Resolve entry handler (layout, cache, or route) with revalidation.
117
+ * Resolve a chain entry's handler (layout, cache, or route) into its segment.
93
118
  */
94
- export declare function resolveEntryHandlerWithRevalidation<TEnv>(entry: Exclude<EntryData, {
119
+ export declare function resolveEntryHandler<TEnv>(pass: ResolutionPass<TEnv>, entry: Exclude<EntryData, {
95
120
  type: "parallel";
96
- }>, params: Record<string, string>, context: HandlerContext<any, TEnv>, belongsToRoute: boolean, clientSegmentIds: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, routeKey: string, deps: SegmentResolutionDeps<TEnv>, actionContext?: ActionContext, stale?: boolean): Promise<{
121
+ }>, belongsToRoute: boolean): Promise<{
97
122
  segment: ResolvedSegment;
98
123
  matchedId: string;
99
124
  }>;
100
125
  /**
101
- * Resolve segments with revalidation awareness (for partial rendering).
126
+ * Resolve one chain entry's segments: its loaders, its handler, its orphan
127
+ * layouts and its parallels, handler first.
102
128
  */
103
- export declare function resolveSegmentWithRevalidation<TEnv>(entry: Exclude<EntryData, {
129
+ export declare function resolveSegment<TEnv>(pass: ResolutionPass<TEnv>, entry: Exclude<EntryData, {
104
130
  type: "parallel";
105
- }>, routeKey: string, params: Record<string, string>, context: HandlerContext<any, TEnv>, clientSegmentIds: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, deps: SegmentResolutionDeps<TEnv>, actionContext?: ActionContext, stale?: boolean,
106
- /** The matched route's full chain; see ResolveSegmentOptions.chain (fresh.ts). */
131
+ }>,
132
+ /** The matched route's full chain; see RevalidatingWalkOptions.chain. */
107
133
  chain?: readonly EntryData[]): Promise<SegmentRevalidationResult>;
108
134
  /**
109
- * Resolve orphan layout with revalidation.
135
+ * Resolve an orphan layout: its loaders, its handler, its slots and the
136
+ * routeless entries nested in it.
110
137
  */
111
- export declare function resolveOrphanLayoutWithRevalidation<TEnv>(orphan: EntryData, params: Record<string, string>, context: HandlerContext<any, TEnv>, clientSegmentIds: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, routeKey: string, belongsToRoute: boolean, deps: SegmentResolutionDeps<TEnv>, actionContext?: ActionContext, stale?: boolean,
138
+ export declare function resolveOrphanLayout<TEnv>(pass: ResolutionPass<TEnv>, orphan: EntryData, belongsToRoute: boolean,
112
139
  /** Parent route entry — its loaders are inherited so parallel slots can access them. */
113
140
  parentRouteEntry?: EntryData,
114
- /** Matched chain entry being resolved (see ResolveSegmentOptions.boundaryEntry); defaults to parentRouteEntry. */
141
+ /**
142
+ * Matched chain entry being resolved (see
143
+ * resolveParallelSegments's boundaryEntry); defaults to
144
+ * parentRouteEntry.
145
+ */
115
146
  boundaryEntry?: EntryData | undefined): Promise<SegmentRevalidationResult>;
147
+ /** What resolveAllSegments needs beyond its pass. */
148
+ export interface RevalidatingWalkOptions {
149
+ /**
150
+ * The intercept the request resolves: the route's entry (its handler and
151
+ * loaders) is skipped and only its id is matched. None on a full match.
152
+ */
153
+ readonly interceptResult?: InterceptResult | null;
154
+ /** For the intercept skip's debug log. */
155
+ readonly localRouteName?: string;
156
+ /** Where an entry's error boundary reports (resolveWithErrorBoundary). */
157
+ readonly pathname: string;
158
+ /**
159
+ * The matched route's full entry chain. Defaults to `entries`;
160
+ * withCacheLookup passes it when it resolves only the entries above a
161
+ * cache() boundary. An orphan list can hold an entry of the chain: a bare
162
+ * cache() marker sits in its layout's layout[] (it wraps that layout's
163
+ * routes) and is the parent of the routes after it. For those routes it
164
+ * resolves once, as a chain entry, below the cache() header latch (issue
165
+ * #918: resolved twice on a MISS, once and discarded on a HIT).
166
+ */
167
+ readonly chain?: readonly EntryData[];
168
+ }
116
169
  /**
117
- * Resolve all segments for a route with revalidation logic (for matchPartial).
170
+ * Resolve all segments for a route: a partial match (matchPartial), a full
171
+ * match with a FRESH pass, or the FRESH pass of an intercept record's
172
+ * background re-render (rerenderAndCacheRoute). A thrown action's pass is cut
173
+ * at its error boundary (ActionContext.boundary).
118
174
  */
119
- export declare function resolveAllSegmentsWithRevalidation<TEnv>(entries: EntryData[], routeKey: string, params: Record<string, string>, context: HandlerContext<any, TEnv>, clientSegmentSet: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, actionContext: ActionContext | undefined, interceptResult: {
120
- intercept: any;
121
- entry: EntryData;
122
- } | null, localRouteName: string, pathname: string, deps: SegmentResolutionDeps<TEnv>, stale?: boolean,
123
- /** The matched route's full chain; see ResolveSegmentOptions.chain (fresh.ts). */
124
- chain?: readonly EntryData[]): Promise<{
175
+ export declare function resolveAllSegments<TEnv>(pass: ResolutionPass<TEnv>, entries: EntryData[], walk: RevalidatingWalkOptions): Promise<{
125
176
  segments: ResolvedSegment[];
126
177
  matchedIds: string[];
127
178
  }>;
@@ -32,6 +32,8 @@ export interface StreamedHandlerOptions<TEnv> {
32
32
  context: HandlerContext<any, TEnv>;
33
33
  routeKey?: string;
34
34
  params: Record<string, string>;
35
+ /** onError's `isPartial`, as the walk reports a sync handler's error. */
36
+ isPartial: true | undefined;
35
37
  /** False where the rejection must reach the caller (prerender, intercept background re-render). */
36
38
  recover: boolean;
37
39
  }
@@ -1,3 +1,2 @@
1
1
  export { handleHandlerResult, warnOnStreamedResponse, buildLoaderErrorContext, } from "./segment-resolution/helpers.js";
2
- export { resolveLoaders, type ResolveSegmentOptions, resolveSegment, resolveOrphanLayout, resolveParallelEntry, resolveAllSegments, resolveLoadersOnly, } from "./segment-resolution/fresh.js";
3
- export { resolveLoadersOnlyWithRevalidation, buildEntryRevalidateMap, resolveParallelSegmentsWithRevalidation, resolveEntryHandlerWithRevalidation, resolveSegmentWithRevalidation, resolveOrphanLayoutWithRevalidation, resolveAllSegmentsWithRevalidation, } from "./segment-resolution/revalidation.js";
2
+ export { resolveLoadersOnly, buildEntryRevalidateMap, resolveParallelSegments, resolveEntryHandler, resolveSegment, resolveOrphanLayout, resolveAllSegments, } from "./segment-resolution/revalidation.js";
@@ -1,51 +1,14 @@
1
- import type { EntryData, InterceptEntry } from "../server/context";
2
- import type { HandlerContext, ResolvedSegment, ShouldRevalidateFn } from "../types";
3
1
  import type { SegmentResolutionDeps } from "./types.js";
4
- import type { ResolveSegmentOptions } from "./segment-resolution.js";
5
- import type { RevalidationContext } from "./router-context.js";
6
- import type { InterceptSelectorContext } from "../server/context";
7
- export interface SegmentWrappers<TEnv = any> {
8
- resolveAllSegments: (entries: EntryData[], routeKey: string, params: Record<string, string>, context: HandlerContext<any, TEnv>, loaderPromises: Map<string, Promise<any>>, options?: ResolveSegmentOptions) => Promise<ResolvedSegment[]>;
9
- resolveLoadersOnly: (entries: EntryData[], context: HandlerContext<any, TEnv>) => Promise<ResolvedSegment[]>;
10
- resolveLoadersOnlyWithRevalidation: (entries: EntryData[], context: HandlerContext<any, TEnv>, clientSegmentIds: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, routeKey: string, actionContext?: {
11
- actionId?: string;
12
- actionUrl?: URL;
13
- actionResult?: any;
14
- formData?: FormData;
15
- }, stale?: boolean) => Promise<{
16
- segments: ResolvedSegment[];
17
- matchedIds: string[];
18
- }>;
19
- buildEntryRevalidateMap: (entries: EntryData[]) => Map<string, {
20
- entry: EntryData;
21
- revalidate: ShouldRevalidateFn<any, any>[];
22
- }>;
23
- resolveAllSegmentsWithRevalidation: (entries: EntryData[], routeKey: string, params: Record<string, string>, context: HandlerContext<any, TEnv>, clientSegmentSet: Set<string>, prevParams: Record<string, string>, request: Request, prevUrl: URL, nextUrl: URL, actionContext: {
24
- actionId?: string;
25
- actionUrl?: URL;
26
- actionResult?: any;
27
- formData?: FormData;
28
- } | undefined, interceptResult: {
29
- intercept: InterceptEntry;
30
- entry: EntryData;
31
- } | null, localRouteName: string, pathname: string, stale?: boolean, chain?: readonly EntryData[]) => Promise<{
32
- segments: ResolvedSegment[];
33
- matchedIds: string[];
34
- }>;
35
- findInterceptForRoute: (targetRouteKey: string, fromEntry: EntryData | null, selectorContext?: InterceptSelectorContext | null, isAction?: boolean) => {
36
- intercept: InterceptEntry;
37
- entry: EntryData;
38
- } | null;
39
- resolveInterceptEntry: (interceptEntry: InterceptEntry, parentEntry: EntryData, params: Record<string, string>, context: HandlerContext<any, TEnv>, belongsToRoute?: boolean, revalidationContext?: any, options?: {
40
- background?: boolean;
41
- }) => Promise<ResolvedSegment[]>;
42
- resolveInterceptLoadersOnly: (interceptEntry: InterceptEntry, parentEntry: EntryData, context: HandlerContext<any, TEnv>, belongsToRoute: boolean, revalidationContext: RevalidationContext) => Promise<ResolvedSegment[]>;
43
- }
2
+ import type { RouterContext } from "./router-context.js";
3
+ import { findInterceptForRoute as _findInterceptForRoute } from "./intercept-resolution.js";
4
+ /** The resolvers RouterContext exposes, with the router's deps bound. */
5
+ export type SegmentWrappers<TEnv = any> = Pick<RouterContext<TEnv>, "resolveAllSegments" | "resolveInterceptEntry"> & Required<Pick<RouterContext<TEnv>, "resolveLoadersOnly" | "buildEntryRevalidateMap" | "resolveInterceptLoadersOnly">> & {
6
+ /** Its own signature: a null selector context, isAction defaulting to false. */
7
+ findInterceptForRoute: typeof _findInterceptForRoute;
8
+ };
44
9
  /**
45
- * Create thin wrapper functions that bind segmentDeps to extracted
46
- * segment resolution and intercept resolution functions.
47
- *
48
- * These maintain the same signatures as the original inline functions
49
- * so that RouterContext and call sites don't need to change.
10
+ * Bind the router's segment deps into the extracted segment and intercept
11
+ * resolvers. Each gets a ResolutionPass: the caller's request-side input with
12
+ * the deps added here, once per call.
50
13
  */
51
- export declare function createSegmentWrappers<TEnv = any>(segmentDeps: SegmentResolutionDeps<TEnv>): SegmentWrappers<TEnv>;
14
+ export declare function createSegmentWrappers<TEnv = any>(deps: SegmentResolutionDeps<TEnv>): SegmentWrappers<TEnv>;
@@ -208,6 +208,8 @@ export declare function safeEmit(sink: TelemetrySink, event: TelemetryEvent): vo
208
208
  * Generated IDs use format "t-{base36}" to distinguish from header values.
209
209
  */
210
210
  export declare function getRequestId(request: Request): string;
211
+ /** Make `id` the id getRequestId returns for `request`. */
212
+ export declare function setRequestId(request: Request, id: string): void;
211
213
  /**
212
214
  * Built-in console sink that logs events in a structured format.
213
215
  * Designed as the default sink for development / debugging.
@@ -15,6 +15,16 @@ export type ActionContext = {
15
15
  actionUrl?: URL;
16
16
  actionResult?: any;
17
17
  formData?: FormData;
18
+ /**
19
+ * A thrown action's error segment (matchError), set on the action's
20
+ * revalidation (rsc/server-action.ts matchBoundaryRevalidation). The walk
21
+ * (resolveAllSegments) resolves every entry above the segment's outlet as on
22
+ * a success, emits the segment in the outlet's place and stops, so nothing
23
+ * at or below the outlet runs. The pass skips the prerender store
24
+ * (cache-lookup.ts): the evicted handler is under the cut. No revalidate()
25
+ * predicate sees it.
26
+ */
27
+ boundary?: ResolvedSegment;
18
28
  };
19
29
  export interface SegmentResolutionDeps<TEnv = any> {
20
30
  wrapLoaderPromise: <T>(promise: Promise<T>, entry: EntryData, segmentId: string, pathname: string, errorContext?: {
@@ -24,13 +34,13 @@ export interface SegmentResolutionDeps<TEnv = any> {
24
34
  params?: Record<string, string>;
25
35
  env?: TEnv;
26
36
  isPartial?: boolean;
27
- requestStartTime?: number;
28
37
  },
29
38
  /** An `ssr: false` loader on a document or capture render. */
30
39
  useDefaultErrorBoundary?: boolean) => Promise<LoaderDataResult<T>>;
31
40
  trackHandler: <T>(promise: Promise<T>, errorContext?: {
32
41
  segmentId?: string;
33
42
  segmentType?: string;
43
+ isPartial?: boolean;
34
44
  }) => Promise<T>;
35
45
  findNearestErrorBoundary: (entry: EntryData | null) => ReactNode | ErrorBoundaryHandler | null;
36
46
  findNearestNotFoundBoundary: (entry: EntryData | null) => ReactNode | NotFoundBoundaryHandler | null;
@@ -32,7 +32,7 @@ export declare function buildFullPayload(m: MatchResult, ctx: HandlerContext<any
32
32
  * visitor's URL. Any other render that shows the visitor's URL marks
33
33
  * `_payloadVisitorLocation`, and the document cache does not store it.
34
34
  */
35
- export declare function renderedLocation(reqCtx: Pick<RequestContext<any>, "_variables" | "_shellCaptureRun" | "_shellCaptureForVisitor" | "_documentCacheRender" | "_payloadVisitorLocation" | "res"> | undefined, url: URL): URL;
35
+ export declare function renderedLocation(reqCtx: Pick<RequestContext<any>, "_variables" | "_shellCaptureState" | "_documentCacheRender" | "_payloadVisitorLocation" | "res"> | undefined, url: URL): URL;
36
36
  /**
37
37
  * A payload's `pathname` (renderedLocation) and, when middleware rewrote the
38
38
  * request, `rewriteTarget`: the path and search the route rendered (the
@@ -63,4 +63,4 @@ export declare function payloadLocation(reqCtx: Parameters<typeof renderedLocati
63
63
  * default it marks `_payloadVisitorTheme`, and the document cache does not
64
64
  * store the response.
65
65
  */
66
- export declare function payloadInitialTheme(reqCtx: Pick<RequestContext<any>, "_themeConfig" | "_shellCaptureRun" | "_readTheme" | "_documentCacheRender" | "_payloadVisitorTheme" | "res">): Theme | undefined;
66
+ export declare function payloadInitialTheme(reqCtx: Pick<RequestContext<any>, "_themeConfig" | "_shellCaptureState" | "_readTheme" | "_documentCacheRender" | "_payloadVisitorTheme" | "res">): Theme | undefined;
@@ -6,11 +6,14 @@
6
6
  * RSC rendering) so they can be standalone modules without closure coupling.
7
7
  */
8
8
  import type { RangoInternal } from "../router/router-interfaces.js";
9
- import type { ErrorPhase } from "../types.js";
10
- import type { InvokeOnErrorContext } from "../router/error-handling.js";
11
9
  import type { RSCDependencies, LoadSSRModule } from "./types.js";
12
10
  import type { SSRStreamMode } from "../router/router-options.js";
13
- export interface HandlerContext<TEnv = unknown> {
11
+ import type { RequestStageContext } from "./request-stages.js";
12
+ /**
13
+ * Extends what the request stages (rsc/request-stages.ts) call back into, so
14
+ * the handler hands this one bundle to them as well.
15
+ */
16
+ export interface HandlerContext<TEnv = unknown> extends RequestStageContext<TEnv> {
14
17
  router: RangoInternal<TEnv, any>;
15
18
  /**
16
19
  * The router's DOCUMENT version (router-versions.ts): payload metadata, the
@@ -26,9 +29,6 @@ export interface HandlerContext<TEnv = unknown> {
26
29
  decodeAction: RSCDependencies["decodeAction"];
27
30
  decodeFormState: RSCDependencies["decodeFormState"];
28
31
  loadSSRModule: LoadSSRModule;
29
- callOnError: (error: unknown, phase: ErrorPhase, context: InvokeOnErrorContext<TEnv>) => void;
30
- getRequiredRouteMap: () => Record<string, string>;
31
- createRedirectFlightResponse: (redirectUrl: string, locationState?: Record<string, unknown>, external?: boolean) => Response;
32
32
  /**
33
33
  * Resolve the SSR stream mode for a given request.
34
34
  * Returns "stream" when no resolveStreaming callback is configured.
@@ -1,10 +1,6 @@
1
1
  /**
2
- * Shared serialization for `json()` response-route results.
3
- *
4
- * Kept in its own lightweight module (depends only on `errors.js`) so the
5
- * `dispatch()` testing primitive can import it WITHOUT dragging in
6
- * `response-route-handler.ts`'s heavy runtime graph, which transitively reaches
7
- * a Vite virtual module and breaks a plain (non-Vite) vitest import.
2
+ * Serialization for `json()` response-route results (depends only on
3
+ * `errors.js`).
8
4
  */
9
5
  /**
10
6
  * Serialize a `json()` response-route result, rejecting a nested unresolved
@@ -13,8 +9,8 @@
13
9
  * the RSC pipeline awaits nested promises but this path does not. Throwing
14
10
  * `RESPONSE_NOT_SERIALIZABLE` makes the failure loud.
15
11
  *
16
- * Shared by the production response-route handler and the `dispatch()` testing
17
- * primitive so a `dispatch` json test of a forgotten await fails exactly where
18
- * production 500s, instead of going green.
12
+ * The `dispatch()` testing primitive runs the same response-route handler, so
13
+ * a `dispatch` json test of a forgotten await fails exactly where production
14
+ * 500s, instead of going green.
19
15
  */
20
16
  export declare function stringifyJsonRouteResult(result: unknown): string;