@rangojs/router 0.34.1 → 0.35.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 (95) hide show
  1. package/README.md +1 -1
  2. package/dist/bin/{chunk-4HHFQSDC.js → chunk-3CQXDX3A.js} +5 -5
  3. package/dist/bin/{client-urls-projection-4Q5EQDAL.js → client-urls-projection-2GBDM5YK.js} +1 -1
  4. package/dist/bin/rango.js +1 -1
  5. package/dist/bin/{runtime-discovery-RY6NMQM3.js → runtime-discovery-PA3V3IFQ.js} +2 -2
  6. package/dist/bin/{temp-rsc-server-F7AHOPV4.js → temp-rsc-server-WDXEHDY7.js} +2 -2
  7. package/dist/types/cache/shell-snapshot.d.ts +1 -1
  8. package/dist/types/cache/types.d.ts +1 -1
  9. package/dist/types/client-urls/server-projection.d.ts +1 -1
  10. package/dist/types/client-urls/types.d.ts +6 -6
  11. package/dist/types/decode-loader-results.d.ts +1 -1
  12. package/dist/types/errors.d.ts +3 -3
  13. package/dist/types/handles/meta.d.ts +2 -2
  14. package/dist/types/loader-store.d.ts +1 -1
  15. package/dist/types/outlet-context.d.ts +1 -1
  16. package/dist/types/route-definition/helpers-types.d.ts +5 -5
  17. package/dist/types/router/loader-resolution.d.ts +1 -1
  18. package/dist/types/router/segment-resolution/loader-cache.d.ts +7 -7
  19. package/dist/types/router/types.d.ts +1 -1
  20. package/dist/types/rsc/shell-capture-constants.d.ts +2 -2
  21. package/dist/types/server/context.d.ts +3 -3
  22. package/dist/types/server/request-context.d.ts +1 -1
  23. package/dist/types/ssr/index.d.ts +1 -1
  24. package/dist/types/ssr/ssr-root.d.ts +1 -1
  25. package/dist/types/ssr-suspension-warning.d.ts +1 -1
  26. package/dist/types/types/loader-types.d.ts +19 -19
  27. package/dist/types/types/segments.d.ts +2 -2
  28. package/dist/types/urls/path-helper-types.d.ts +4 -4
  29. package/dist/types/urls/pattern-types.d.ts +1 -1
  30. package/dist/types/vite/plugin-types.d.ts +1 -1
  31. package/dist/vite/index.js +7 -7
  32. package/package.json +1 -1
  33. package/skills/app-structure/e-commerce.md +1 -1
  34. package/skills/breadcrumbs/SKILL.md +5 -5
  35. package/skills/cache-guide/SKILL.md +4 -4
  36. package/skills/caching/SKILL.md +1 -1
  37. package/skills/catalog.json +2 -2
  38. package/skills/client-urls/SKILL.md +20 -20
  39. package/skills/comparison/references/framework-comparison.md +6 -6
  40. package/skills/defer-hydration/SKILL.md +2 -2
  41. package/skills/handler-use/SKILL.md +5 -5
  42. package/skills/hooks/data.md +1 -1
  43. package/skills/hooks/handle-and-actions.md +9 -9
  44. package/skills/loader/SKILL.md +52 -47
  45. package/skills/middleware/SKILL.md +2 -2
  46. package/skills/migrate-nextjs/SKILL.md +10 -10
  47. package/skills/migrate-react-router/SKILL.md +1 -1
  48. package/skills/migrate-react-router/component-migration.md +2 -2
  49. package/skills/migrate-react-router/data-and-actions.md +2 -2
  50. package/skills/migrate-react-router/route-mapping.md +2 -2
  51. package/skills/parallel/SKILL.md +2 -2
  52. package/skills/ppr/SKILL.md +91 -92
  53. package/skills/prerender/SKILL.md +5 -5
  54. package/skills/rango/SKILL.md +7 -7
  55. package/skills/route/SKILL.md +1 -1
  56. package/skills/router-setup/SKILL.md +2 -2
  57. package/skills/scripts/SKILL.md +3 -3
  58. package/skills/shell-manifest/SKILL.md +3 -3
  59. package/skills/testing/serve-shell-request.md +1 -1
  60. package/skills/theme/SKILL.md +2 -2
  61. package/skills/typesafety/env-and-bindings.md +2 -2
  62. package/skills/use-cache/SKILL.md +1 -1
  63. package/skills/ux-architecture/SKILL.md +7 -7
  64. package/src/cache/shell-snapshot.ts +1 -1
  65. package/src/cache/types.ts +1 -1
  66. package/src/client-urls/client-urls.ts +16 -9
  67. package/src/client-urls/server-projection.ts +4 -4
  68. package/src/client-urls/types.ts +6 -6
  69. package/src/decode-loader-results.ts +1 -1
  70. package/src/errors.ts +9 -9
  71. package/src/handles/meta.ts +2 -2
  72. package/src/loader-store.ts +1 -1
  73. package/src/outlet-context.ts +1 -1
  74. package/src/route-definition/dsl-helpers.ts +4 -8
  75. package/src/route-definition/helpers-types.ts +5 -5
  76. package/src/router/loader-resolution.ts +4 -4
  77. package/src/router/segment-resolution/loader-cache.ts +8 -8
  78. package/src/router/segment-resolution/prefetch-deferral.ts +1 -1
  79. package/src/router/segment-resolution/revalidation.ts +3 -3
  80. package/src/router/types.ts +1 -1
  81. package/src/rsc/shell-capture-constants.ts +3 -3
  82. package/src/rsc/shell-capture.ts +12 -12
  83. package/src/segment-system.tsx +3 -3
  84. package/src/server/context.ts +5 -5
  85. package/src/server/cookie-store.ts +1 -1
  86. package/src/server/request-context.ts +1 -1
  87. package/src/ssr/index.tsx +6 -6
  88. package/src/ssr/ssr-root.tsx +1 -1
  89. package/src/ssr-suspension-warning.ts +4 -4
  90. package/src/types/loader-types.ts +19 -19
  91. package/src/types/segments.ts +2 -2
  92. package/src/urls/path-helper-types.ts +4 -4
  93. package/src/urls/pattern-types.ts +1 -1
  94. package/src/vite/discovery/shell-prerender-phase.ts +1 -1
  95. package/src/vite/plugin-types.ts +1 -1
