@rangojs/router 0.16.0 → 0.18.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 (309) hide show
  1. package/README.md +255 -89
  2. package/dist/testing/vitest.js +252 -0
  3. package/dist/types/browser/cookie-name.d.ts +6 -0
  4. package/dist/types/browser/history-state.d.ts +16 -0
  5. package/dist/types/browser/navigation-transaction.d.ts +6 -0
  6. package/dist/types/browser/partial-update.d.ts +11 -0
  7. package/dist/types/browser/react/ScrollRestoration.d.ts +6 -6
  8. package/dist/types/browser/rsc-router.d.ts +1 -1
  9. package/dist/types/browser/scroll-restoration.d.ts +7 -0
  10. package/dist/types/cache/cache-exec-scope.d.ts +18 -1
  11. package/dist/types/cache/cache-key-utils.d.ts +17 -2
  12. package/dist/types/cache/cache-policy.d.ts +17 -0
  13. package/dist/types/cache/cache-scope.d.ts +132 -19
  14. package/dist/types/cache/cache-tag.d.ts +92 -7
  15. package/dist/types/cache/cf/cf-base64.d.ts +6 -0
  16. package/dist/types/cache/cf/cf-cache-constants.d.ts +11 -0
  17. package/dist/types/cache/cf/cf-cache-store.d.ts +185 -44
  18. package/dist/types/cache/cf/cf-cache-types.d.ts +31 -4
  19. package/dist/types/cache/cf/cf-shell-frame.d.ts +95 -0
  20. package/dist/types/cache/cf/cf-tag-marker-memo.d.ts +34 -0
  21. package/dist/types/cache/handle-capture.d.ts +41 -3
  22. package/dist/types/cache/handle-snapshot.d.ts +54 -13
  23. package/dist/types/cache/index.d.ts +1 -0
  24. package/dist/types/cache/isolate-tag-memo.d.ts +149 -0
  25. package/dist/types/cache/segment-codec.d.ts +10 -3
  26. package/dist/types/cache/shell-memo.d.ts +178 -0
  27. package/dist/types/cache/shell-snapshot.d.ts +110 -21
  28. package/dist/types/cache/tag-invalidation.d.ts +30 -3
  29. package/dist/types/cache/taint.d.ts +1 -1
  30. package/dist/types/cache/types.d.ts +220 -44
  31. package/dist/types/cache/vercel/vercel-cache-store.d.ts +111 -13
  32. package/dist/types/client.d.ts +4 -4
  33. package/dist/types/client.rsc.d.ts +4 -5
  34. package/dist/types/components/DefaultDocument.d.ts +5 -2
  35. package/dist/types/context-var.d.ts +6 -5
  36. package/dist/types/escape-script.d.ts +1 -1
  37. package/dist/types/handles/MetaTags.d.ts +5 -4
  38. package/dist/types/handles/Scripts.d.ts +8 -7
  39. package/dist/types/handles/meta.d.ts +2 -2
  40. package/dist/types/handles/script.d.ts +17 -16
  41. package/dist/types/href-client.d.ts +1 -1
  42. package/dist/types/html.d.ts +12 -0
  43. package/dist/types/index.d.ts +1 -1
  44. package/dist/types/index.rsc.d.ts +3 -2
  45. package/dist/types/loader-store.d.ts +7 -4
  46. package/dist/types/prerender/build-shell-capture.d.ts +11 -4
  47. package/dist/types/reverse.d.ts +36 -4
  48. package/dist/types/route-definition/dsl-helpers.d.ts +3 -3
  49. package/dist/types/route-definition/helpers-types.d.ts +33 -9
  50. package/dist/types/route-definition/resolve-handler-use.d.ts +23 -1
  51. package/dist/types/route-types.d.ts +1 -1
  52. package/dist/types/router/debug-manifest.d.ts +3 -2
  53. package/dist/types/router/error-handling.d.ts +20 -0
  54. package/dist/types/router/handler-context.d.ts +6 -0
  55. package/dist/types/router/instrument.d.ts +8 -0
  56. package/dist/types/router/match-middleware/background-revalidation.d.ts +46 -5
  57. package/dist/types/router/middleware-types.d.ts +9 -3
  58. package/dist/types/router/router-context.d.ts +3 -1
  59. package/dist/types/router/router-interfaces.d.ts +24 -2
  60. package/dist/types/router/router-options.d.ts +8 -5
  61. package/dist/types/router/segment-resolution/fresh.d.ts +10 -0
  62. package/dist/types/router/segment-resolution/loader-cache.d.ts +66 -1
  63. package/dist/types/router/segment-resolution/loader-mask.d.ts +9 -19
  64. package/dist/types/router/segment-resolution/loader-snapshot.d.ts +23 -12
  65. package/dist/types/router/segment-resolution/mask-nested.d.ts +67 -26
  66. package/dist/types/router/segment-resolution/revalidation.d.ts +6 -2
  67. package/dist/types/router/segment-wrappers.d.ts +1 -1
  68. package/dist/types/rsc/full-payload.d.ts +14 -0
  69. package/dist/types/rsc/handler.d.ts +1 -1
  70. package/dist/types/rsc/response-route-handler.d.ts +1 -1
  71. package/dist/types/rsc/rsc-rendering.d.ts +1 -2
  72. package/dist/types/rsc/shell-build-manifest.d.ts +8 -0
  73. package/dist/types/rsc/shell-capture-constants.d.ts +61 -6
  74. package/dist/types/rsc/shell-capture.d.ts +151 -19
  75. package/dist/types/rsc/shell-serve.d.ts +140 -17
  76. package/dist/types/rsc/ssr-setup.d.ts +6 -6
  77. package/dist/types/rsc/types.d.ts +17 -0
  78. package/dist/types/server/context.d.ts +139 -15
  79. package/dist/types/server/cookie-store.d.ts +21 -0
  80. package/dist/types/server/handle-store.d.ts +26 -2
  81. package/dist/types/server/request-context.d.ts +182 -53
  82. package/dist/types/ssr/index.d.ts +24 -0
  83. package/dist/types/ssr/ssr-root.d.ts +9 -8
  84. package/dist/types/static-handler.d.ts +4 -1
  85. package/dist/types/testing/flight.entry.d.ts +7 -0
  86. package/dist/types/testing/generated-routes.d.ts +2 -2
  87. package/dist/types/testing/internal/context.d.ts +1 -1
  88. package/dist/types/testing/render-route.d.ts +32 -6
  89. package/dist/types/testing/run-loader.d.ts +18 -3
  90. package/dist/types/testing/serve-shell-request.d.ts +132 -0
  91. package/dist/types/testing/shell-status.d.ts +23 -10
  92. package/dist/types/testing/vitest-stubs/plugin-rsc.d.ts +28 -5
  93. package/dist/types/testing/vitest.d.ts +35 -1
  94. package/dist/types/theme/ThemeScript.d.ts +3 -3
  95. package/dist/types/types/cache-types.d.ts +14 -10
  96. package/dist/types/types/handler-context.d.ts +28 -1
  97. package/dist/types/types/loader-types.d.ts +8 -6
  98. package/dist/types/urls/pattern-types.d.ts +22 -18
  99. package/dist/types/urls/response-types.d.ts +3 -12
  100. package/dist/types/use-loader.d.ts +12 -3
  101. package/dist/types/vite/plugins/use-cache-transform.d.ts +33 -2
  102. package/dist/types/vite/rango.d.ts +1 -1
  103. package/dist/types/vite/router-discovery.d.ts +29 -2
  104. package/dist/vite/index.js +1420 -1348
  105. package/package.json +2 -2
  106. package/skills/api-client/SKILL.md +22 -10
  107. package/skills/breadcrumbs/SKILL.md +75 -22
  108. package/skills/bundle-analysis/SKILL.md +22 -22
  109. package/skills/cache-guide/SKILL.md +306 -124
  110. package/skills/caching/SKILL.md +530 -98
  111. package/skills/catalog.json +16 -16
  112. package/skills/client-urls/SKILL.md +65 -38
  113. package/skills/cloudflare/SKILL.md +87 -20
  114. package/skills/cloudflare/references/d1-and-local-dev.md +15 -2
  115. package/skills/cloudflare/references/streaming-and-deploy.md +10 -3
  116. package/skills/cloudflare/references/webhooks-and-crypto.md +9 -2
  117. package/skills/comparison/SKILL.md +5 -0
  118. package/skills/comparison/references/framework-comparison.md +75 -57
  119. package/skills/composability/SKILL.md +38 -29
  120. package/skills/css/SKILL.md +10 -13
  121. package/skills/debug-manifest/SKILL.md +74 -31
  122. package/skills/defer-hydration/SKILL.md +52 -31
  123. package/skills/deployment-caching/SKILL.md +11 -3
  124. package/skills/document-cache/SKILL.md +98 -28
  125. package/skills/fonts/SKILL.md +16 -8
  126. package/skills/handler-use/SKILL.md +55 -17
  127. package/skills/hooks/SKILL.md +28 -20
  128. package/skills/hooks/data.md +23 -3
  129. package/skills/hooks/handle-and-actions.md +34 -17
  130. package/skills/hooks/navigation.md +39 -10
  131. package/skills/hooks/outlets.md +13 -6
  132. package/skills/hooks/state.md +39 -15
  133. package/skills/hooks/urls.md +7 -5
  134. package/skills/host-router/SKILL.md +64 -12
  135. package/skills/i18n/SKILL.md +60 -34
  136. package/skills/intercept/SKILL.md +161 -26
  137. package/skills/layout/SKILL.md +106 -50
  138. package/skills/links/SKILL.md +51 -19
  139. package/skills/loader/SKILL.md +386 -128
  140. package/skills/middleware/SKILL.md +129 -26
  141. package/skills/migrate-nextjs/SKILL.md +156 -70
  142. package/skills/migrate-nextjs/backend-host-swap.md +5 -2
  143. package/skills/migrate-react-router/SKILL.md +51 -39
  144. package/skills/migrate-react-router/component-migration.md +28 -7
  145. package/skills/migrate-react-router/data-and-actions.md +21 -6
  146. package/skills/migrate-react-router/route-mapping.md +19 -10
  147. package/skills/mime-routes/SKILL.md +12 -7
  148. package/skills/observability/SKILL.md +92 -14
  149. package/skills/parallel/SKILL.md +88 -47
  150. package/skills/ppr/SKILL.md +866 -379
  151. package/skills/prerender/SKILL.md +210 -108
  152. package/skills/rango/SKILL.md +115 -65
  153. package/skills/react-compiler/SKILL.md +6 -5
  154. package/skills/response-routes/SKILL.md +133 -25
  155. package/skills/route/SKILL.md +170 -60
  156. package/skills/router-setup/SKILL.md +420 -240
  157. package/skills/scripts/SKILL.md +39 -21
  158. package/skills/server-actions/SKILL.md +231 -59
  159. package/skills/shell-manifest/SKILL.md +28 -14
  160. package/skills/streams-and-websockets/SKILL.md +32 -14
  161. package/skills/tailwind/SKILL.md +37 -33
  162. package/skills/testing/SKILL.md +73 -33
  163. package/skills/testing/cache-prerender.md +60 -33
  164. package/skills/testing/client-components.md +59 -6
  165. package/skills/testing/e2e-parity.md +12 -2
  166. package/skills/testing/flight.md +19 -11
  167. package/skills/testing/handles.md +8 -5
  168. package/skills/testing/loader.md +26 -6
  169. package/skills/testing/middleware.md +8 -3
  170. package/skills/testing/predicates.md +120 -0
  171. package/skills/testing/render-handler.md +70 -22
  172. package/skills/testing/response-routes.md +11 -4
  173. package/skills/testing/reverse-and-types.md +20 -14
  174. package/skills/testing/serve-shell-request.md +188 -0
  175. package/skills/testing/server-actions.md +12 -3
  176. package/skills/testing/server-tree.md +9 -0
  177. package/skills/testing/setup.md +9 -5
  178. package/skills/theme/SKILL.md +155 -30
  179. package/skills/typesafety/SKILL.md +20 -9
  180. package/skills/typesafety/env-and-bindings.md +137 -50
  181. package/skills/typesafety/generated-files-and-cli.md +26 -14
  182. package/skills/typesafety/params-and-search.md +44 -19
  183. package/skills/typesafety/route-types.md +50 -14
  184. package/skills/use-cache/SKILL.md +224 -83
  185. package/skills/vercel/SKILL.md +35 -13
  186. package/skills/view-transitions/SKILL.md +42 -21
  187. package/src/__augment-tests__/augmented.check.ts +26 -1
  188. package/src/browser/cookie-name.ts +23 -0
  189. package/src/browser/history-state.ts +23 -0
  190. package/src/browser/index.ts +2 -2
  191. package/src/browser/navigation-bridge.ts +3 -4
  192. package/src/browser/navigation-transaction.ts +22 -2
  193. package/src/browser/partial-update.ts +35 -25
  194. package/src/browser/react/ScrollRestoration.tsx +6 -6
  195. package/src/browser/rsc-router.tsx +6 -1
  196. package/src/browser/scroll-restoration.ts +53 -6
  197. package/src/cache/cache-exec-scope.ts +37 -4
  198. package/src/cache/cache-key-utils.ts +23 -8
  199. package/src/cache/cache-policy.ts +22 -0
  200. package/src/cache/cache-runtime.ts +264 -68
  201. package/src/cache/cache-scope.ts +419 -43
  202. package/src/cache/cache-tag.ts +375 -11
  203. package/src/cache/cf/cf-base64.ts +36 -4
  204. package/src/cache/cf/cf-cache-constants.ts +12 -0
  205. package/src/cache/cf/cf-cache-store.ts +990 -348
  206. package/src/cache/cf/cf-cache-types.ts +32 -4
  207. package/src/cache/cf/cf-shell-frame.ts +258 -0
  208. package/src/cache/cf/cf-tag-marker-memo.ts +143 -39
  209. package/src/cache/document-cache.ts +15 -0
  210. package/src/cache/handle-capture.ts +90 -10
  211. package/src/cache/handle-snapshot.ts +133 -28
  212. package/src/cache/index.ts +2 -0
  213. package/src/cache/isolate-tag-memo.ts +308 -0
  214. package/src/cache/segment-codec.ts +26 -7
  215. package/src/cache/shell-memo.ts +341 -0
  216. package/src/cache/shell-snapshot.ts +217 -27
  217. package/src/cache/tag-invalidation.ts +108 -22
  218. package/src/cache/taint.ts +1 -1
  219. package/src/cache/types.ts +225 -44
  220. package/src/cache/vercel/vercel-cache-store.ts +545 -61
  221. package/src/client.rsc.tsx +10 -9
  222. package/src/client.tsx +5 -4
  223. package/src/components/DefaultDocument.tsx +7 -2
  224. package/src/context-var.ts +6 -5
  225. package/src/escape-script.ts +1 -1
  226. package/src/handles/MetaTags.tsx +13 -11
  227. package/src/handles/Scripts.tsx +11 -10
  228. package/src/handles/meta.ts +2 -2
  229. package/src/handles/script.ts +17 -16
  230. package/src/href-client.ts +1 -1
  231. package/src/html.ts +12 -0
  232. package/src/index.rsc.ts +5 -0
  233. package/src/index.ts +1 -0
  234. package/src/loader-store.ts +7 -4
  235. package/src/prerender/build-shell-capture.ts +73 -22
  236. package/src/reverse.ts +44 -4
  237. package/src/route-definition/dsl-helpers.ts +121 -33
  238. package/src/route-definition/helpers-types.ts +33 -9
  239. package/src/route-definition/resolve-handler-use.ts +121 -6
  240. package/src/route-types.ts +0 -3
  241. package/src/router/debug-manifest.ts +10 -2
  242. package/src/router/error-handling.ts +51 -15
  243. package/src/router/handler-context.ts +71 -28
  244. package/src/router/instrument.ts +54 -2
  245. package/src/router/intercept-resolution.ts +141 -43
  246. package/src/router/loader-resolution.ts +115 -39
  247. package/src/router/match-api.ts +40 -26
  248. package/src/router/match-handlers.ts +5 -0
  249. package/src/router/match-middleware/background-revalidation.ts +161 -96
  250. package/src/router/match-middleware/cache-lookup.ts +110 -10
  251. package/src/router/match-middleware/cache-store.ts +48 -101
  252. package/src/router/middleware-types.ts +9 -6
  253. package/src/router/middleware.ts +75 -13
  254. package/src/router/prerender-match.ts +59 -19
  255. package/src/router/route-snapshot.ts +11 -1
  256. package/src/router/router-context.ts +2 -0
  257. package/src/router/router-interfaces.ts +25 -2
  258. package/src/router/router-options.ts +8 -5
  259. package/src/router/segment-resolution/fresh.ts +62 -21
  260. package/src/router/segment-resolution/helpers.ts +4 -2
  261. package/src/router/segment-resolution/loader-cache.ts +407 -76
  262. package/src/router/segment-resolution/loader-mask.ts +12 -22
  263. package/src/router/segment-resolution/loader-snapshot.ts +208 -56
  264. package/src/router/segment-resolution/mask-nested.ts +138 -44
  265. package/src/router/segment-resolution/revalidation.ts +61 -16
  266. package/src/router/segment-wrappers.ts +4 -0
  267. package/src/rsc/full-payload.ts +25 -1
  268. package/src/rsc/handler.ts +14 -2
  269. package/src/rsc/progressive-enhancement.ts +3 -2
  270. package/src/rsc/render-pipeline.ts +3 -0
  271. package/src/rsc/response-cache-serve.ts +9 -6
  272. package/src/rsc/response-route-handler.ts +11 -3
  273. package/src/rsc/rsc-rendering.ts +608 -225
  274. package/src/rsc/shell-build-manifest.ts +27 -9
  275. package/src/rsc/shell-capture-constants.ts +73 -6
  276. package/src/rsc/shell-capture.ts +1068 -296
  277. package/src/rsc/shell-serve.ts +316 -34
  278. package/src/rsc/ssr-setup.ts +14 -8
  279. package/src/rsc/types.ts +18 -0
  280. package/src/server/context.ts +300 -32
  281. package/src/server/cookie-store.ts +87 -61
  282. package/src/server/handle-store.ts +232 -7
  283. package/src/server/request-context.ts +297 -67
  284. package/src/ssr/index.tsx +136 -44
  285. package/src/ssr/ssr-root.tsx +9 -8
  286. package/src/static-handler.ts +4 -1
  287. package/src/testing/flight-runtime.d.ts +21 -0
  288. package/src/testing/flight.entry.ts +14 -0
  289. package/src/testing/generated-routes.ts +2 -2
  290. package/src/testing/internal/context.ts +1 -1
  291. package/src/testing/internal/flight-client-globals.ts +7 -5
  292. package/src/testing/render-route.tsx +85 -24
  293. package/src/testing/run-loader.ts +68 -6
  294. package/src/testing/serve-shell-request.ts +378 -0
  295. package/src/testing/shell-status.ts +34 -12
  296. package/src/testing/vitest-stubs/plugin-rsc.ts +123 -20
  297. package/src/testing/vitest.ts +62 -1
  298. package/src/theme/ThemeProvider.tsx +7 -6
  299. package/src/theme/ThemeScript.tsx +3 -3
  300. package/src/types/cache-types.ts +14 -10
  301. package/src/types/handler-context.ts +28 -1
  302. package/src/types/loader-types.ts +8 -6
  303. package/src/urls/pattern-types.ts +22 -18
  304. package/src/urls/response-types.ts +3 -23
  305. package/src/use-loader.tsx +12 -3
  306. package/src/vite/discovery/shell-prerender-phase.ts +9 -0
  307. package/src/vite/plugins/use-cache-transform.ts +118 -74
  308. package/src/vite/rango.ts +7 -3
  309. package/src/vite/router-discovery.ts +14 -4
