@rangojs/router 0.0.0-experimental.32 → 0.0.0-experimental.3232cd17
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.
- package/AGENTS.md +4 -0
- package/README.md +198 -44
- package/dist/bin/rango.js +287 -105
- package/dist/testing/vitest.js +82 -0
- package/dist/vite/index.js +3248 -1117
- package/dist/vite/plugins/cloudflare-protocol-loader-hook.mjs +76 -0
- package/package.json +73 -21
- package/skills/api-client/SKILL.md +211 -0
- package/skills/breadcrumbs/SKILL.md +107 -1
- package/skills/bundle-analysis/SKILL.md +159 -0
- package/skills/cache-guide/SKILL.md +245 -21
- package/skills/caching/SKILL.md +302 -6
- package/skills/composability/SKILL.md +27 -2
- package/skills/css/SKILL.md +76 -0
- package/skills/document-cache/SKILL.md +78 -55
- package/skills/handler-use/SKILL.md +364 -0
- package/skills/hooks/SKILL.md +270 -30
- package/skills/host-router/SKILL.md +82 -22
- package/skills/i18n/SKILL.md +276 -0
- package/skills/intercept/SKILL.md +49 -5
- package/skills/layout/SKILL.md +35 -9
- package/skills/links/SKILL.md +249 -17
- package/skills/loader/SKILL.md +294 -30
- package/skills/middleware/SKILL.md +52 -13
- package/skills/migrate-nextjs/SKILL.md +584 -0
- package/skills/migrate-react-router/SKILL.md +769 -0
- package/skills/mime-routes/SKILL.md +27 -0
- package/skills/observability/SKILL.md +137 -0
- package/skills/parallel/SKILL.md +203 -7
- package/skills/prerender/SKILL.md +123 -100
- package/skills/rango/SKILL.md +250 -22
- package/skills/react-compiler/SKILL.md +168 -0
- package/skills/response-routes/SKILL.md +122 -47
- package/skills/route/SKILL.md +97 -5
- package/skills/router-setup/SKILL.md +90 -5
- package/skills/server-actions/SKILL.md +775 -0
- package/skills/streams-and-websockets/SKILL.md +283 -0
- package/skills/tailwind/SKILL.md +27 -3
- package/skills/testing/SKILL.md +129 -0
- package/skills/testing/bindings.md +89 -0
- package/skills/testing/cache-prerender.md +124 -0
- package/skills/testing/client-components.md +122 -0
- package/skills/testing/e2e-parity.md +125 -0
- package/skills/testing/flight.md +92 -0
- package/skills/testing/handles.md +129 -0
- package/skills/testing/loader.md +128 -0
- package/skills/testing/middleware.md +99 -0
- package/skills/testing/render-handler.md +121 -0
- package/skills/testing/response-routes.md +95 -0
- package/skills/testing/reverse-and-types.md +84 -0
- package/skills/testing/server-actions.md +107 -0
- package/skills/testing/server-tree.md +128 -0
- package/skills/testing/setup.md +120 -0
- package/skills/typesafety/SKILL.md +329 -27
- package/skills/use-cache/SKILL.md +36 -5
- package/skills/view-transitions/SKILL.md +294 -0
- package/src/__augment-tests__/augment.ts +81 -0
- package/src/__augment-tests__/augmented.check.ts +116 -0
- package/src/__internal.ts +67 -40
- package/src/browser/action-coordinator.ts +53 -36
- package/src/browser/action-fence.ts +47 -0
- package/src/browser/app-shell.ts +39 -0
- package/src/browser/app-version.ts +14 -0
- package/src/browser/cookie-name.ts +140 -0
- package/src/browser/event-controller.ts +86 -147
- package/src/browser/history-state.ts +21 -0
- package/src/browser/index.ts +3 -3
- package/src/browser/invalidate-client-cache.ts +52 -0
- package/src/browser/link-interceptor.ts +4 -0
- package/src/browser/navigation-bridge.ts +148 -19
- package/src/browser/navigation-client.ts +187 -67
- package/src/browser/navigation-store-handle.ts +38 -0
- package/src/browser/navigation-store.ts +76 -67
- package/src/browser/navigation-transaction.ts +18 -66
- package/src/browser/partial-update.ts +123 -94
- package/src/browser/prefetch/cache.ts +214 -36
- package/src/browser/prefetch/fetch.ts +260 -38
- package/src/browser/prefetch/policy.ts +6 -0
- package/src/browser/prefetch/queue.ts +126 -20
- package/src/browser/prefetch/resource-ready.ts +77 -0
- package/src/browser/rango-state.ts +158 -76
- package/src/browser/react/Link.tsx +93 -11
- package/src/browser/react/NavigationProvider.tsx +115 -34
- package/src/browser/react/ScrollRestoration.tsx +10 -6
- package/src/browser/react/context.ts +7 -2
- package/src/browser/react/filter-segment-order.ts +49 -7
- package/src/browser/react/index.ts +0 -48
- package/src/browser/react/location-state-shared.ts +166 -8
- package/src/browser/react/location-state.ts +39 -14
- package/src/browser/react/use-action.ts +6 -15
- package/src/browser/react/use-handle.ts +23 -69
- package/src/browser/react/use-link-status.ts +0 -4
- package/src/browser/react/use-navigation.ts +22 -5
- package/src/browser/react/use-params.ts +20 -10
- package/src/browser/react/use-reverse.ts +106 -0
- package/src/browser/react/use-router.ts +46 -11
- package/src/browser/react/use-search-params.ts +0 -5
- package/src/browser/react/use-segments.ts +11 -21
- package/src/browser/response-adapter.ts +52 -1
- package/src/browser/rsc-router.tsx +215 -76
- package/src/browser/scroll-restoration.ts +46 -39
- package/src/browser/segment-reconciler.ts +36 -9
- package/src/browser/segment-structure-assert.ts +2 -2
- package/src/browser/server-action-bridge.ts +176 -50
- package/src/browser/types.ts +95 -11
- package/src/browser/validate-redirect-origin.ts +43 -16
- package/src/build/collect-fallback-refs.ts +107 -0
- package/src/build/generate-manifest.ts +65 -40
- package/src/build/generate-route-types.ts +5 -0
- package/src/build/index.ts +8 -2
- package/src/build/prefix-tree-utils.ts +123 -0
- package/src/build/route-trie.ts +137 -32
- package/src/build/route-types/codegen.ts +4 -4
- package/src/build/route-types/include-resolution.ts +9 -2
- package/src/build/route-types/param-extraction.ts +6 -3
- package/src/build/route-types/per-module-writer.ts +7 -4
- package/src/build/route-types/router-processing.ts +278 -96
- package/src/build/route-types/scan-filter.ts +9 -2
- package/src/build/route-types/source-scan.ts +118 -0
- package/src/build/runtime-discovery.ts +9 -20
- package/src/cache/cache-error.ts +104 -0
- package/src/cache/cache-policy.ts +68 -28
- package/src/cache/cache-runtime.ts +149 -43
- package/src/cache/cache-scope.ts +148 -81
- package/src/cache/cache-tag.ts +98 -0
- package/src/cache/cf/cf-cache-store.ts +2550 -93
- package/src/cache/cf/index.ts +11 -17
- package/src/cache/document-cache.ts +78 -27
- package/src/cache/handle-snapshot.ts +63 -0
- package/src/cache/index.ts +23 -20
- package/src/cache/memory-segment-store.ts +136 -37
- package/src/cache/profile-registry.ts +6 -30
- package/src/cache/read-through-swr.ts +41 -11
- package/src/cache/segment-codec.ts +0 -16
- package/src/cache/tag-invalidation.ts +230 -0
- package/src/cache/taint.ts +55 -0
- package/src/cache/types.ts +33 -100
- package/src/cache/vercel/index.ts +11 -0
- package/src/cache/vercel/vercel-cache-store.ts +799 -0
- package/src/client.rsc.tsx +6 -21
- package/src/client.tsx +108 -290
- package/src/component-utils.ts +19 -0
- package/src/context-var.ts +84 -2
- package/src/debug.ts +2 -2
- package/src/decode-loader-results.ts +36 -0
- package/src/defer.ts +196 -0
- package/src/deps/ssr.ts +0 -1
- package/src/errors.ts +30 -4
- package/src/handle.ts +70 -22
- package/src/handles/MetaTags.tsx +0 -14
- package/src/handles/breadcrumbs.ts +16 -5
- package/src/handles/meta.ts +0 -39
- package/src/host/cookie-handler.ts +0 -36
- package/src/host/errors.ts +0 -24
- package/src/host/index.ts +8 -2
- package/src/host/pattern-matcher.ts +7 -50
- package/src/host/router.ts +107 -99
- package/src/host/testing.ts +40 -27
- package/src/host/types.ts +37 -4
- package/src/host/utils.ts +1 -1
- package/src/href-client.ts +137 -22
- package/src/index.rsc.ts +52 -26
- package/src/index.ts +100 -38
- package/src/internal-debug.ts +2 -4
- package/src/loader-store.ts +500 -0
- package/src/loader.rsc.ts +20 -13
- package/src/loader.ts +12 -11
- package/src/missing-id-error.ts +68 -0
- package/src/network-error-thrower.tsx +1 -6
- package/src/outlet-context.ts +1 -1
- package/src/outlet-provider.tsx +1 -5
- package/src/prerender/param-hash.ts +10 -11
- package/src/prerender/store.ts +37 -41
- package/src/prerender.ts +198 -82
- package/src/redirect-origin.ts +100 -0
- package/src/response-utils.ts +37 -0
- package/src/reverse.ts +65 -15
- package/src/root-error-boundary.tsx +1 -19
- package/src/route-content-wrapper.tsx +7 -72
- package/src/route-definition/dsl-helpers.ts +437 -274
- package/src/route-definition/helper-factories.ts +29 -139
- package/src/route-definition/helpers-types.ts +113 -37
- package/src/route-definition/index.ts +3 -0
- package/src/route-definition/redirect.ts +52 -10
- package/src/route-definition/resolve-handler-use.ts +161 -0
- package/src/route-definition/use-item-types.ts +32 -0
- package/src/route-map-builder.ts +7 -17
- package/src/route-types.ts +37 -41
- package/src/router/basename.ts +14 -0
- package/src/router/content-negotiation.ts +108 -9
- package/src/router/error-handling.ts +13 -17
- package/src/router/find-match.ts +45 -22
- package/src/router/handler-context.ts +83 -41
- package/src/router/intercept-resolution.ts +25 -23
- package/src/router/lazy-includes.ts +19 -53
- package/src/router/loader-resolution.ts +213 -30
- package/src/router/logging.ts +5 -8
- package/src/router/manifest.ts +49 -45
- package/src/router/match-api.ts +120 -204
- package/src/router/match-context.ts +0 -22
- package/src/router/match-handlers.ts +58 -58
- package/src/router/match-middleware/background-revalidation.ts +27 -6
- package/src/router/match-middleware/cache-lookup.ts +205 -249
- package/src/router/match-middleware/cache-store.ts +45 -32
- package/src/router/match-middleware/intercept-resolution.ts +8 -28
- package/src/router/match-middleware/segment-resolution.ts +52 -18
- package/src/router/match-pipelines.ts +1 -42
- package/src/router/match-result.ts +104 -40
- package/src/router/metrics.ts +5 -34
- package/src/router/middleware-types.ts +13 -142
- package/src/router/middleware.ts +173 -143
- package/src/router/navigation-snapshot.ts +131 -0
- package/src/router/params-util.ts +23 -0
- package/src/router/pattern-matching.ts +109 -63
- package/src/router/prerender-match.ts +190 -54
- package/src/router/preview-match.ts +32 -102
- package/src/router/request-classification.ts +276 -0
- package/src/router/revalidation.ts +63 -55
- package/src/router/route-snapshot.ts +244 -0
- package/src/router/router-context.ts +6 -28
- package/src/router/router-interfaces.ts +100 -35
- package/src/router/router-options.ts +91 -11
- package/src/router/router-registry.ts +2 -5
- package/src/router/segment-resolution/fresh.ts +242 -75
- package/src/router/segment-resolution/helpers.ts +63 -24
- package/src/router/segment-resolution/loader-cache.ts +41 -37
- package/src/router/segment-resolution/revalidation.ts +456 -372
- package/src/router/segment-resolution/static-store.ts +19 -5
- package/src/router/segment-resolution/streamed-handler-telemetry.ts +52 -0
- package/src/router/segment-resolution/view-transition-default.ts +36 -0
- package/src/router/segment-resolution.ts +4 -1
- package/src/router/segment-wrappers.ts +2 -3
- package/src/router/state-cookie-name.ts +33 -0
- package/src/router/substitute-pattern-params.ts +56 -0
- package/src/router/telemetry-otel.ts +0 -20
- package/src/router/telemetry.ts +96 -19
- package/src/router/timeout.ts +0 -20
- package/src/router/trie-matching.ts +91 -46
- package/src/router/types.ts +10 -63
- package/src/router/url-params.ts +44 -0
- package/src/router.ts +134 -43
- package/src/rsc/handler-context.ts +3 -2
- package/src/rsc/handler.ts +492 -383
- package/src/rsc/helpers.ts +162 -46
- package/src/rsc/index.ts +1 -1
- package/src/rsc/json-route-result.ts +38 -0
- package/src/rsc/loader-fetch.ts +23 -3
- package/src/rsc/manifest-init.ts +33 -42
- package/src/rsc/origin-guard.ts +39 -25
- package/src/rsc/progressive-enhancement.ts +30 -3
- package/src/rsc/redirect-guard.ts +99 -0
- package/src/rsc/response-error.ts +79 -12
- package/src/rsc/response-route-handler.ts +90 -63
- package/src/rsc/rsc-rendering.ts +56 -54
- package/src/rsc/runtime-warnings.ts +23 -10
- package/src/rsc/server-action.ts +74 -67
- package/src/rsc/ssr-setup.ts +18 -2
- package/src/rsc/types.ts +25 -6
- package/src/runtime-env.ts +18 -0
- package/src/search-params.ts +4 -20
- package/src/segment-content-promise.ts +67 -0
- package/src/segment-loader-promise.ts +134 -0
- package/src/segment-system.tsx +272 -129
- package/src/serialize.ts +243 -0
- package/src/server/context.ts +309 -61
- package/src/server/cookie-store.ts +80 -5
- package/src/server/handle-store.ts +26 -24
- package/src/server/loader-registry.ts +10 -28
- package/src/server/request-context.ts +338 -126
- package/src/ssr/index.tsx +23 -15
- package/src/static-handler.ts +27 -18
- package/src/testing/cache-status.ts +162 -0
- package/src/testing/collect-handle.ts +40 -0
- package/src/testing/dispatch.ts +618 -0
- package/src/testing/dom.entry.ts +22 -0
- package/src/testing/e2e/fixture.ts +188 -0
- package/src/testing/e2e/index.ts +128 -0
- package/src/testing/e2e/matchers.ts +35 -0
- package/src/testing/e2e/page-helpers.ts +272 -0
- package/src/testing/e2e/parity.ts +387 -0
- package/src/testing/e2e/server.ts +195 -0
- package/src/testing/flight-matchers.ts +97 -0
- package/src/testing/flight-normalize.ts +11 -0
- package/src/testing/flight-runtime.d.ts +57 -0
- package/src/testing/flight-tree.ts +682 -0
- package/src/testing/flight.entry.ts +52 -0
- package/src/testing/flight.ts +232 -0
- package/src/testing/generated-routes.ts +183 -0
- package/src/testing/index.ts +99 -0
- package/src/testing/internal/context.ts +348 -0
- package/src/testing/internal/flight-client-globals.ts +30 -0
- package/src/testing/internal/seed-vars.ts +54 -0
- package/src/testing/render-handler.ts +330 -0
- package/src/testing/render-route.tsx +566 -0
- package/src/testing/run-loader.ts +378 -0
- package/src/testing/run-middleware.ts +205 -0
- package/src/testing/vitest-stubs/cloudflare-email.ts +9 -0
- package/src/testing/vitest-stubs/cloudflare-workers.ts +21 -0
- package/src/testing/vitest-stubs/plugin-rsc.ts +16 -0
- package/src/testing/vitest-stubs/version.ts +5 -0
- package/src/testing/vitest.ts +305 -0
- package/src/theme/ThemeProvider.tsx +0 -52
- package/src/theme/ThemeScript.tsx +0 -6
- package/src/theme/constants.ts +0 -12
- package/src/theme/index.ts +0 -7
- package/src/theme/theme-context.ts +1 -5
- package/src/theme/theme-script.ts +0 -14
- package/src/theme/use-theme.ts +0 -3
- package/src/types/boundaries.ts +0 -35
- package/src/types/cache-types.ts +17 -8
- package/src/types/error-types.ts +30 -90
- package/src/types/global-namespace.ts +54 -41
- package/src/types/handler-context.ts +233 -81
- package/src/types/index.ts +1 -10
- package/src/types/loader-types.ts +44 -15
- package/src/types/request-scope.ts +107 -0
- package/src/types/route-config.ts +6 -50
- package/src/types/route-entry.ts +19 -7
- package/src/types/segments.ts +37 -14
- package/src/urls/include-helper.ts +33 -70
- package/src/urls/index.ts +1 -11
- package/src/urls/path-helper-types.ts +58 -11
- package/src/urls/path-helper.ts +57 -111
- package/src/urls/pattern-types.ts +48 -19
- package/src/urls/response-types.ts +25 -22
- package/src/urls/type-extraction.ts +58 -139
- package/src/urls/urls-function.ts +1 -18
- package/src/use-loader.tsx +346 -89
- package/src/vite/debug.ts +185 -0
- package/src/vite/discovery/bundle-postprocess.ts +36 -38
- package/src/vite/discovery/discover-routers.ts +130 -85
- package/src/vite/discovery/discovery-errors.ts +194 -0
- package/src/vite/discovery/gate-state.ts +171 -0
- package/src/vite/discovery/prerender-collection.ts +192 -99
- package/src/vite/discovery/route-types-writer.ts +40 -84
- package/src/vite/discovery/self-gen-tracking.ts +27 -1
- package/src/vite/discovery/state.ts +51 -6
- package/src/vite/discovery/virtual-module-codegen.ts +14 -34
- package/src/vite/index.ts +8 -0
- package/src/vite/plugin-types.ts +187 -69
- package/src/vite/plugins/cjs-to-esm.ts +8 -18
- package/src/vite/plugins/client-ref-dedup.ts +16 -11
- package/src/vite/plugins/client-ref-hashing.ts +28 -15
- package/src/vite/plugins/cloudflare-protocol-loader-hook.d.mts +23 -0
- package/src/vite/plugins/cloudflare-protocol-loader-hook.mjs +76 -0
- package/src/vite/plugins/cloudflare-protocol-stub.ts +194 -0
- package/src/vite/plugins/expose-action-id.ts +49 -98
- package/src/vite/plugins/expose-id-utils.ts +11 -50
- package/src/vite/plugins/expose-ids/export-analysis.ts +76 -34
- package/src/vite/plugins/expose-ids/handler-transform.ts +10 -48
- package/src/vite/plugins/expose-ids/loader-transform.ts +3 -20
- package/src/vite/plugins/expose-ids/router-transform.ts +20 -16
- package/src/vite/plugins/expose-internal-ids.ts +554 -317
- package/src/vite/plugins/performance-tracks.ts +89 -0
- package/src/vite/plugins/refresh-cmd.ts +89 -27
- package/src/vite/plugins/use-cache-transform.ts +73 -83
- package/src/vite/plugins/vercel-output.ts +258 -0
- package/src/vite/plugins/version-injector.ts +21 -25
- package/src/vite/plugins/version-plugin.ts +41 -20
- package/src/vite/plugins/virtual-entries.ts +2 -17
- package/src/vite/rango.ts +257 -289
- package/src/vite/router-discovery.ts +930 -140
- package/src/vite/utils/ast-handler-extract.ts +15 -31
- package/src/vite/utils/banner.ts +4 -4
- package/src/vite/utils/bundle-analysis.ts +10 -15
- package/src/vite/utils/client-chunks.ts +184 -0
- package/src/vite/utils/forward-user-plugins.ts +171 -0
- package/src/vite/utils/manifest-utils.ts +4 -59
- package/src/vite/utils/package-resolution.ts +20 -52
- package/src/vite/utils/prerender-utils.ts +27 -29
- package/src/vite/utils/shared-utils.ts +92 -42
- package/src/browser/action-response-classifier.ts +0 -99
- package/src/browser/react/use-client-cache.ts +0 -58
- package/src/browser/shallow.ts +0 -40
- package/src/handles/index.ts +0 -7
- package/src/router/middleware-cookies.ts +0 -55
package/src/router.ts
CHANGED
|
@@ -1,9 +1,6 @@
|
|
|
1
1
|
import { type ReactNode } from "react";
|
|
2
2
|
import { createCacheScope } from "./cache/cache-scope.js";
|
|
3
|
-
import {
|
|
4
|
-
setCacheProfiles,
|
|
5
|
-
resolveCacheProfiles,
|
|
6
|
-
} from "./cache/profile-registry.js";
|
|
3
|
+
import { resolveCacheProfiles } from "./cache/profile-registry.js";
|
|
7
4
|
import { isCachedFunction } from "./cache/taint.js";
|
|
8
5
|
import { assertClientComponent } from "./component-utils.js";
|
|
9
6
|
import { DefaultDocument } from "./components/DefaultDocument.js";
|
|
@@ -19,11 +16,13 @@ import {
|
|
|
19
16
|
import MapRootLayout from "./server/root-layout.js";
|
|
20
17
|
import type { AllUseItems } from "./route-types.js";
|
|
21
18
|
import type { UrlPatterns } from "./urls.js";
|
|
19
|
+
import type { UrlBuilder } from "./urls/pattern-types.js";
|
|
20
|
+
import { urls } from "./urls.js";
|
|
21
|
+
import { buildPrecomputedByPrefix } from "./build/prefix-tree-utils.js";
|
|
22
22
|
import {
|
|
23
|
-
EntryData,
|
|
24
|
-
InterceptSelectorContext,
|
|
23
|
+
type EntryData,
|
|
25
24
|
getContext,
|
|
26
|
-
|
|
25
|
+
RangoContext,
|
|
27
26
|
type MetricsStore,
|
|
28
27
|
} from "./server/context";
|
|
29
28
|
import { createHandleStore, type HandleStore } from "./server/handle-store.js";
|
|
@@ -55,6 +54,7 @@ import { buildDebugManifest } from "./router/debug-manifest.js";
|
|
|
55
54
|
|
|
56
55
|
import type { SegmentResolutionDeps, MatchApiDeps } from "./router/types.js";
|
|
57
56
|
import { createHandlerContext } from "./router/handler-context.js";
|
|
57
|
+
import { normalizeBasename } from "./router/basename.js";
|
|
58
58
|
import {
|
|
59
59
|
setupLoaderAccess,
|
|
60
60
|
setupLoaderAccessSilent,
|
|
@@ -69,6 +69,7 @@ import {
|
|
|
69
69
|
} from "./router/middleware.js";
|
|
70
70
|
import {
|
|
71
71
|
extractStaticPrefix,
|
|
72
|
+
joinPrefix,
|
|
72
73
|
traverseBack,
|
|
73
74
|
} from "./router/pattern-matching.js";
|
|
74
75
|
import { resolveSink, safeEmit, getRequestId } from "./router/telemetry.js";
|
|
@@ -89,13 +90,10 @@ import {
|
|
|
89
90
|
RouterRegistry,
|
|
90
91
|
nextRouterAutoId,
|
|
91
92
|
} from "./router/router-registry.js";
|
|
93
|
+
import type { RangoOptions, RootLayoutProps } from "./router/router-options.js";
|
|
92
94
|
import type {
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
} from "./router/router-options.js";
|
|
96
|
-
import type {
|
|
97
|
-
RSCRouter,
|
|
98
|
-
RSCRouterInternal,
|
|
95
|
+
Rango,
|
|
96
|
+
RangoInternal,
|
|
99
97
|
RouterRequestInput,
|
|
100
98
|
} from "./router/router-interfaces.js";
|
|
101
99
|
|
|
@@ -110,29 +108,31 @@ import {
|
|
|
110
108
|
matchForPrerender as _matchForPrerender,
|
|
111
109
|
renderStaticSegment as _renderStaticSegment,
|
|
112
110
|
} from "./router/prerender-match.js";
|
|
111
|
+
import { resolveStateCookieName } from "./router/state-cookie-name.js";
|
|
113
112
|
|
|
114
113
|
// Re-export public types and values from extracted modules
|
|
115
114
|
export { RSC_ROUTER_BRAND, RouterRegistry } from "./router/router-registry.js";
|
|
116
115
|
export type {
|
|
117
|
-
|
|
116
|
+
RangoOptions,
|
|
118
117
|
RootLayoutProps,
|
|
119
118
|
SSRStreamMode,
|
|
120
119
|
SSROptions,
|
|
121
120
|
ResolveStreamingContext,
|
|
122
121
|
} from "./router/router-options.js";
|
|
123
122
|
export type {
|
|
124
|
-
|
|
125
|
-
|
|
123
|
+
Rango,
|
|
124
|
+
RangoInternal,
|
|
126
125
|
RouterRequestInput,
|
|
127
126
|
} from "./router/router-interfaces.js";
|
|
128
127
|
export { toInternal } from "./router/router-interfaces.js";
|
|
129
128
|
|
|
130
129
|
export function createRouter<TEnv = any>(
|
|
131
|
-
options:
|
|
132
|
-
):
|
|
130
|
+
options: RangoOptions<TEnv> = {},
|
|
131
|
+
): Rango<TEnv, {}> {
|
|
133
132
|
const {
|
|
134
133
|
id: userProvidedId,
|
|
135
134
|
$$id: injectedId,
|
|
135
|
+
basename: basenameOption,
|
|
136
136
|
debugPerformance = false,
|
|
137
137
|
document: documentOption,
|
|
138
138
|
defaultErrorBoundary,
|
|
@@ -148,6 +148,7 @@ export function createRouter<TEnv = any>(
|
|
|
148
148
|
nonce,
|
|
149
149
|
version,
|
|
150
150
|
prefetchCacheTTL: prefetchCacheTTLOption,
|
|
151
|
+
stateCookiePrefix: stateCookiePrefixOption,
|
|
151
152
|
warmup: warmupOption,
|
|
152
153
|
allowDebugManifest: allowDebugManifestOption = false,
|
|
153
154
|
telemetry: telemetrySink,
|
|
@@ -156,16 +157,31 @@ export function createRouter<TEnv = any>(
|
|
|
156
157
|
timeouts: timeoutsOption,
|
|
157
158
|
onTimeout,
|
|
158
159
|
originCheck: originCheckOption,
|
|
160
|
+
viewTransition: viewTransitionOption = "auto",
|
|
161
|
+
debugCacheSignal: debugCacheSignalOption = false,
|
|
159
162
|
} = options;
|
|
160
163
|
|
|
164
|
+
// Debug cache signal gate (DEVELOPMENT/TEST ONLY). Enabled by the
|
|
165
|
+
// debugCacheSignal option OR the RANGO_TEST_SIGNALS=1 env flag. When off,
|
|
166
|
+
// no X-Rango-Cache header is emitted and output is byte-identical.
|
|
167
|
+
const cacheSignalEnabled =
|
|
168
|
+
debugCacheSignalOption ||
|
|
169
|
+
(typeof process !== "undefined" &&
|
|
170
|
+
(process as { env?: Record<string, string | undefined> }).env
|
|
171
|
+
?.RANGO_TEST_SIGNALS === "1");
|
|
172
|
+
|
|
173
|
+
// Normalize basename: ensure leading slash, strip trailing slash.
|
|
174
|
+
// A bare "/" is equivalent to no basename. Shared with the testing
|
|
175
|
+
// primitives via normalizeBasename so they can never drift.
|
|
176
|
+
const basename = normalizeBasename(basenameOption);
|
|
177
|
+
|
|
161
178
|
// Resolve telemetry sink (no-op when not configured)
|
|
162
179
|
const telemetry = resolveSink(telemetrySink);
|
|
163
180
|
|
|
164
|
-
// Resolve cache profiles: merge user config with guaranteed default
|
|
165
|
-
// This resolved map is
|
|
166
|
-
//
|
|
181
|
+
// Resolve cache profiles: merge user config with the guaranteed default
|
|
182
|
+
// profile. This resolved map is threaded onto each request context; the
|
|
183
|
+
// "use cache: <profile>" runtime path reads it request-scoped.
|
|
167
184
|
const resolvedCacheProfiles = resolveCacheProfiles(cacheProfilesOption);
|
|
168
|
-
setCacheProfiles(resolvedCacheProfiles);
|
|
169
185
|
|
|
170
186
|
// Source file: prefer Vite-injected path (zero cost), fall back to
|
|
171
187
|
// stack trace parsing for non-Vite environments (e.g. tests).
|
|
@@ -200,6 +216,14 @@ export function createRouter<TEnv = any>(
|
|
|
200
216
|
const routerId =
|
|
201
217
|
userProvidedId ?? injectedId ?? `router_${nextRouterAutoId()}`;
|
|
202
218
|
|
|
219
|
+
// Resolve the rango state cookie name once, here, so the two cookie writers
|
|
220
|
+
// (the client document.cookie writer and the server Set-Cookie writer)
|
|
221
|
+
// consume one pre-composed name and cannot drift.
|
|
222
|
+
const resolvedStateCookieName = resolveStateCookieName(
|
|
223
|
+
stateCookiePrefixOption,
|
|
224
|
+
routerId,
|
|
225
|
+
);
|
|
226
|
+
|
|
203
227
|
// Resolve prefetch cache TTL (default: 300 seconds / 5 minutes)
|
|
204
228
|
// Clamp to a non-negative integer for valid Cache-Control max-age.
|
|
205
229
|
const rawTTL =
|
|
@@ -246,9 +270,14 @@ export function createRouter<TEnv = any>(
|
|
|
246
270
|
invokeOnError(onError, error, phase, context, "Router");
|
|
247
271
|
}
|
|
248
272
|
|
|
249
|
-
// Validate document is a client component
|
|
273
|
+
// Validate document is a client component. Under a test runner the "use
|
|
274
|
+
// client" transform has not run, so a real exported document has no marker;
|
|
275
|
+
// allowServerInTest lets the router construct in a bare unit test (for
|
|
276
|
+
// dispatch / assertGeneratedRoutesMatch) while a real build still throws.
|
|
250
277
|
if (documentOption !== undefined) {
|
|
251
|
-
assertClientComponent(documentOption, "document"
|
|
278
|
+
assertClientComponent(documentOption, "document", {
|
|
279
|
+
allowServerInTest: true,
|
|
280
|
+
});
|
|
252
281
|
}
|
|
253
282
|
|
|
254
283
|
// Use default document if none provided (keeps internal name as rootLayout)
|
|
@@ -322,7 +351,6 @@ export function createRouter<TEnv = any>(
|
|
|
322
351
|
regex,
|
|
323
352
|
paramNames,
|
|
324
353
|
handler,
|
|
325
|
-
mountPrefix,
|
|
326
354
|
});
|
|
327
355
|
}
|
|
328
356
|
|
|
@@ -356,9 +384,11 @@ export function createRouter<TEnv = any>(
|
|
|
356
384
|
getRouterPrecomputedEntries(routerId) ?? getPrecomputedEntries();
|
|
357
385
|
if (current !== precomputedSource) {
|
|
358
386
|
precomputedSource = current;
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
387
|
+
// buildPrecomputedByPrefix drops any staticPrefix owned by more than one
|
|
388
|
+
// leaf include instead of collapsing it last-wins (which would mis-assign
|
|
389
|
+
// one include's routes to another's entry and 500 a valid sibling route).
|
|
390
|
+
// Such shared-prefix includes resolve via the handler path instead.
|
|
391
|
+
precomputedByPrefix = current ? buildPrecomputedByPrefix(current) : null;
|
|
362
392
|
}
|
|
363
393
|
return precomputedByPrefix;
|
|
364
394
|
}
|
|
@@ -526,7 +556,9 @@ export function createRouter<TEnv = any>(
|
|
|
526
556
|
trackHandler,
|
|
527
557
|
findNearestErrorBoundary,
|
|
528
558
|
findNearestNotFoundBoundary,
|
|
559
|
+
notFoundComponent: notFound,
|
|
529
560
|
callOnError,
|
|
561
|
+
viewTransitionDefault: viewTransitionOption,
|
|
530
562
|
};
|
|
531
563
|
|
|
532
564
|
// Match API dependencies
|
|
@@ -560,6 +592,7 @@ export function createRouter<TEnv = any>(
|
|
|
560
592
|
mergedRouteMap,
|
|
561
593
|
nextMountIndex: () => mountIndex++,
|
|
562
594
|
getPrecomputedByPrefix,
|
|
595
|
+
routerId,
|
|
563
596
|
};
|
|
564
597
|
|
|
565
598
|
function evaluateLazyEntry(entry: RouteEntry<TEnv>): void {
|
|
@@ -613,6 +646,8 @@ export function createRouter<TEnv = any>(
|
|
|
613
646
|
params: Record<string, string>,
|
|
614
647
|
buildVars?: Record<string, any>,
|
|
615
648
|
isPassthroughRoute?: boolean,
|
|
649
|
+
buildEnv?: TEnv,
|
|
650
|
+
devMode?: boolean,
|
|
616
651
|
) {
|
|
617
652
|
return _matchForPrerender(
|
|
618
653
|
pathname,
|
|
@@ -620,6 +655,8 @@ export function createRouter<TEnv = any>(
|
|
|
620
655
|
prerenderDeps,
|
|
621
656
|
buildVars,
|
|
622
657
|
isPassthroughRoute,
|
|
658
|
+
buildEnv,
|
|
659
|
+
devMode,
|
|
623
660
|
);
|
|
624
661
|
}
|
|
625
662
|
|
|
@@ -627,12 +664,16 @@ export function createRouter<TEnv = any>(
|
|
|
627
664
|
handler: Function,
|
|
628
665
|
handlerId: string,
|
|
629
666
|
routeName?: string,
|
|
667
|
+
buildEnv?: TEnv,
|
|
668
|
+
devMode?: boolean,
|
|
630
669
|
) {
|
|
631
670
|
return _renderStaticSegment<TEnv>(
|
|
632
671
|
handler,
|
|
633
672
|
handlerId,
|
|
634
673
|
mergedRouteMap,
|
|
635
674
|
routeName,
|
|
675
|
+
buildEnv,
|
|
676
|
+
devMode,
|
|
636
677
|
);
|
|
637
678
|
}
|
|
638
679
|
|
|
@@ -645,6 +686,7 @@ export function createRouter<TEnv = any>(
|
|
|
645
686
|
findMatch,
|
|
646
687
|
findInterceptForRoute,
|
|
647
688
|
telemetry: telemetrySink,
|
|
689
|
+
cacheSignalEnabled,
|
|
648
690
|
});
|
|
649
691
|
|
|
650
692
|
const { match, matchPartial, matchError, previewMatch } = matchHandlers;
|
|
@@ -654,11 +696,18 @@ export function createRouter<TEnv = any>(
|
|
|
654
696
|
* The type system tracks accumulated routes through the builder chain
|
|
655
697
|
* Initial TRoutes is {} (empty) to avoid poisoning accumulated types with Record<string, string>
|
|
656
698
|
*/
|
|
657
|
-
const router:
|
|
699
|
+
const router: RangoInternal<TEnv, {}> = {
|
|
658
700
|
__brand: RSC_ROUTER_BRAND,
|
|
659
701
|
id: routerId,
|
|
702
|
+
basename,
|
|
703
|
+
|
|
704
|
+
routes(patternsOrBuilder: UrlPatterns<TEnv> | UrlBuilder<TEnv>): any {
|
|
705
|
+
// Wrap builder functions in urls() automatically
|
|
706
|
+
const urlPatterns: UrlPatterns<TEnv> =
|
|
707
|
+
typeof patternsOrBuilder === "function"
|
|
708
|
+
? (urls(patternsOrBuilder) as UrlPatterns<TEnv>)
|
|
709
|
+
: patternsOrBuilder;
|
|
660
710
|
|
|
661
|
-
routes(urlPatterns: UrlPatterns<TEnv>): any {
|
|
662
711
|
// Store reference for runtime manifest generation
|
|
663
712
|
storedUrlPatterns = urlPatterns;
|
|
664
713
|
const currentMountIndex = mountIndex++;
|
|
@@ -689,13 +738,13 @@ export function createRouter<TEnv = any>(
|
|
|
689
738
|
errorBoundary: [],
|
|
690
739
|
notFoundBoundary: [],
|
|
691
740
|
layout: [],
|
|
692
|
-
parallel:
|
|
741
|
+
parallel: {},
|
|
693
742
|
intercept: [],
|
|
694
743
|
loader: [],
|
|
695
744
|
};
|
|
696
745
|
|
|
697
746
|
let handlerResult: AllUseItems[] = [];
|
|
698
|
-
|
|
747
|
+
RangoContext.run(
|
|
699
748
|
{
|
|
700
749
|
manifest,
|
|
701
750
|
patterns: routePatterns,
|
|
@@ -706,6 +755,10 @@ export function createRouter<TEnv = any>(
|
|
|
706
755
|
counters: {},
|
|
707
756
|
mountIndex: currentMountIndex,
|
|
708
757
|
cacheProfiles: resolvedCacheProfiles,
|
|
758
|
+
// basename sets the initial URL prefix so all path() patterns
|
|
759
|
+
// are registered with the prefix (e.g. "/admin" + "/users" = "/admin/users").
|
|
760
|
+
// No namePrefix — route names stay unprefixed.
|
|
761
|
+
...(basename ? { urlPrefix: basename } : {}),
|
|
709
762
|
},
|
|
710
763
|
() => {
|
|
711
764
|
handlerResult = urlPatterns.handler() as AllUseItems[];
|
|
@@ -725,7 +778,7 @@ export function createRouter<TEnv = any>(
|
|
|
725
778
|
if (entry.type === "route" && entry.isPrerender) {
|
|
726
779
|
if (!prerenderRouteKeys) prerenderRouteKeys = new Set();
|
|
727
780
|
prerenderRouteKeys.add(name);
|
|
728
|
-
if (entry.
|
|
781
|
+
if (entry.isPassthrough === true) {
|
|
729
782
|
if (!passthroughRouteKeys) passthroughRouteKeys = new Set();
|
|
730
783
|
passthroughRouteKeys.add(name);
|
|
731
784
|
}
|
|
@@ -751,6 +804,7 @@ export function createRouter<TEnv = any>(
|
|
|
751
804
|
trailingSlash: trailingSlashConfig,
|
|
752
805
|
handler: urlPatterns.handler,
|
|
753
806
|
mountIndex: currentMountIndex,
|
|
807
|
+
routerId,
|
|
754
808
|
cacheProfiles: resolvedCacheProfiles,
|
|
755
809
|
...(prerenderRouteKeys ? { prerenderRouteKeys } : {}),
|
|
756
810
|
...(passthroughRouteKeys ? { passthroughRouteKeys } : {}),
|
|
@@ -770,6 +824,7 @@ export function createRouter<TEnv = any>(
|
|
|
770
824
|
trailingSlash: trailingSlashConfig,
|
|
771
825
|
handler: urlPatterns.handler,
|
|
772
826
|
mountIndex: currentMountIndex,
|
|
827
|
+
routerId,
|
|
773
828
|
cacheProfiles: resolvedCacheProfiles,
|
|
774
829
|
...(prerenderRouteKeys ? { prerenderRouteKeys } : {}),
|
|
775
830
|
...(passthroughRouteKeys ? { passthroughRouteKeys } : {}),
|
|
@@ -801,10 +856,13 @@ export function createRouter<TEnv = any>(
|
|
|
801
856
|
|
|
802
857
|
// Create placeholder RouteEntry for each lazy include
|
|
803
858
|
for (const lazyInclude of lazyIncludes) {
|
|
804
|
-
// Compute the full URL prefix (combining parent prefix if any)
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
859
|
+
// Compute the full URL prefix (combining parent prefix if any). Use the
|
|
860
|
+
// slash-collapsing join so a trailing-slash parent prefix does not
|
|
861
|
+
// produce a double-slash staticPrefix the trie's sp can never match.
|
|
862
|
+
const fullPrefix = joinPrefix(
|
|
863
|
+
lazyInclude.context.urlPrefix,
|
|
864
|
+
lazyInclude.prefix,
|
|
865
|
+
);
|
|
808
866
|
|
|
809
867
|
const lazyEntry: RouteEntry<TEnv> & { _lazyPrefix?: string } = {
|
|
810
868
|
prefix: "",
|
|
@@ -813,6 +871,7 @@ export function createRouter<TEnv = any>(
|
|
|
813
871
|
trailingSlash: trailingSlashConfig,
|
|
814
872
|
handler: urlPatterns.handler,
|
|
815
873
|
mountIndex: mountIndex++,
|
|
874
|
+
routerId,
|
|
816
875
|
// Lazy evaluation fields
|
|
817
876
|
lazy: true,
|
|
818
877
|
lazyPatterns: lazyInclude.patterns,
|
|
@@ -851,8 +910,18 @@ export function createRouter<TEnv = any>(
|
|
|
851
910
|
patternOrMiddleware: string | MiddlewareFn<TEnv>,
|
|
852
911
|
middleware?: MiddlewareFn<TEnv>,
|
|
853
912
|
): any {
|
|
854
|
-
//
|
|
855
|
-
|
|
913
|
+
// Auto-prefix pattern with basename so router-level middleware
|
|
914
|
+
// patterns are router-relative (e.g. "/users/*" matches "/app/users/*").
|
|
915
|
+
if (basename && typeof patternOrMiddleware === "string") {
|
|
916
|
+
const pattern = patternOrMiddleware;
|
|
917
|
+
const prefixed =
|
|
918
|
+
pattern === "/*" || pattern === "*"
|
|
919
|
+
? `${basename}/*`
|
|
920
|
+
: `${basename}${pattern}`;
|
|
921
|
+
addMiddleware(prefixed, middleware, null);
|
|
922
|
+
} else {
|
|
923
|
+
addMiddleware(patternOrMiddleware, middleware, null);
|
|
924
|
+
}
|
|
856
925
|
return router;
|
|
857
926
|
},
|
|
858
927
|
|
|
@@ -889,6 +958,10 @@ export function createRouter<TEnv = any>(
|
|
|
889
958
|
prefetchCacheControl,
|
|
890
959
|
prefetchCacheTTL,
|
|
891
960
|
|
|
961
|
+
// Expose the resolved rango state cookie name for the server-side writer
|
|
962
|
+
// (invalidateClientCache) and for shipping to the client in metadata.
|
|
963
|
+
resolvedStateCookieName,
|
|
964
|
+
|
|
892
965
|
// Expose warmup enabled flag for handler and client
|
|
893
966
|
warmupEnabled,
|
|
894
967
|
|
|
@@ -953,6 +1026,16 @@ export function createRouter<TEnv = any>(
|
|
|
953
1026
|
// Expose source file for per-router type generation
|
|
954
1027
|
__sourceFile,
|
|
955
1028
|
|
|
1029
|
+
// Expose basename for runtime manifest generation
|
|
1030
|
+
__basename: basename,
|
|
1031
|
+
|
|
1032
|
+
// Expose router-level boundary defaults for build-time clientChunks
|
|
1033
|
+
// discovery (so a "use client" default boundary lands in app-fallback).
|
|
1034
|
+
// These are createRouter options, never pushed onto EntryData.
|
|
1035
|
+
__defaultErrorBoundary: defaultErrorBoundary,
|
|
1036
|
+
__defaultNotFoundBoundary: defaultNotFoundBoundary,
|
|
1037
|
+
__notFound: notFound,
|
|
1038
|
+
|
|
956
1039
|
// RSC request handler (lazily created on first call)
|
|
957
1040
|
fetch: (() => {
|
|
958
1041
|
// Handler is created on first call and reused
|
|
@@ -970,8 +1053,10 @@ export function createRouter<TEnv = any>(
|
|
|
970
1053
|
if (!handler) {
|
|
971
1054
|
// Lazy import deferred to first request to avoid dev mode issues
|
|
972
1055
|
const { createRSCHandler } = await import("./rsc/handler.js");
|
|
973
|
-
// Cast:
|
|
974
|
-
//
|
|
1056
|
+
// Cast: createRSCHandler receives `router as any`, which erases TEnv
|
|
1057
|
+
// and infers its handler as RouterRequestInput<unknown>. Re-narrow the
|
|
1058
|
+
// returned handler to RouterRequestInput<TEnv> so the call below stays
|
|
1059
|
+
// typed. (The handler already accepts (request, RouterRequestInput).)
|
|
975
1060
|
handler = createRSCHandler({
|
|
976
1061
|
router: router as any,
|
|
977
1062
|
cache,
|
|
@@ -986,6 +1071,10 @@ export function createRouter<TEnv = any>(
|
|
|
986
1071
|
};
|
|
987
1072
|
})(),
|
|
988
1073
|
|
|
1074
|
+
// Low-level route matching for request classification
|
|
1075
|
+
findMatch: (pathname: string, metricsStore?: any) =>
|
|
1076
|
+
findMatch(pathname, metricsStore),
|
|
1077
|
+
|
|
989
1078
|
// Debug utility for manifest inspection
|
|
990
1079
|
debugManifest: () => buildDebugManifest<TEnv>(routesEntries),
|
|
991
1080
|
};
|
|
@@ -994,8 +1083,10 @@ export function createRouter<TEnv = any>(
|
|
|
994
1083
|
RouterRegistry.set(routerId, router);
|
|
995
1084
|
|
|
996
1085
|
// If urls option was provided, auto-register them
|
|
997
|
-
if (urlsOption) {
|
|
998
|
-
return router.routes(urlsOption) as
|
|
1086
|
+
if (typeof urlsOption === "function") {
|
|
1087
|
+
return router.routes(urlsOption) as Rango<TEnv, {}>;
|
|
1088
|
+
} else if (urlsOption) {
|
|
1089
|
+
return router.routes(urlsOption) as Rango<TEnv, {}>;
|
|
999
1090
|
}
|
|
1000
1091
|
|
|
1001
1092
|
return router;
|
|
@@ -6,14 +6,14 @@
|
|
|
6
6
|
* RSC rendering) so they can be standalone modules without closure coupling.
|
|
7
7
|
*/
|
|
8
8
|
|
|
9
|
-
import type {
|
|
9
|
+
import type { RangoInternal } from "../router/router-interfaces.js";
|
|
10
10
|
import type { ErrorPhase } from "../types.js";
|
|
11
11
|
import type { InvokeOnErrorContext } from "../router/error-handling.js";
|
|
12
12
|
import type { RSCDependencies, LoadSSRModule } from "./types.js";
|
|
13
13
|
import type { SSRStreamMode } from "../router/router-options.js";
|
|
14
14
|
|
|
15
15
|
export interface HandlerContext<TEnv = unknown> {
|
|
16
|
-
router:
|
|
16
|
+
router: RangoInternal<TEnv, any>;
|
|
17
17
|
version: string;
|
|
18
18
|
renderToReadableStream: RSCDependencies["renderToReadableStream"];
|
|
19
19
|
decodeReply: RSCDependencies["decodeReply"];
|
|
@@ -31,6 +31,7 @@ export interface HandlerContext<TEnv = unknown> {
|
|
|
31
31
|
createRedirectFlightResponse: (
|
|
32
32
|
redirectUrl: string,
|
|
33
33
|
locationState?: Record<string, unknown>,
|
|
34
|
+
external?: boolean,
|
|
34
35
|
) => Response;
|
|
35
36
|
|
|
36
37
|
/**
|