@@ -381,7 +381,7 @@ middleware `ctx` passed in); under `cache()` loaders can still read it because a
381
381
  DSL loader re-runs on every hit (a `"use cache"` function a loader calls cannot,
382
382
  and a loader bound with its own `cache()` only with a `key()`, which switches
383
383
  the check off, so the key must include the value). On a `ppr` route only a
384
- loader without `ssr: false` that no handler awaits may read it: a read the shell
384
+ loader without `ssr: "await"` that no handler awaits may read it: a read the shell
385
385
  capture waits for refuses the capture. A middleware `ctx` passed to a
386
386
  `"use cache"` function keys the call by host, pathname, params and search, plus
387
387
  the route name once the route is matched (a global middleware before `next()`
@@ -556,7 +556,7 @@ direct visit does. A shell keyed by the visitor's URL
556
556
  that URL.
557
557
 
558
558
  **Middleware only, by design.** `rewrite()` is a middleware tool. A route
559
- handler or a loader (any loader, `ssr: false` included) cannot rewrite: its
559
+ handler or a loader (any loader, `ssr: "await"` included) cannot rewrite: its
560
560
  throw is an error whose message points you to route middleware. A rewrite
561
561
  that depends on data goes in the route's middleware, reading the data
562
562
  through a cached function the loader shares, so the lookup runs once:
@@ -40,7 +40,7 @@ Common reasons to migrate:
40
40
  build-time rendering instead of mixing rendering and caching behind conventions.
41
41
  See: `/prerender`
42
42
  - **Partial prerendering, shipped** — the `ppr` path option caches a page's
43
- HTML shell and resumes its holes per request: loaders without `ssr: false`,
43
+ HTML shell and resumes its holes per request: loaders without `ssr: "await"`,
44
44
  read under `loading()` or an inline `<Suspense>`. Handler output bakes into
45
45
  the shell. It maps to Next's `experimental_ppr`, stable and per-route, but
46
46
  holes come from loaders, not from any `<Suspense>`.
@@ -100,7 +100,7 @@ its call site with the real Rango API:
100
100
  `next/dynamic`'s `{ ssr: false }` keeps a component out of server rendering:
101
101
  render it only after mount in a `"use client"` component (a `useEffect` flag,
102
102
  with `React.lazy()` if its code should split out). Do not map it to
103
- `loader(L, { ssr: false })`, which does the opposite: the server settles that
103
+ `loader(L, { ssr: "await" })`, which does the opposite: the server settles that
104
104
  loader before the first flush, and under `ppr` it bakes into the shell.
105
105
 
106
106
  If an import has no row here and no obvious Rango equivalent, stop and surface
@@ -533,7 +533,7 @@ function ProductPage(ctx: HandlerContext) {
533
533
  );
534
534
  }