@@ -164,8 +164,10 @@ export interface RangoOptions<TEnv = any> {
164
164
  *
165
165
  * Must be a client component ("use client") that accepts { children }.
166
166
  *
167
- * If not provided, a default document with basic HTML structure is used:
168
- * `<html><head><meta charset/viewport></head><body>{children}</body></html>`
167
+ * If not provided, a default document is used: `Html.Meta` and `Html.Scripts`
168
+ * in `<head>`, `Html.Scripts position="body"` before `{children}` and
169
+ * `Html.ScrollRestoration` after it. Pass your own to set `getKey` or to
170
+ * leave back/forward scrolling to the browser.
169
171
  *
170
172
  * @example
171
173
  * ```typescript
@@ -201,7 +203,8 @@ export interface RangoOptions<TEnv = any> {
201
203
 
202
204
  /**
203
205
  * Default not-found boundary fallback used when no notFoundBoundary is defined in the route tree
204
- * If not provided, DataNotFoundError will be treated as a regular error
206
+ * If not provided, notFound() renders the `notFound` option, else a plain
207
+ * `<h1>Not Found</h1>` (status 404)
205
208
  */
206
209
  defaultNotFoundBoundary?: ReactNode | NotFoundBoundaryHandler;
207
210
 
@@ -211,7 +214,7 @@ export interface RangoOptions<TEnv = any> {
211
214
  * This is rendered within your document/app shell with a 404 status code.
212
215
  * Use this for a custom 404 page that maintains your app's look and feel.
213
216
  *
214
- * If not provided, a default "Page not found" component is rendered.
217
+ * If not provided, a plain `<h1>Not Found</h1>` is rendered.
215
218
  *
216
219
  * Can be a static ReactNode or a function receiving the pathname.
217
220
  *
@@ -368,7 +371,7 @@ export interface RangoOptions<TEnv = any> {
368
371
  * When provided, enables:
369
372
  * - ctx.theme and ctx.setTheme() in route handlers
370
373
  * - useTheme() hook for client components
371
- * - FOUC prevention via inline script in MetaTags
374
+ * - FOUC prevention via inline script in `<Html.Meta />`
372
375
  * - Automatic ThemeProvider wrapping in NavigationProvider
373
376
  *
374
377
  * @example
@@ -37,7 +37,7 @@ import { applyViewTransitionDefault } from "./view-transition-default.js";
37
37
  import { _getRequestContext } from "../../server/request-context.js";
38
38
  import { getRouterContext } from "../router-context.js";
39
39
  import { observeStreamedHandler } from "./streamed-handler-telemetry.js";
40
- import { observeHandler } from "../instrument.js";
40
+ import { observeSegmentHandler } from "../instrument.js";
41
41
  import {
42
42
  track,
43
43
  RangoContext,
@@ -120,12 +120,8 @@ export async function resolveLoaders<TEnv>(
120
120
  // loading-disabled entries consult it), so normal requests are unchanged.
121
121
  const emitStreaming = !loadingDisabled || isShellCaptureActive();
122
122
 
123
- // PPR lane decision for this entry's loaders (loader-container-bake): an
124
- // entry WITHOUT renderable loading() puts its loaders on the BAKE lane —
125
- // executed at capture (container bakes, nested pending promises hole at the
126
- // consumer's Suspense) and overlay-pinned from the shell snapshot on a HIT.
127
- // Renderable loading() keeps the LIVE lane (masked at capture, always
128
- // fresh). Computed per entry; resolveLoaderData applies the policy.
123
+ // PPR bake/seed key input only; lane rule: see resolveLoaderData
124
+ // (loader-cache.ts). Unflagged loaders mask at capture regardless of the key.
129
125
  const bakeLane = !entryLoadingMasksLoaders(entry.loading);
130
126
 
131
127
  // Error context for wrapLoaderPromise: without it, a throwing DSL loader never
@@ -146,9 +142,9 @@ export async function resolveLoaders<TEnv>(
146
142
  // barrier), and the loader body can call rendered() before the await below
147
143
  // is reached.
148
144
  //
149
- // Shell-capture renders await too: flagged loaders BAKE at capture
150
- // (loader-mask masks only LIVE-lane loaders). Capture must await them so
151
- // bake-lane handle pushes land in the prelude.
145
+ // Shell-capture renders await too: flagged loaders execute at capture
146
+ // (lane rule: see resolveLoaderData, loader-cache.ts), so their handle
147
+ // pushes must land in the prelude.
152
148
  const awaitedIndices = registerAwaitBeforeFlushIds(loaderEntries);
153
149
 
154
150
  // Streaming loaders: promises kick off now, settle during RSC serialization.
@@ -177,9 +173,7 @@ export async function resolveLoaders<TEnv>(
177
173
  // bakes at capture regardless of the entry's loading() lane
178
174
  // (loader-cache.ts capture branch) and its HIT-tail seed
179
175
  // overlay needs the same key.
180
- bakeLane || loaderEntry.awaitBeforeFlush === true
181
- ? segmentId
182
- : null,
176
+ bakeLane || loaderEntry.bake === true ? segmentId : null,
183
177
  ),
184
178
  ),
185
179
  entry,
@@ -227,7 +221,7 @@ export async function resolveLoaders<TEnv>(
227
221
  loaderEntry,
228
222
  ctx,
229
223
  ctx.pathname,
230
- bakeLane || loaderEntry.awaitBeforeFlush === true ? segmentId : null,
224
+ bakeLane || loaderEntry.bake === true ? segmentId : null,
231
225
  ),
232
226
  ),
233
227
  entry,
@@ -276,6 +270,16 @@ export interface ResolveSegmentOptions {
276
270
  * so error boundaries keep catching at request time.
277
271
  */
278
272
  throwOnError?: boolean;
273
+ /**
274
+ * The matched route's full entry chain. resolveAllSegments defaults it to
275
+ * its `entries`; withCacheLookup passes it when it resolves only the entries
276
+ * above a cache() boundary. An orphan list can hold an entry of the chain: a
277
+ * bare cache() marker sits in its layout's layout[] (it wraps that layout's
278
+ * routes) and is the parent of the routes after it. For those routes it
279
+ * resolves once, as a chain entry, below the cache() header latch (issue
280
+ * #918: resolved twice on a MISS, once and discarded on a HIT).
281
+ */
282
+ chain?: readonly EntryData[];
279
283
  }
280
284
 
281
285
  /**
@@ -349,6 +353,7 @@ export async function resolveSegment<TEnv>(
349
353
  }
350
354
 
351
355
  for (const orphan of entry.layout) {
356
+ if (options?.chain?.includes(orphan)) continue;
352
357
  const orphanSegments = await resolveOrphanLayout(
353
358
  orphan,
354
359
  params,
@@ -389,7 +394,7 @@ export async function resolveSegment<TEnv>(
389
394
  const doneRouteHandler = track(`handler:${entry.id}`, 2);
390
395
  if (entry.loading) {
391
396
  const result = handleHandlerResult(
392
- observeHandler(entry.id, handler, context),
397
+ observeSegmentHandler(entry.shortCode, entry.id, handler, context),
393
398
  );
394
399
  if (result instanceof Promise) {
395
400
  warnOnStreamedResponse(result, entry.id);
@@ -413,7 +418,12 @@ export async function resolveSegment<TEnv>(
413
418
  }
414
419
  } else {
415
420
  component = handleHandlerResult(
416
- await observeHandler(entry.id, handler, context),
421
+ await observeSegmentHandler(
422
+ entry.shortCode,
423
+ entry.id,
424
+ handler,
425
+ context,
426
+ ),
417
427
  );
418
428
  doneRouteHandler();
419
429
  }
@@ -578,6 +588,26 @@ export async function resolveOrphanLayout<TEnv>(
578
588
  resolvedParallelEntries.add(parallelEntry.id);
579
589
  }
580
590
 
591
+ // Routeless entries nested in this one (a layout() after a bare cache()
592
+ // marker, a wrapper inside a routeless wrapper) wrap the same content one
593
+ // level deeper. Issue #918: they were never rendered. None is in the
594
+ // matched chain: that would put this orphan in it, and resolveSegment
595
+ // skips those.
596
+ for (const nested of orphan.layout) {
597
+ segments.push(
598
+ ...(await resolveOrphanLayout(
599
+ nested,
600
+ params,
601
+ context,
602
+ loaderPromises,
603
+ belongsToRoute,
604
+ deps,
605
+ options,
606
+ routeKey,
607
+ )),
608
+ );
609
+ }
610
+
581
611
  return segments;
582
612
  }
583
613
 
@@ -643,7 +673,12 @@ export async function resolveParallelEntry<TEnv>(
643
673
  if (hasLoadingFallback) {
644
674
  const result =
645
675
  typeof handler === "function"
646
- ? observeHandler(`${parallelEntry.id}.${slot}`, handler, context)
676
+ ? observeSegmentHandler(
677
+ `${parentShortCode}.${slot}`,
678
+ `${parallelEntry.id}.${slot}`,
679
+ handler,
680
+ context,
681
+ )
647
682
  : handler;
648
683
  if (result instanceof Promise) {
649
684
  result.finally(doneParallelHandler).catch(() => {});
@@ -667,7 +702,8 @@ export async function resolveParallelEntry<TEnv>(
667
702
  } else {
668
703
  component =
669
704
  typeof handler === "function"
670
- ? await observeHandler(
705
+ ? await observeSegmentHandler(
706
+ `${parentShortCode}.${slot}`,
671
707
  `${parallelEntry.id}.${slot}`,
672
708
  handler,
673
709
  context,
@@ -736,6 +772,10 @@ export async function resolveAllSegments<TEnv>(
736
772
  ): Promise<ResolvedSegment[]> {
737
773
  const allSegments: ResolvedSegment[] = [];
738
774
  const seenIds = new Set<string>();
775
+ const segmentOptions: ResolveSegmentOptions = {
776
+ ...options,
777
+ chain: options?.chain ?? entries,
778
+ };
739
779
 
740
780
  // ppr routes are document-scoped cached territory: the whole chain (root
741
781
  // layout down to the page) bakes into the shared shell, so the header-write
@@ -760,8 +800,9 @@ export async function resolveAllSegments<TEnv>(
760
800
  // Set ALS flag when entering a cache() boundary so that ctx.get()
761
801
  // can guard non-cacheable variable reads. Also latch the header-write
762
802
  // scope (response-level side effects — headers/cookies/status).
763
- // Persists for all descendant entries.
764
- if (entry.type === "cache") {
803
+ // Persists for all descendant entries. A route entry carries `cache` when
804
+ // cache() is among its own children (dsl-helpers.ts cache()).
805
+ if (entry.cache) {
765
806
  const store = RangoContext.getStore();
766
807
  if (store) store.insideCacheScope = true;
767
808
  latchCachedHeaderScope("cache", routeKey);
@@ -779,7 +820,7 @@ export async function resolveAllSegments<TEnv>(
779
820
  loaderPromises,
780
821
  deps,
781
822
  false,
782
- options,
823
+ segmentOptions,
783
824
  ),
784
825
  (seg) => [seg],
785
826
  deps,
@@ -29,7 +29,7 @@ import type {
29
29
  import type { SegmentResolutionDeps } from "../types.js";
30
30
  import { debugLog } from "../logging.js";
31
31
  import { tryStaticLookup } from "./static-store.js";
32
- import { observeHandler } from "../instrument.js";
32
+ import { observeSegmentHandler } from "../instrument.js";
33
33
  import type { TelemetrySink } from "../telemetry.js";
34
34
  import { resolveSink, safeEmit, getRequestId } from "../telemetry.js";
35
35
 
@@ -175,7 +175,9 @@ export async function resolveLayoutComponent<TEnv>(
175
175
  // by track("handler:<id>") at the call site). handleHandlerResult stays OUTSIDE
176
176
  // the span so a handler that returns a Response (redirect control flow, which it
177
177
  // rethrows) is not recorded as a span error — mirrors the route-handler sites.
178
- return handleHandlerResult(await observeHandler(entry.id, handler, context));
178
+ return handleHandlerResult(
179
+ await observeSegmentHandler(entry.shortCode, entry.id, handler, context),
180
+ );
179
181
  }
180
182
 
181
183
  // ---------------------------------------------------------------------------