535
535
 
536
- // Rango, live price: a loader without ssr: false, read with
536
+ // Rango, live price: a loader without ssr: "await", read with
537
537
  // useLoader(LivePriceLoader) in a client component. loading() (or an inline
538
538
  // <Suspense> around the reader) is the hole boundary (/ppr → The loader lane
539
539
  // rule).
@@ -560,9 +560,9 @@ Differences that matter during migration:
560
560
  component, a nested promise in a handle it pushes, a loader it awaits — is
561
561
  awaited at capture (bounded by `ppr.captureTimeout`) and served frozen for
562
562
  the shell's lifetime; a shell HIT never runs a handler. Keep the parts that
563
- must be fresh in loaders without `ssr: false`, read with `useLoader` under
564
- `loading()` or an inline `<Suspense>`; inside an `ssr: false` loader, return
565
- them as nested promises. For loaders, `ssr: false` (not `loading()`) selects
563
+ must be fresh in loaders without `ssr: "await"`, read with `useLoader` under
564
+ `loading()` or an inline `<Suspense>`; inside an `ssr: "await"` loader, return
565
+ them as nested promises. For loaders, `ssr: "await"` (not `loading()`) selects
566
566
  the lane — see `/ppr` → The loader lane rule.
567
567
  - **Shell freshness is explicit.** Next's PPR shell is fixed until the next
568
568
  build; Rango's has `ttl`/`swr`/`tags` per route, and `updateTag()` /
@@ -577,7 +577,7 @@ Differences that matter during migration:
577
577
  `ctx.request.headers`, a `{ cache: false }` variable, and `ctx.dynamic()` refuse it anywhere the
578
578
  capture waits: a handler, a promise it passes or pushes, an async component,
579
579
  a loader it awaits. Per-user reads must move into a live loader (no
580
- `ssr: false`; a nested promise does not help). A normal `ctx.get()` value is
580
+ `ssr: "await"`; a nested promise does not help). A normal `ctx.get()` value is
581
581
  not guarded and bakes as the capturing request's value. The refusal surfaces
582
582
  at migration time, which is the point.
583
583
  - **A store is required.** PPR needs the app-level `createRouter({ cache })`
@@ -890,7 +890,7 @@ const HomePage: Handler<"home"> = (ctx) => {
890
890
 
891
891
  `generateMetadata({ params })` — DATA-derived, document-blocking metadata —
892
892
  maps to a Meta push from the LOADER that owns the data, plus
893
- `{ ssr: false }` for the blocking-until-in-head part:
893
+ `{ ssr: "await" }` for the blocking-until-in-head part:
894
894
 
895
895
  ```typescript
896
896
  // Next.js: export async function generateMetadata({ params }) {
@@ -907,7 +907,7 @@ export const ProductLoader = createLoader(async (ctx) => {
907
907
  });
908
908
 
909
909
  path("/product/:slug", ProductPage, { name: "product" }, () => [
910
- loader(ProductLoader, { ssr: false }),
910
+ loader(ProductLoader, { ssr: "await" }),
911
911
  ]);
912
912
  ```
913
913
 
@@ -1008,7 +1008,7 @@ See `/theme` for full API including system detection and cookie persistence.
1008
1008
  10. [ ] Convert loading/error files to `loading()` / `errorBoundary()`
1009
1009
  11. [ ] Migrate API routes to `path.json()` / `path.text()`
1010
1010
  12. [ ] Update metadata to use `Meta` handle + `<Html.Meta />` in document head
1011
- (`generateMetadata` → loader push + `{ ssr: false }`)
1011
+ (`generateMetadata` → loader push + `{ ssr: "await" }`)
1012
1012
  13. [ ] Replace `next-themes` with `theme: true` in createRouter (see `/theme`)
1013
1013
  14. [ ] Map rendering-mode segment config: `revalidate = N` → `cache({ ttl })`,
1014
1014
  `force-static` → `Static()`/`Prerender()`, `experimental_ppr` → the
@@ -34,7 +34,7 @@ Common reasons to migrate:
34
34
  - **Live data layer** — `createLoader()` and `loader()` keep data fresh
35
35
  independently of cached UI. A route can serve cached segments while loaders
36
36
  still resolve live on every request (on a `ppr` route, a loader registered
37
- with `ssr: false` bakes into the cached HTML shell instead; see `/ppr`).
37
+ with `ssr: "await"` bakes into the cached HTML shell instead; see `/ppr`).
38
38
  See: `/loader`, `/caching`, `/cache-guide`
39
39
  - **Explicit caching model** — `cache()` DSL, `revalidate()`, `use cache`, and
40
40
  custom cache stores make data and render caching a first-class part of the router.
@@ -153,9 +153,9 @@ const HomePage: Handler<"home"> = (ctx) => {
153
153
 
154
154
  RR's data-derived `meta({ data })` maps to the same push from the LOADER that
155
155
  owns the data — `ctx.use(Meta)({ title: data.name })` in the loader body, with
156
- `loader(Def, { ssr: false })` when the title must be in the SSR'd
156
+ `loader(Def, { ssr: "await" })` when the title must be in the SSR'd
157
157
  head. See `/loader` → "Writing Handles from Loaders". The loader flag is
158
- unrelated to RR7's `ssr: false` (SPA mode), which has no route-wide Rango
158
+ unrelated to RR7's `ssr: "await"` (SPA mode), which has no route-wide Rango
159
159
  equivalent: it makes the server settle that loader before the first flush.
160
160
 
161
161
  Add `<Html.Meta />` in the Document component's `<head>`:
@@ -48,8 +48,8 @@ Use it only when you need capabilities beyond what the handler provides:
48
48
  document loads, never an HTTP 302 — pre-stream 302s move to middleware)
49
49
  - **`meta({ data })` / `handle` exports** — data-derived page metadata becomes
50
50
  a handle push from the loader body (`ctx.use(Meta)({ title: data.name })`),
51
- with `loader(L, { ssr: false })` when it must be in the SSR'd head (not
52
- RR7's `ssr: false` SPA mode, which has no route-wide Rango equivalent: the
51
+ with `loader(L, { ssr: "await" })` when it must be in the SSR'd head (not
52
+ RR7's `ssr: "await"` SPA mode, which has no route-wide Rango equivalent: the
53
53
  loader flag makes the server settle that loader before the first flush)
54
54
 
55
55
  If the React Router loader just fetches data for its page component AND the
@@ -141,10 +141,10 @@ The loader-shaped variant is equally valid — and closer to the RR module when
141
141
  the loader carried authority. A `createLoader()` body can throw `notFound()`
142
142
  for the missing product AND push the data-derived meta itself
143
143
  (`ctx.use(Meta)({ title: product.name })`); register it with
144
- `loader(ProductLoader, { ssr: false })` when the 404 status and
144
+ `loader(ProductLoader, { ssr: "await" })` when the 404 status and
145
145
  title must be in the document deterministically (the flag makes the server
146
146
  settle that loader before the first flush; it is unrelated to RR7's
147
- `ssr: false` SPA mode, which has no route-wide Rango equivalent). See
147
+ `ssr: "await"` SPA mode, which has no route-wide Rango equivalent). See
148
148
  `/loader` → "Loader Authority" and "Writing Handles from Loaders". (One RR
149
149
  habit that does NOT carry over: a loader `throw redirect()` is a client-side
150
150
  navigate on document loads, never an HTTP 302 — pre-stream 302s belong in
@@ -152,10 +152,10 @@ layout, and `Meta` keeps the last value per key, so the override wins.
152
152
  > just to reach a `ctx.use(Meta)` call: under `cache()` the slot's output is
153
153
  > stored with the segment, and on a `ppr` route it bakes into the shell and a
154
154
  > HIT replays it without running the slot. The loader can push `Meta` itself
155
- > (`/loader` → "Writing Handles from Loaders"). Without `ssr: false` the
155
+ > (`/loader` → "Writing Handles from Loaders"). Without `ssr: "await"` the
156
156
  > loader runs per request, but on a `ppr` route its push is not in the
157
157
  > shell's `<head>` (it applies after hydration). Add
158
- > `loader(Def, { ssr: false })` when the meta must be in the SSR'd head; on a
158
+ > `loader(Def, { ssr: "await" })` when the meta must be in the SSR'd head; on a
159
159
  > `ppr` route that bakes the push into the shell, and a HIT serves it without
160
160
  > running the loader when its value has no promises. Keep the `@meta` slot for
161
161
  > metadata that is NOT loader-derived (templates, static descriptions,