@rangojs/router 0.24.4 → 0.26.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.
- package/README.md +1 -0
- package/dist/bin/rango.js +363 -39
- package/dist/testing/vitest.js +37 -4
- package/dist/types/browser/event-controller.d.ts +24 -5
- package/dist/types/browser/intercept-utils.d.ts +5 -2
- package/dist/types/browser/merge-segment-loaders.d.ts +0 -23
- package/dist/types/browser/navigation-transaction.d.ts +5 -5
- package/dist/types/browser/partial-update.d.ts +21 -13
- package/dist/types/browser/prefetch/cache.d.ts +8 -0
- package/dist/types/browser/rango-marker.d.ts +7 -0
- package/dist/types/browser/react/filter-segment-order.d.ts +10 -0
- package/dist/types/browser/react/use-handle.d.ts +20 -0
- package/dist/types/browser/react/use-href.d.ts +6 -0
- package/dist/types/browser/react/use-router.d.ts +6 -1
- package/dist/types/browser/response-adapter.d.ts +5 -3
- package/dist/types/browser/scroll-restoration.d.ts +9 -3
- package/dist/types/browser/segment-reconciler.d.ts +10 -13
- package/dist/types/browser/types.d.ts +38 -8
- package/dist/types/build/route-types/per-module-writer.d.ts +12 -0
- package/dist/types/cache/cf/cf-cache-store.d.ts +0 -2
- package/dist/types/cache/cf/cf-cache-types.d.ts +0 -16
- package/dist/types/cache/cf/cf-shell-frame.d.ts +2 -0
- package/dist/types/cache/handle-snapshot.d.ts +2 -2
- package/dist/types/cache/types.d.ts +16 -6
- package/dist/types/cache/vercel/vercel-cache-store.d.ts +1 -15
- package/dist/types/client-urls/client-urls.d.ts +6 -2
- package/dist/types/client-urls/revalidate-registry.d.ts +1 -1
- package/dist/types/client-urls/server-projection.d.ts +9 -5
- package/dist/types/client-urls/types.d.ts +29 -16
- package/dist/types/client.d.ts +2 -2
- package/dist/types/client.rsc.d.ts +2 -2
- package/dist/types/decode-loader-results.d.ts +28 -7
- package/dist/types/handles/deferred-resolution.d.ts +3 -2
- package/dist/types/handles/meta.d.ts +5 -0
- package/dist/types/href-client.d.ts +3 -1
- package/dist/types/index.rsc.d.ts +1 -1
- package/dist/types/loader-redirect.d.ts +2 -3
- package/dist/types/outlet-context.d.ts +7 -6
- package/dist/types/prefetch-markers.d.ts +14 -5
- package/dist/types/prerender/build-shell-capture.d.ts +1 -2
- package/dist/types/prerender/writable-store.d.ts +2 -3
- package/dist/types/route-content-wrapper.d.ts +17 -14
- package/dist/types/route-definition/helpers-types.d.ts +7 -2
- package/dist/types/route-definition/resolve-handler-use.d.ts +6 -1
- package/dist/types/route-definition/rewrite.d.ts +48 -5
- package/dist/types/route-types.d.ts +2 -2
- package/dist/types/router/handler-context.d.ts +14 -2
- package/dist/types/router/intercept-resolution.d.ts +19 -46
- package/dist/types/router/lazy-includes.d.ts +7 -0
- package/dist/types/router/match-middleware/intercept-resolution.d.ts +2 -2
- package/dist/types/router/middleware.d.ts +0 -16
- package/dist/types/router/navigation-snapshot.d.ts +2 -0
- package/dist/types/router/prefetch-cache-ttl.d.ts +8 -11
- package/dist/types/router/revalidation.d.ts +8 -1
- package/dist/types/router/router-context.d.ts +4 -16
- package/dist/types/router/router-interfaces.d.ts +0 -11
- package/dist/types/router/router-options.d.ts +4 -27
- package/dist/types/router/segment-resolution/mask-nested.d.ts +5 -3
- package/dist/types/router/segment-resolution/prefetch-deferral.d.ts +31 -8
- package/dist/types/router/segment-resolution/revalidation.d.ts +38 -4
- package/dist/types/router/segment-resolution.d.ts +1 -1
- package/dist/types/router/segment-wrappers.d.ts +3 -5
- package/dist/types/router/substitute-pattern-params.d.ts +3 -2
- package/dist/types/router/tracing.d.ts +2 -2
- package/dist/types/router-versions.d.ts +8 -6
- package/dist/types/rsc/full-payload.d.ts +14 -2
- package/dist/types/rsc/helpers.d.ts +8 -0
- package/dist/types/rsc/manifest-init.d.ts +20 -0
- package/dist/types/rsc/prefetch-render-error.d.ts +22 -0
- package/dist/types/rsc/progressive-enhancement.d.ts +20 -0
- package/dist/types/rsc/rewrite-passes.d.ts +12 -2
- package/dist/types/rsc/server-action.d.ts +6 -0
- package/dist/types/rsc/shell-capture-constants.d.ts +14 -4
- package/dist/types/rsc/shell-capture.d.ts +23 -2
- package/dist/types/rsc/types.d.ts +5 -8
- package/dist/types/segment-system.d.ts +15 -0
- package/dist/types/server/build-version-table.d.ts +10 -13
- package/dist/types/server/context.d.ts +90 -6
- package/dist/types/server/handle-store.d.ts +17 -6
- package/dist/types/server/request-context.d.ts +45 -7
- package/dist/types/server/request-headers.d.ts +12 -0
- package/dist/types/server/rewrite-trail.d.ts +8 -1
- package/dist/types/testing/build-versions.d.ts +0 -3
- package/dist/types/testing/e2e/index.d.ts +1 -1
- package/dist/types/testing/flight.entry.d.ts +1 -1
- package/dist/types/testing/index.d.ts +1 -1
- package/dist/types/testing/internal/client-urls-projection.d.ts +4 -3
- package/dist/types/testing/internal/seed-vars.d.ts +4 -4
- package/dist/types/testing/render-route.d.ts +21 -11
- package/dist/types/testing/run-loader.d.ts +7 -0
- package/dist/types/testing/run-middleware.d.ts +7 -0
- package/dist/types/testing/run-revalidate.d.ts +5 -4
- package/dist/types/testing/serve-shell-request.d.ts +42 -5
- package/dist/types/testing/shell-status.d.ts +17 -0
- package/dist/types/testing/vitest-stubs/version.d.ts +1 -0
- package/dist/types/testing/vitest.d.ts +10 -1
- package/dist/types/thenable-status.d.ts +0 -6
- package/dist/types/types/handler-context.d.ts +12 -1
- package/dist/types/types/loader-types.d.ts +10 -4
- package/dist/types/types/route-entry.d.ts +2 -1
- package/dist/types/urls/path-helper-types.d.ts +4 -2
- package/dist/types/vite/discovery/client-urls-projection.d.ts +55 -5
- package/dist/types/vite/discovery/state.d.ts +20 -0
- package/dist/types/vite/plugins/client-urls-revalidate-hoist.d.ts +28 -16
- package/dist/types/vite/plugins/hoist/source.d.ts +8 -7
- package/dist/types/vite/plugins/virtual-entries.d.ts +6 -0
- package/dist/types/vite/utils/prerender-utils.d.ts +7 -0
- package/dist/vite/index.js +6819 -6555
- package/package.json +1 -1
- package/skills/app-structure/SKILL.md +255 -0
- package/skills/app-structure/content-site.md +333 -0
- package/skills/app-structure/e-commerce.md +435 -0
- package/skills/app-structure/large-app.md +885 -0
- package/skills/app-structure/multi-app.md +280 -0
- package/skills/breadcrumbs/SKILL.md +6 -1
- package/skills/cache-guide/SKILL.md +4 -8
- package/skills/caching/SKILL.md +6 -6
- package/skills/catalog.json +12 -0
- package/skills/client-urls/SKILL.md +185 -32
- package/skills/comparison/references/framework-comparison.md +1 -1
- package/skills/composability/SKILL.md +10 -8
- package/skills/handler-use/SKILL.md +48 -9
- package/skills/hooks/handle-and-actions.md +104 -0
- package/skills/hooks/navigation.md +24 -10
- package/skills/hooks/urls.md +1 -1
- package/skills/host-router/SKILL.md +1 -1
- package/skills/i18n/SKILL.md +2 -1
- package/skills/intercept/SKILL.md +60 -29
- package/skills/layout/SKILL.md +6 -3
- package/skills/links/SKILL.md +151 -17
- package/skills/loader/SKILL.md +42 -19
- package/skills/middleware/SKILL.md +111 -15
- package/skills/observability/SKILL.md +11 -0
- package/skills/parallel/SKILL.md +5 -5
- package/skills/ppr/SKILL.md +103 -52
- package/skills/prerender/SKILL.md +4 -5
- package/skills/rango/SKILL.md +3 -0
- package/skills/response-routes/SKILL.md +4 -1
- package/skills/router-setup/SKILL.md +0 -2
- package/skills/scripts/SKILL.md +12 -1
- package/skills/server-actions/SKILL.md +60 -20
- package/skills/testing/SKILL.md +1 -0
- package/skills/testing/client-components.md +13 -10
- package/skills/testing/loader.md +25 -24
- package/skills/testing/middleware.md +11 -11
- package/skills/testing/render-handler.md +17 -17
- package/skills/testing/response-routes.md +4 -1
- package/skills/testing/serve-shell-request.md +86 -22
- package/skills/testing/server-actions.md +16 -16
- package/skills/ux-architecture/SKILL.md +980 -0
- package/skills/vercel/SKILL.md +1 -1
- package/skills/view-transitions/SKILL.md +43 -10
- package/src/__augment-tests__/augmented.check.ts +28 -0
- package/src/browser/event-controller.ts +44 -18
- package/src/browser/intercept-utils.ts +3 -2
- package/src/browser/merge-segment-loaders.ts +0 -85
- package/src/browser/navigation-bridge.ts +112 -84
- package/src/browser/navigation-client.ts +20 -15
- package/src/browser/navigation-store.ts +4 -2
- package/src/browser/navigation-transaction.ts +9 -8
- package/src/browser/partial-update.ts +90 -32
- package/src/browser/prefetch/cache.ts +8 -0
- package/src/browser/prefetch/fetch.ts +13 -3
- package/src/browser/rango-marker.ts +13 -0
- package/src/browser/react/NavigationProvider.tsx +25 -7
- package/src/browser/react/filter-segment-order.ts +13 -0
- package/src/browser/react/use-action.ts +9 -15
- package/src/browser/react/use-handle.ts +63 -71
- package/src/browser/react/use-href.tsx +24 -5
- package/src/browser/react/use-link-status.ts +1 -1
- package/src/browser/react/use-navigation.ts +30 -40
- package/src/browser/react/use-router.ts +37 -6
- package/src/browser/react/use-segments.ts +8 -12
- package/src/browser/response-adapter.ts +11 -5
- package/src/browser/rsc-router.tsx +3 -1
- package/src/browser/scroll-restoration.ts +34 -20
- package/src/browser/segment-reconciler.ts +11 -29
- package/src/browser/server-action-bridge.ts +52 -16
- package/src/browser/types.ts +40 -8
- package/src/build/generate-manifest.ts +12 -1
- package/src/build/route-types/codegen.ts +6 -2
- package/src/build/route-types/per-module-writer.ts +94 -61
- package/src/cache/cache-runtime.ts +9 -0
- package/src/cache/cache-scope.ts +2 -1
- package/src/cache/cf/cf-cache-store.ts +6 -7
- package/src/cache/cf/cf-cache-types.ts +0 -17
- package/src/cache/cf/cf-shell-frame.ts +3 -0
- package/src/cache/handle-snapshot.ts +2 -2
- package/src/cache/types.ts +16 -6
- package/src/cache/vercel/vercel-cache-store.ts +8 -19
- package/src/client-urls/client-urls.ts +202 -153
- package/src/client-urls/revalidate-registry.ts +12 -3
- package/src/client-urls/server-projection.ts +137 -66
- package/src/client-urls/types.ts +30 -15
- package/src/client.rsc.tsx +11 -1
- package/src/client.tsx +9 -1
- package/src/decode-loader-results.ts +64 -31
- package/src/handles/deferred-resolution.ts +3 -2
- package/src/handles/meta.ts +5 -0
- package/src/href-client.ts +3 -1
- package/src/index.rsc.ts +1 -0
- package/src/index.ts +12 -4
- package/src/loader-redirect.tsx +2 -3
- package/src/outlet-context.ts +7 -6
- package/src/prefetch-markers.ts +15 -5
- package/src/prerender/build-shell-capture.ts +1 -2
- package/src/prerender/writable-store.ts +2 -3
- package/src/reverse.ts +3 -3
- package/src/route-content-wrapper.tsx +19 -17
- package/src/route-definition/dsl-helpers.ts +41 -21
- package/src/route-definition/helpers-types.ts +7 -2
- package/src/route-definition/resolve-handler-use.ts +23 -10
- package/src/route-definition/rewrite.ts +86 -19
- package/src/route-types.ts +1 -2
- package/src/router/find-match.ts +37 -1
- package/src/router/handler-context.ts +85 -40
- package/src/router/intercept-resolution.ts +161 -307
- package/src/router/lazy-includes.ts +43 -27
- package/src/router/loader-resolution.ts +21 -1
- package/src/router/manifest.ts +15 -10
- package/src/router/match-api.ts +11 -1
- package/src/router/match-middleware/background-revalidation.ts +2 -4
- package/src/router/match-middleware/cache-lookup.ts +16 -20
- package/src/router/match-middleware/intercept-resolution.ts +41 -60
- package/src/router/match-result.ts +31 -2
- package/src/router/middleware.ts +6 -147
- package/src/router/navigation-snapshot.ts +38 -2
- package/src/router/prefetch-cache-ttl.ts +10 -18
- package/src/router/prerender-match.ts +2 -1
- package/src/router/revalidation.ts +24 -3
- package/src/router/router-context.ts +5 -18
- package/src/router/router-interfaces.ts +0 -13
- package/src/router/router-options.ts +4 -28
- package/src/router/segment-resolution/fresh.ts +6 -2
- package/src/router/segment-resolution/helpers.ts +7 -1
- package/src/router/segment-resolution/loader-cache.ts +4 -3
- package/src/router/segment-resolution/mask-nested.ts +5 -3
- package/src/router/segment-resolution/prefetch-deferral.ts +62 -12
- package/src/router/segment-resolution/revalidation.ts +75 -35
- package/src/router/segment-resolution.ts +0 -1
- package/src/router/segment-wrappers.ts +8 -13
- package/src/router/substitute-pattern-params.ts +3 -2
- package/src/router/tracing.ts +2 -2
- package/src/router-versions.ts +7 -7
- package/src/router.ts +5 -17
- package/src/rsc/full-payload.ts +26 -4
- package/src/rsc/handler.ts +86 -48
- package/src/rsc/helpers.ts +13 -0
- package/src/rsc/manifest-init.ts +56 -3
- package/src/rsc/prefetch-render-error.ts +38 -0
- package/src/rsc/progressive-enhancement.ts +161 -211
- package/src/rsc/rewrite-passes.ts +56 -9
- package/src/rsc/rsc-rendering.ts +79 -23
- package/src/rsc/server-action.ts +25 -2
- package/src/rsc/shell-capture-constants.ts +26 -3
- package/src/rsc/shell-capture.ts +137 -51
- package/src/rsc/types.ts +5 -9
- package/src/segment-system.tsx +125 -119
- package/src/server/build-version-table.ts +12 -24
- package/src/server/context.ts +160 -7
- package/src/server/handle-store.ts +80 -12
- package/src/server/request-context.ts +46 -6
- package/src/server/request-headers.ts +32 -0
- package/src/server/rewrite-trail.ts +55 -9
- package/src/ssr/ssr-root.tsx +6 -10
- package/src/testing/build-versions.ts +0 -3
- package/src/testing/dispatch.ts +5 -8
- package/src/testing/e2e/index.ts +1 -0
- package/src/testing/flight.entry.ts +1 -0
- package/src/testing/index.ts +1 -0
- package/src/testing/internal/client-urls-projection.ts +31 -11
- package/src/testing/internal/seed-vars.ts +4 -4
- package/src/testing/render-route.tsx +83 -40
- package/src/testing/run-loader.ts +26 -2
- package/src/testing/run-middleware.ts +10 -0
- package/src/testing/run-revalidate.ts +13 -6
- package/src/testing/serve-shell-request.ts +79 -9
- package/src/testing/shell-status.ts +40 -0
- package/src/testing/vitest-stubs/version.ts +1 -0
- package/src/testing/vitest.ts +74 -7
- package/src/thenable-status.ts +0 -11
- package/src/types/handler-context.ts +12 -1
- package/src/types/loader-types.ts +10 -4
- package/src/types/route-entry.ts +2 -1
- package/src/urls/include-helper.ts +38 -11
- package/src/urls/path-helper-types.ts +4 -2
- package/src/vite/discovery/client-urls-projection.ts +205 -16
- package/src/vite/discovery/discover-routers.ts +2 -2
- package/src/vite/discovery/prerender-collection.ts +2 -6
- package/src/vite/discovery/shell-prerender-phase.ts +1 -5
- package/src/vite/discovery/state.ts +26 -0
- package/src/vite/plugins/client-urls-revalidate-hoist.ts +190 -77
- package/src/vite/plugins/expose-internal-ids.ts +46 -40
- package/src/vite/plugins/hoist/source.ts +8 -7
- package/src/vite/plugins/transition-when-hoist.ts +1 -0
- package/src/vite/plugins/version-plugin.ts +7 -0
- package/src/vite/plugins/version.d.ts +7 -0
- package/src/vite/plugins/virtual-entries.ts +20 -0
- package/src/vite/rango.ts +4 -1
- package/src/vite/router-discovery.ts +39 -7
- package/src/vite/utils/prerender-utils.ts +17 -0
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A prefetch whose render reported an error is not kept (#1170).
|
|
3
|
+
*
|
|
4
|
+
* WHY: its 200 left with the headers before a streamed part failed, so the
|
|
5
|
+
* client stored the error boundary as a healthy prefetch, served it to a
|
|
6
|
+
* click and respawned it. The status cannot change any more, and the body
|
|
7
|
+
* cannot end with an error: workerd delivers an errored body as a clean end,
|
|
8
|
+
* and in Chromium the error drops the rows a click that adopted the prefetch
|
|
9
|
+
* has not decoded yet (a Flight "network error" in place of the page).
|
|
10
|
+
*
|
|
11
|
+
* So the body ends cleanly with one more row, PREFETCH_FAILED_ROW, which the
|
|
12
|
+
* Flight decoder skips and teeWithCompletion (browser/response-adapter.ts)
|
|
13
|
+
* reads as a stream that did not end cleanly: the client evicts the prefetch
|
|
14
|
+
* and never respawns it. Prefetch responses carry no Cache-Control, so the
|
|
15
|
+
* browser HTTP cache keeps none of it either.
|
|
16
|
+
*
|
|
17
|
+
* The errors are the render's `_renderErrors`: a Flight error row, a streamed
|
|
18
|
+
* handler recovered into its boundary, a loader that threw (redirect() and
|
|
19
|
+
* notFound() are not errors). Each is recorded before Flight writes the row
|
|
20
|
+
* that carries it, so the list is complete once Flight closes the stream.
|
|
21
|
+
*/
|
|
22
|
+
export declare function markPrefetchOnRenderError(response: Response, renderErrors: readonly unknown[]): Response;
|
|
@@ -7,6 +7,8 @@
|
|
|
7
7
|
*/
|
|
8
8
|
import { getRequestContext } from "../server/request-context.js";
|
|
9
9
|
import type { MiddlewareFn } from "../router/middleware.js";
|
|
10
|
+
import type { ReactFormState } from "./types.js";
|
|
11
|
+
import type { MatchResult } from "../types.js";
|
|
10
12
|
import type { HandlerContext } from "./handler-context.js";
|
|
11
13
|
export interface PeRouteMiddlewareInfo {
|
|
12
14
|
routeMiddleware?: Array<{
|
|
@@ -17,3 +19,21 @@ export interface PeRouteMiddlewareInfo {
|
|
|
17
19
|
routeReverse?: (name: string, params?: Record<string, string>, search?: Record<string, unknown>) => string;
|
|
18
20
|
}
|
|
19
21
|
export declare function handleProgressiveEnhancement<TEnv>(ctx: HandlerContext<TEnv>, request: Request, env: TEnv, url: URL, isAction: boolean, handleStore: ReturnType<typeof getRequestContext>["_handleStore"], nonce: string | undefined, routeMwInfo?: PeRouteMiddlewareInfo): Promise<Response | null>;
|
|
22
|
+
/** What a no-JS form post's action left for the re-render (`_actionRan`). */
|
|
23
|
+
export interface FormActionOutcome {
|
|
24
|
+
reactFormState: ReactFormState | null;
|
|
25
|
+
directActionId: string | null;
|
|
26
|
+
/** The action threw, or the form body did not parse. */
|
|
27
|
+
failure?: PeFailure;
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* A failed no-JS form post and the error boundary matched for it. The boundary
|
|
31
|
+
* renders in place of the page, inside route middleware as the JS path renders
|
|
32
|
+
* its own (server-action.ts `errorBoundary`). With none, the page re-renders
|
|
33
|
+
* with 500, the JS path's status for the same boundaryless error.
|
|
34
|
+
*/
|
|
35
|
+
export interface PeFailure {
|
|
36
|
+
error: unknown;
|
|
37
|
+
actionId: string | null | undefined;
|
|
38
|
+
boundary: MatchResult | null;
|
|
39
|
+
}
|
|
@@ -32,8 +32,18 @@ export interface RewritePass {
|
|
|
32
32
|
/**
|
|
33
33
|
* Move the request context to `rewrite`'s target for the next pass: check
|
|
34
34
|
* that this request can be rewritten, resolve the target, count the hop,
|
|
35
|
-
* then rebase the context. Throws the site error for a
|
|
36
|
-
*
|
|
35
|
+
* then rebase the context. Throws the site error for a loader fetch, a
|
|
36
|
+
* refused mutation or one whose body middleware read before its action ran,
|
|
37
|
+
* a resolution error, and RewriteLoopError.
|
|
38
|
+
*
|
|
39
|
+
* A mutation moves too (#1145). Before its action ran (a rewrite from global
|
|
40
|
+
* middleware) it moves with its body, and the target's pass runs the action
|
|
41
|
+
* after the target's global middleware, as a direct post there would. After
|
|
42
|
+
* it ran (route middleware wraps only the re-render), the target's pass
|
|
43
|
+
* re-renders from `reqCtx._actionRan`. `disallowMutations()` refuses the
|
|
44
|
+
* first, so a lock never runs a mutation; the second is already committed,
|
|
45
|
+
* and refusing it reports an error for a write that happened, so the caller
|
|
46
|
+
* retries it.
|
|
37
47
|
*/
|
|
38
48
|
export declare function applyRewrite(rewrite: Rewrite, passRequest: Request, reqCtx: RequestContext<any>, routeMap: Record<string, string>, basename: string | undefined): RewritePass;
|
|
39
49
|
/** The response to a rewrite loop. */
|
|
@@ -53,6 +53,12 @@ export interface ActionContinuation {
|
|
|
53
53
|
* or an ActionContinuation for the revalidation phase.
|
|
54
54
|
*/
|
|
55
55
|
export declare function executeServerAction<TEnv>(ctx: HandlerContext<TEnv>, request: Request, env: TEnv, url: URL, actionId: string, handleStore: ReturnType<typeof getRequestContext>["_handleStore"]): Promise<Response | ActionContinuation>;
|
|
56
|
+
/**
|
|
57
|
+
* The continuation for a rewrite pass after the action ran (#1145): a failed
|
|
58
|
+
* action's error boundary is re-matched on the target, since the one pass 1
|
|
59
|
+
* matched (or missed) is the rewriting route's.
|
|
60
|
+
*/
|
|
61
|
+
export declare function continuationForRewritePass<TEnv>(ctx: HandlerContext<TEnv>, request: Request, env: TEnv, continuation: ActionContinuation): Promise<ActionContinuation>;
|
|
56
62
|
/**
|
|
57
63
|
* Phase 2: Revalidate after action.
|
|
58
64
|
*
|
|
@@ -41,7 +41,7 @@ export declare const PPR_REPLAY_STATUS_HEADER: string;
|
|
|
41
41
|
* producer (rsc-rendering.ts) and the parser (testing/shell-status.ts): a
|
|
42
42
|
* reason the parser does not list parses as null.
|
|
43
43
|
*/
|
|
44
|
-
export declare const PPR_REPLAY_BYPASS_REASONS: readonly ["method", "dynamic", "nonce", "store-unavailable", "passive-read-unsupported", "no-navigation-context", "prerender-store", "intercept", "cache-disabled", "read-error", "no-entry", "invalid-version", "corrupt-entry", "no-segment-snapshot", "snapshot-miss", "explicit-cache-hit"];
|
|
44
|
+
export declare const PPR_REPLAY_BYPASS_REASONS: readonly ["method", "dynamic", "nonce", "store-unavailable", "passive-read-unsupported", "no-navigation-context", "prerender-store", "intercept", "cache-disabled", "read-error", "no-entry", "invalid-version", "corrupt-entry", "no-segment-snapshot", "snapshot-miss", "explicit-cache-hit", "rewritten"];
|
|
45
45
|
/** One of {@link PPR_REPLAY_BYPASS_REASONS}. */
|
|
46
46
|
export type PprReplayBypassReason = (typeof PPR_REPLAY_BYPASS_REASONS)[number];
|
|
47
47
|
/**
|
|
@@ -84,6 +84,15 @@ export declare function buildShellKey(routerId: string, url: URL, filter?: Searc
|
|
|
84
84
|
* replayed to gold's navigations. Encoded, it holds no `:` or `|`.
|
|
85
85
|
*/
|
|
86
86
|
export declare function partitionShellKey(key: string, partition: string): string;
|
|
87
|
+
/**
|
|
88
|
+
* The shell key of a `rewrite(...).shell("visitor")` request: the visitor's
|
|
89
|
+
* URL, partitioned by `rw:` + the target's path and search (both searches
|
|
90
|
+
* filtered and sorted, shellSearchSeed). The visitor's URL keeps two public
|
|
91
|
+
* URLs of one target apart; the target keeps a conditional rewrite (an A/B
|
|
92
|
+
* arm, a lock) apart from the URL's own shell. The route's own partition
|
|
93
|
+
* composes after it.
|
|
94
|
+
*/
|
|
95
|
+
export declare function visitorShellKey(routerId: string, visitor: URL, target: URL, filter?: SearchParamsFilter): string;
|
|
87
96
|
/**
|
|
88
97
|
* The navigation-only entry beside a document shell key (a cold partial
|
|
89
98
|
* request's capture, rsc-rendering.ts). A suffix after the (encoded)
|
|
@@ -139,9 +148,10 @@ export declare const SHELL_CAPTURE_TASK_HARD_CAP_MS = 25000;
|
|
|
139
148
|
* (ShellCaptureDebugEvent.refusal, `caches.refusal` on a `router.prerender()`
|
|
140
149
|
* result): `identity` (a request-scoped read: cookies(), headers(), the
|
|
141
150
|
* theme, a `{ cache: false }` variable), `dynamic` (`ctx.dynamic()`),
|
|
142
|
-
* `loader` (a `{ ssr: false }` loader rejected,
|
|
143
|
-
* redirect()/notFound()
|
|
144
|
-
*
|
|
151
|
+
* `loader` (a `{ ssr: false }` loader rejected, settled with
|
|
152
|
+
* redirect()/notFound(), or a promise it pushed rejected),
|
|
153
|
+
* `no-record` (no doc record: the route's cache() refused the write, or the
|
|
154
|
+
* handler output failed), `handles` (a pushed
|
|
145
155
|
* handle value did not finish encoding), `size` (over the store's value
|
|
146
156
|
* limit), `record-expired` (the route cache() record the capture wrote ran
|
|
147
157
|
* out first), `invalidated` (a tag of the shell was invalidated after the
|
|
@@ -330,6 +330,13 @@ export interface ShellCaptureDescriptor {
|
|
|
330
330
|
debugSink?: (event: ShellCaptureDebugEvent) => void;
|
|
331
331
|
/** Store the snapshot for navigation replay, never the captured HTML prelude. */
|
|
332
332
|
navigationOnly?: true;
|
|
333
|
+
/**
|
|
334
|
+
* Set for a shell keyed by the visitor's URL (`rewrite(...).shell("visitor")`,
|
|
335
|
+
* visitorShellKey): the capture renders the visitor's location
|
|
336
|
+
* (`RequestContext._shellCaptureForVisitor`) and stores it as
|
|
337
|
+
* ShellCacheEntry.pathname.
|
|
338
|
+
*/
|
|
339
|
+
pathname?: string;
|
|
333
340
|
/**
|
|
334
341
|
* lastStoredCaptureSeq(key) when a document request read the store and
|
|
335
342
|
* missed. The request schedules its capture only after rendering the MISS,
|
|
@@ -495,8 +502,9 @@ export type CaptureRecordOutcome = {
|
|
|
495
502
|
* component showed one value in the prelude and another on every HIT.
|
|
496
503
|
*
|
|
497
504
|
* Order, all bounded by the one capture deadline (`ppr.captureTimeout`):
|
|
498
|
-
* top-level handle promises
|
|
499
|
-
*
|
|
505
|
+
* top-level handle promises (a bake-lane loader's pushed promises among
|
|
506
|
+
* them, #1182), the handler pushes' nested promises, and the bake-lane
|
|
507
|
+
* loader containers settle first (the record encodes the handles
|
|
500
508
|
* a HIT restores, and its handle encode has its own 5s timeout that must
|
|
501
509
|
* never be the one that fires); then the capture's onResponse callbacks fire
|
|
502
510
|
* with a synthetic 200 (the implicit doc scope's cacheRoute, an explicit
|
|
@@ -522,6 +530,19 @@ export interface CaptureContextDerivation {
|
|
|
522
530
|
* record encodes its handles, so that encode never races a pending value.
|
|
523
531
|
*/
|
|
524
532
|
handlerPushesSettled: () => Promise<void>;
|
|
533
|
+
/**
|
|
534
|
+
* Every promise a bake-lane loader body pushed (#1182), in push order.
|
|
535
|
+
* The record-first step waits for them (they are in the recorded cut) and
|
|
536
|
+
* names the loader and the handle of one that rejects or misses the
|
|
537
|
+
* deadline.
|
|
538
|
+
*/
|
|
539
|
+
loaderPromisePushes: readonly LoaderPromisePush[];
|
|
540
|
+
}
|
|
541
|
+
/** A promise a bake-lane loader pushed at capture, owned by that loader. */
|
|
542
|
+
export interface LoaderPromisePush {
|
|
543
|
+
loaderId: string;
|
|
544
|
+
handleName: string;
|
|
545
|
+
state: "pending" | "fulfilled" | "rejected";
|
|
525
546
|
}
|
|
526
547
|
/**
|
|
527
548
|
* Derive the capture request context from a base context. Producer A passes
|
|
@@ -16,6 +16,11 @@ import type { ResolvedThemeConfig, Theme } from "../theme/types.js";
|
|
|
16
16
|
export interface RscPayload {
|
|
17
17
|
metadata?: {
|
|
18
18
|
pathname: string;
|
|
19
|
+
/**
|
|
20
|
+
* Path and search of the URL the route rendered for, when middleware
|
|
21
|
+
* rewrote the request there (full-payload.ts payloadLocation).
|
|
22
|
+
*/
|
|
23
|
+
rewriteTarget?: string;
|
|
19
24
|
segments: ResolvedSegment[];
|
|
20
25
|
/** Router instance ID. When this changes between navigations, the client
|
|
21
26
|
* discards cached segments and does a full tree replacement (app switch). */
|
|
@@ -328,14 +333,6 @@ export interface CreateRSCHandlerOptions<TEnv = unknown, TRoutes extends Record<
|
|
|
328
333
|
* ```
|
|
329
334
|
*/
|
|
330
335
|
cache?: HandlerCacheConfig | ((env: TEnv) => HandlerCacheConfig);
|
|
331
|
-
/**
|
|
332
|
-
* Version override for this handler. Same meaning as
|
|
333
|
-
* `createRouter({ version })`, which it takes precedence over: this exact
|
|
334
|
-
* value is used for both of the router's versions.
|
|
335
|
-
*
|
|
336
|
-
* @default createRouter({ version }), else the router's build versions
|
|
337
|
-
*/
|
|
338
|
-
version?: string;
|
|
339
336
|
/**
|
|
340
337
|
* Nonce provider for Content Security Policy (CSP).
|
|
341
338
|
*
|
|
@@ -1,6 +1,21 @@
|
|
|
1
1
|
import { type ReactNode, type ComponentType } from "react";
|
|
2
2
|
import type { ResolvedSegment, RootLayoutProps } from "./types.js";
|
|
3
3
|
export declare function restoreParallelLoaderMarkers(segments: ResolvedSegment[]): ResolvedSegment[];
|
|
4
|
+
/**
|
|
5
|
+
* An intercept's loaders arrive as loader segments of its slot
|
|
6
|
+
* (`${slot.id}D${i}.${$$id}`, router/intercept-resolution.ts). Folded back
|
|
7
|
+
* onto the slot before the tree walk, as one aggregate the slot's
|
|
8
|
+
* LoaderBoundary reads (client.tsx renderSlotContent): walked as loaders they
|
|
9
|
+
* would attach to the slot's parent, whose subtree (the page under the modal)
|
|
10
|
+
* would change shape and remount. Any other loader segment passes through; a
|
|
11
|
+
* list with nothing to fold is returned as it is, synchronously.
|
|
12
|
+
* The slot is a new object (rule 6, suspense-contract.md); its aggregate is
|
|
13
|
+
* memoized on the loaders' data (rule 1). Settled before the commit when
|
|
14
|
+
* nothing in it is deferred and the slot has no loading() or the lane settles
|
|
15
|
+
* loaders (forceAwait, action): a modal with no loading() commits whole, as
|
|
16
|
+
* when the server awaited its loaders.
|
|
17
|
+
*/
|
|
18
|
+
export declare function foldInterceptLoaders(segments: ResolvedSegment[], settleLoaders: boolean): ResolvedSegment[] | Promise<ResolvedSegment[]>;
|
|
4
19
|
/**
|
|
5
20
|
* Options for renderSegments
|
|
6
21
|
*/
|
|
@@ -2,21 +2,18 @@ import { type RouterVersions, type RouterVersionsTable } from "../router-version
|
|
|
2
2
|
/**
|
|
3
3
|
* The versions a router serves with, in order:
|
|
4
4
|
*
|
|
5
|
-
* 1.
|
|
6
|
-
*
|
|
7
|
-
* 2. The router's entry in the build table, else the whole-build entry.
|
|
8
|
-
* 3. `VERSION` for both: the dev stamp, bumped on every RSC module edit.
|
|
5
|
+
* 1. The router's entry in the build table, else the whole-build entry.
|
|
6
|
+
* 2. `VERSION` for both: the dev stamp, bumped on every RSC module edit.
|
|
9
7
|
*/
|
|
10
|
-
export declare function resolveRouterVersions(routerId: string | undefined
|
|
8
|
+
export declare function resolveRouterVersions(routerId: string | undefined): RouterVersions;
|
|
11
9
|
/**
|
|
12
10
|
* The version an on-demand prerender overlay key carries: the router's data
|
|
13
11
|
* version, because the overlay stores segment data, as the segment cache does
|
|
14
12
|
* (a client-only deploy keeps both). The write side (`router.prerender`,
|
|
15
|
-
* router.ts) and the read side (rsc/handler.ts) both call this
|
|
16
|
-
*
|
|
17
|
-
* cannot disagree; a `createRSCHandler({ version })` does not move it.
|
|
13
|
+
* router.ts) and the read side (rsc/handler.ts) both call this, so they
|
|
14
|
+
* cannot disagree.
|
|
18
15
|
*/
|
|
19
|
-
export declare function resolvePrerenderVersion(routerId: string | undefined
|
|
16
|
+
export declare function resolvePrerenderVersion(routerId: string | undefined): string;
|
|
20
17
|
/**
|
|
21
18
|
* The versions of the router serving the current request, for a cache store
|
|
22
19
|
* building a key. A store operation with no request context (a detached task
|
|
@@ -40,11 +37,11 @@ export declare function getCacheVersions(): RouterVersions;
|
|
|
40
37
|
export type KeyVersion = keyof RouterVersions | null;
|
|
41
38
|
/**
|
|
42
39
|
* The `v/{version}/` prefix of a persistent store key, or "" for an
|
|
43
|
-
* unversioned one.
|
|
44
|
-
*
|
|
45
|
-
*
|
|
40
|
+
* unversioned one. The version is the serving router's, read per operation
|
|
41
|
+
* because the cache factory builds the store before the request context
|
|
42
|
+
* exists.
|
|
46
43
|
*/
|
|
47
|
-
export declare function versionKeyPrefix(
|
|
44
|
+
export declare function versionKeyPrefix(kind: KeyVersion): string;
|
|
48
45
|
/**
|
|
49
46
|
* @internal Install a table, or restore the build's with `undefined`. A
|
|
50
47
|
* request handler resolves its router's versions once, when it is created, so
|
|
@@ -61,6 +61,12 @@ export type EntryPropCommon = {
|
|
|
61
61
|
cache?: EntryCacheConfig;
|
|
62
62
|
/** URL prefix from include() scope, used for MountContext on client */
|
|
63
63
|
mountPath?: string;
|
|
64
|
+
/**
|
|
65
|
+
* Include scope the entry's handler and loaders resolve `ctx.reverse(".name")`
|
|
66
|
+
* in. Structural entries only (layout, cache, parallel, wrapping
|
|
67
|
+
* middleware); a route resolves from its own name. See ReverseScope.
|
|
68
|
+
*/
|
|
69
|
+
reverseScope?: ReverseScope;
|
|
64
70
|
/** clientUrls() group key (PathOptions.clientGroup); route entries only. */
|
|
65
71
|
clientGroup?: string;
|
|
66
72
|
};
|
|
@@ -91,6 +97,11 @@ export type EntryPropRender = {
|
|
|
91
97
|
* on both DSL evaluations, whatever `ssr` did to `loading`.
|
|
92
98
|
*/
|
|
93
99
|
loadingPrefetch?: false;
|
|
100
|
+
/**
|
|
101
|
+
* loading(fallback, { ssr: false }), on both DSL evaluations; a document
|
|
102
|
+
* then sets `loading` to false (applyDocumentModeLoading).
|
|
103
|
+
*/
|
|
104
|
+
loadingSsr?: false;
|
|
94
105
|
transition?: TransitionConfig;
|
|
95
106
|
};
|
|
96
107
|
/**
|
|
@@ -111,7 +122,8 @@ export type LoaderEntry = {
|
|
|
111
122
|
* Resolved at DSL-evaluation time from ctx.isSSR — entries are cached
|
|
112
123
|
* per-isSSR (router/manifest.ts cache key), so the flag is already
|
|
113
124
|
* request-mode-correct when resolveLoaders (fresh.ts) reads it and never
|
|
114
|
-
* appears on navigation-lane entries.
|
|
125
|
+
* appears on navigation-lane entries. Set by documentModeLoader, which
|
|
126
|
+
* getDocumentModeEntry also applies to a lazy include's captured ancestors.
|
|
115
127
|
*/
|
|
116
128
|
awaitBeforeFlush?: true;
|
|
117
129
|
/**
|
|
@@ -129,6 +141,13 @@ export type LoaderEntry = {
|
|
|
129
141
|
* (router/segment-resolution/prefetch-deferral.ts).
|
|
130
142
|
*/
|
|
131
143
|
prefetch?: false;
|
|
144
|
+
/**
|
|
145
|
+
* The declaring layout's / parallel's / cache()'s include scope, for the
|
|
146
|
+
* loader body's `ctx.reverse(".name")` (its DSL kickoff carries it,
|
|
147
|
+
* runInsideLoaderScope). Unset on a route's loaders: they resolve from the
|
|
148
|
+
* route's name.
|
|
149
|
+
*/
|
|
150
|
+
reverseScope?: ReverseScope;
|
|
132
151
|
};
|
|
133
152
|
/**
|
|
134
153
|
* Segments state for intercept context
|
|
@@ -192,7 +211,6 @@ export type InterceptEntry = {
|
|
|
192
211
|
slotName: `@${string}`;
|
|
193
212
|
routeName: string;
|
|
194
213
|
handler: ReactNode | Handler<any, any, any>;
|
|
195
|
-
middleware: MiddlewareFn<any, any>[];
|
|
196
214
|
loader: LoaderEntry[];
|
|
197
215
|
loading?: ReactNode | false;
|
|
198
216
|
transition?: TransitionConfig;
|
|
@@ -267,10 +285,21 @@ export type EntryData = ({
|
|
|
267
285
|
/** Cache entries create cache boundaries and render like layouts (with Outlet) */
|
|
268
286
|
handler: ReactNode | Handler<any, any, any>;
|
|
269
287
|
} & EntryPropCommon & EntryPropDatas & EntryPropSegments & EntryPropRender);
|
|
288
|
+
/**
|
|
289
|
+
* Where an include()'s handler runs in the route tree. Hidden include-scope
|
|
290
|
+
* names (`$prefix_*`) derive from it, never from counter state, so build
|
|
291
|
+
* discovery and runtime expansion name every include the same (#1104).
|
|
292
|
+
*/
|
|
293
|
+
export interface IncludeScopePosition {
|
|
294
|
+
/** Sibling indexes of the enclosing includes, "_"-joined ("" at a mount root). */
|
|
295
|
+
scopePath?: string;
|
|
296
|
+
/** The scopePath tail since the nearest include that added a name segment. */
|
|
297
|
+
hiddenScopePath?: string;
|
|
298
|
+
}
|
|
270
299
|
/**
|
|
271
300
|
* Tracked include info for build-time manifest generation
|
|
272
301
|
*/
|
|
273
|
-
export interface TrackedInclude {
|
|
302
|
+
export interface TrackedInclude extends IncludeScopePosition {
|
|
274
303
|
prefix: string;
|
|
275
304
|
fullPrefix: string;
|
|
276
305
|
namePrefix?: string;
|
|
@@ -290,7 +319,7 @@ export type CachedHeaderScope = {
|
|
|
290
319
|
/**
|
|
291
320
|
* Context stored in AsyncLocalStorage
|
|
292
321
|
*/
|
|
293
|
-
interface HelperContext {
|
|
322
|
+
interface HelperContext extends IncludeScopePosition {
|
|
294
323
|
manifest: Map<string, EntryData>;
|
|
295
324
|
namespace: string;
|
|
296
325
|
parent: EntryData | null;
|
|
@@ -302,7 +331,8 @@ interface HelperContext {
|
|
|
302
331
|
* different routers don't clobber each other (route-map-builder.ts). */
|
|
303
332
|
routerId?: string;
|
|
304
333
|
metrics?: MetricsStore;
|
|
305
|
-
/** True when rendering for SSR (document requests)
|
|
334
|
+
/** True when rendering for SSR (document requests). DSL decisions on it
|
|
335
|
+
* go through the document-mode helpers (documentModeLoader). */
|
|
306
336
|
isSSR?: boolean;
|
|
307
337
|
/** URL patterns map for path() routes (route name -> pattern) */
|
|
308
338
|
patterns?: Map<string, string>;
|
|
@@ -399,6 +429,37 @@ export declare function getNamePrefix(): string | undefined;
|
|
|
399
429
|
* Returns true at root or inside { name: "" } includes, false inside named includes.
|
|
400
430
|
*/
|
|
401
431
|
export declare function getRootScoped(): boolean;
|
|
432
|
+
/**
|
|
433
|
+
* The include scope a segment's dot-local `ctx.reverse(".name")` resolves in.
|
|
434
|
+
*
|
|
435
|
+
* One handler ctx serves every segment of a request and is built from the
|
|
436
|
+
* matched route's name (match-api.ts), so a parent module's layout resolved
|
|
437
|
+
* `.settings` from the matched CHILD module's prefix first: on
|
|
438
|
+
* `/acme/web/issues` the account layout's `.settings` hit the project
|
|
439
|
+
* module's route. Structural entries (layout, cache, parallel, wrapping
|
|
440
|
+
* middleware) and the loaders they declare capture the scope where the DSL
|
|
441
|
+
* defined them. Their handler gets a ctx whose `reverse` carries it
|
|
442
|
+
* (withReverseScope, router/handler-context.ts), and their loaders' DSL
|
|
443
|
+
* kickoff carries it in the loader scope (runInsideLoaderScope) for the
|
|
444
|
+
* loader ctx the executor builds. Global names and mount-param autofill do
|
|
445
|
+
* not change.
|
|
446
|
+
*/
|
|
447
|
+
export interface ReverseScope {
|
|
448
|
+
/** Include name prefix ("account.project"); undefined outside named includes. */
|
|
449
|
+
readonly prefix: string | undefined;
|
|
450
|
+
/** getRootScoped() where the segment was defined: bare-name fallback allowed. */
|
|
451
|
+
readonly rootScoped: boolean;
|
|
452
|
+
}
|
|
453
|
+
/** The ReverseScope of the DSL position being evaluated. */
|
|
454
|
+
export declare function getReverseScope(): ReverseScope;
|
|
455
|
+
/**
|
|
456
|
+
* A createReverseFunction result (router/handler-context.ts). The internal
|
|
457
|
+
* 4th argument resolves dot names in a segment's ReverseScope instead of the
|
|
458
|
+
* route's name.
|
|
459
|
+
*/
|
|
460
|
+
export type ScopableReverse = (name: string, hrefParams?: Record<string, string>, search?: Record<string, unknown>, segmentScope?: ReverseScope) => string;
|
|
461
|
+
/** `reverse` with dot names resolved in `scope`, if any. */
|
|
462
|
+
export declare function scopeReverse(reverse: ScopableReverse, scope: ReverseScope | undefined): ScopableReverse;
|
|
402
463
|
/**
|
|
403
464
|
* Stamp build-time scope identity onto a Static() definition at mount time.
|
|
404
465
|
* The bake collector (prerender-collection.ts) renders defs OUTSIDE any
|
|
@@ -425,6 +486,23 @@ export type { HelperContext };
|
|
|
425
486
|
* parent pointer, handler) stays shared, which is correct and cheap.
|
|
426
487
|
*/
|
|
427
488
|
export declare function getIsolatedLazyParent(captured: EntryData | null | undefined): EntryData | null;
|
|
489
|
+
/** loader(Def, { ssr: false }): a document awaits it before the first flush. */
|
|
490
|
+
export declare function documentModeLoader(entry: LoaderEntry): LoaderEntry;
|
|
491
|
+
/** loading(fallback, { ssr: false }): a document renders no fallback. */
|
|
492
|
+
export declare function applyDocumentModeLoading(entry: EntryPropRender): void;
|
|
493
|
+
/**
|
|
494
|
+
* `entry`, its ancestors, orphan layouts and parallels as a document (isSSR)
|
|
495
|
+
* DSL evaluation builds them, from an evaluation without isSSR.
|
|
496
|
+
*
|
|
497
|
+
* include() captures its parent chain on router.ts routes() or
|
|
498
|
+
* lazy-includes.ts runExpansion, neither of which has isSSR, and loadManifest
|
|
499
|
+
* reuses it for every request. Handed to a document as is, every ancestor
|
|
500
|
+
* outside the include kept its navigation-mode decisions (#1179). Intercepts
|
|
501
|
+
* stay as they are: a document never resolves one.
|
|
502
|
+
*
|
|
503
|
+
* Memoized per entry, so an ancestor several includes share maps to one copy.
|
|
504
|
+
*/
|
|
505
|
+
export declare function getDocumentModeEntry(entry: EntryData): EntryData;
|
|
428
506
|
export declare function getParallelEntries(parallels: ParallelEntries | EntryData[] | undefined): ParallelEntryData[];
|
|
429
507
|
export declare function getParallelSlotEntries(parallels: ParallelEntries | EntryData[] | undefined): Array<{
|
|
430
508
|
slot: `@${string}`;
|
|
@@ -689,7 +767,13 @@ export declare function assertCachedHeaderWriteAllowed(surface: string, surfaceP
|
|
|
689
767
|
* are bypassed because loaders are always fresh (never cached) and
|
|
690
768
|
* their side effects (setCookie, header, etc.) are safe.
|
|
691
769
|
*/
|
|
692
|
-
export declare function runInsideLoaderScope<T>(fn: () => T, loaderId?: string): T;
|
|
770
|
+
export declare function runInsideLoaderScope<T>(fn: () => T, loaderId?: string, reverseScope?: ReverseScope): T;
|
|
771
|
+
/**
|
|
772
|
+
* The ReverseScope of the DSL loader kickoff around this call: a loader the
|
|
773
|
+
* kickoff starts, and one its body starts with ctx.use(), resolve dot names
|
|
774
|
+
* in it. A handler's ctx.use(Loader) runs outside any kickoff: none.
|
|
775
|
+
*/
|
|
776
|
+
export declare function getLoaderReverseScope(): ReverseScope | undefined;
|
|
693
777
|
/**
|
|
694
778
|
* The loader whose run a handle push here belongs to, for the browser's
|
|
695
779
|
* merge of a partial response (handles/pushed-by.ts): the DSL loader
|
|
@@ -123,12 +123,14 @@ export interface HandleStore {
|
|
|
123
123
|
*/
|
|
124
124
|
pushPlaceholder(handleName: string, segmentId: string, data: unknown, loaderId: string): void;
|
|
125
125
|
/**
|
|
126
|
-
* push() a record's copy of `loaderId`'s
|
|
127
|
-
*
|
|
128
|
-
*
|
|
129
|
-
*
|
|
130
|
-
*
|
|
131
|
-
*
|
|
126
|
+
* push() a record's copy of `loaderId`'s push that stands (restoreHandles):
|
|
127
|
+
* the record supplies the loader's value too. From then on this request
|
|
128
|
+
* drops every thenable-free push the loader makes (live, or replayed from
|
|
129
|
+
* a cache entry, anywhere inside its body), and keeps the ones holding a
|
|
130
|
+
* thenable (holdsThenable: what the record could not keep), placed among
|
|
131
|
+
* the restored copies in the loader's push order. A top-level promise is
|
|
132
|
+
* judged by its settled value, as the capture judged it (#1182): dropped
|
|
133
|
+
* when it settles thenable-free or rejects, else kept once it settles.
|
|
132
134
|
*/
|
|
133
135
|
pushRestored(handleName: string, segmentId: string, data: unknown, loaderId: string): void;
|
|
134
136
|
/**
|
|
@@ -140,6 +142,15 @@ export interface HandleStore {
|
|
|
140
142
|
* takes a push made inside a hole it awaited.
|
|
141
143
|
*/
|
|
142
144
|
setRecordAuthority(authority: (loaderId: string) => RecordAuthority): void;
|
|
145
|
+
/**
|
|
146
|
+
* Capture only (shell-capture.ts deriveShellCaptureContext): the slot
|
|
147
|
+
* holding `value` becomes a DSL-loader push without an owner, so the
|
|
148
|
+
* record and the prelude leave it out (getDataForSegment's
|
|
149
|
+
* `excludeLoaderPushes`). The capture owns a bake-lane loader's promise
|
|
150
|
+
* when it is pushed, and calls this once the promise settled to a value
|
|
151
|
+
* that holds one (#1182).
|
|
152
|
+
*/
|
|
153
|
+
unrecordPush(handleName: string, segmentId: string, value: unknown): void;
|
|
143
154
|
/**
|
|
144
155
|
* `loaderId`'s run in this request settled (resolved or rejected), its
|
|
145
156
|
* pushes made (loader-resolution.ts createLoaderExecutor). Its placeholders
|
|
@@ -13,7 +13,7 @@ import { parseCookiesFromHeader } from "./cookie-parse.js";
|
|
|
13
13
|
import type { CacheErrorCategory } from "../cache/cache-error.js";
|
|
14
14
|
import type { CookieOptions } from "../router/middleware.js";
|
|
15
15
|
import type { LoaderDefinition } from "../types.js";
|
|
16
|
-
import type {
|
|
16
|
+
import type { AutofillAwareReverseFunction } from "../types/handler-context.js";
|
|
17
17
|
import type { DefaultEnv, DefaultReverseRouteMap, DefaultRouteName } from "../types/global-namespace.js";
|
|
18
18
|
import type { Handle } from "../handle.js";
|
|
19
19
|
import { type ContextVar } from "../context-var.js";
|
|
@@ -28,6 +28,8 @@ import type { ResolvedTracing } from "../router/tracing.js";
|
|
|
28
28
|
import type { RenderMode, RenderPhase } from "../router/timeout.js";
|
|
29
29
|
import type { LocationStateEntry } from "../browser/react/location-state-shared.js";
|
|
30
30
|
import type { RoutineTrace } from "../rsc/routine-plan.js";
|
|
31
|
+
import type { ActionContinuation } from "../rsc/server-action.js";
|
|
32
|
+
import type { FormActionOutcome } from "../rsc/progressive-enhancement.js";
|
|
31
33
|
import { type ExecutionStart } from "../cache/invalidation-order.js";
|
|
32
34
|
export interface RenderForegroundCursor {
|
|
33
35
|
mode: RenderMode;
|
|
@@ -243,6 +245,12 @@ export interface RequestContext<TEnv = DefaultEnv, TParams = Record<string, stri
|
|
|
243
245
|
* locally and passes it to scheduleShellCapture directly.
|
|
244
246
|
*/
|
|
245
247
|
_shellCaptureRun?: boolean;
|
|
248
|
+
/**
|
|
249
|
+
* @internal Set beside `_shellCaptureRun` when the shell is keyed by the
|
|
250
|
+
* visitor's URL (`rewrite(...).shell("visitor")`): the capture renders the
|
|
251
|
+
* visitor's location and `ctx.rewrittenFrom`; the theme stays the default.
|
|
252
|
+
*/
|
|
253
|
+
_shellCaptureForVisitor?: boolean;
|
|
246
254
|
/**
|
|
247
255
|
* @internal Bake-lane loader containers collected DURING a shell capture:
|
|
248
256
|
* segment-key -> the loader's (pre-wrap) result promise. Populated by
|
|
@@ -256,9 +264,10 @@ export interface RequestContext<TEnv = DefaultEnv, TParams = Record<string, stri
|
|
|
256
264
|
_shellCaptureLoaderRecords?: Map<string, Promise<unknown>>;
|
|
257
265
|
/**
|
|
258
266
|
* @internal Set on a capture's derived context when a loader pushed a
|
|
259
|
-
* value the record cannot keep (
|
|
260
|
-
*
|
|
261
|
-
* `runs: 1`, so a HIT still
|
|
267
|
+
* value the record cannot keep (masked nested promises, a pushed promise
|
|
268
|
+
* that settled to one, a live-lane loader's push, or a push outside a
|
|
269
|
+
* loader body): the loader records then carry `runs: 1`, so a HIT still
|
|
270
|
+
* runs their bodies for those pushes.
|
|
262
271
|
*/
|
|
263
272
|
_shellCaptureUnrecordedLoaderPush?: true;
|
|
264
273
|
/**
|
|
@@ -635,12 +644,25 @@ export interface RequestContext<TEnv = DefaultEnv, TParams = Record<string, stri
|
|
|
635
644
|
* Generate URLs from route names.
|
|
636
645
|
* Uses the global route map. After route matching, scoped (`.name`) resolution
|
|
637
646
|
* works within the matched include() scope.
|
|
638
|
-
|
|
639
|
-
|
|
647
|
+
*
|
|
648
|
+
* Params are optional in the type because the fill depends on the phase.
|
|
649
|
+
* After the route match (route middleware, handlers, loaders, server actions)
|
|
650
|
+
* missing params come from the matched route's params; explicit params win.
|
|
651
|
+
* In global middleware before `next()` nothing is matched and the fill is
|
|
652
|
+
* empty, so a route with a required param throws `Missing param "<name>" for
|
|
653
|
+
* route "<route>"` at runtime (a param-less route still resolves).
|
|
654
|
+
*/
|
|
655
|
+
reverse: AutofillAwareReverseFunction<Record<string, string>, DefaultReverseRouteMap>;
|
|
640
656
|
/** @internal Route name from route matching, used for scoped reverse resolution */
|
|
641
657
|
_routeName?: string;
|
|
642
658
|
/** @internal Previous route key (from the navigation source), used for revalidation */
|
|
643
659
|
_prevRouteKey?: string;
|
|
660
|
+
/**
|
|
661
|
+
* @internal Leaving a rewritten page, the visitor's URL moved
|
|
662
|
+
* (router/match-api.ts): the default revalidation counts it as a search
|
|
663
|
+
* change, since the render may read `ctx.rewrittenFrom`.
|
|
664
|
+
*/
|
|
665
|
+
_visitorMoved?: boolean;
|
|
644
666
|
/**
|
|
645
667
|
* @internal True while the post-action revalidation render is running (set by
|
|
646
668
|
* revalidateAfterAction). The "use cache" runtime reads this to prefer
|
|
@@ -650,6 +672,22 @@ export interface RequestContext<TEnv = DefaultEnv, TParams = Record<string, stri
|
|
|
650
672
|
* revalidating in the background. A plain navigation (flag unset) keeps SWR.
|
|
651
673
|
*/
|
|
652
674
|
_inActionRevalidation?: boolean;
|
|
675
|
+
/**
|
|
676
|
+
* @internal The outcome of the action this request ran (a JS server
|
|
677
|
+
* action's continuation, a no-JS form post's form state), set before route
|
|
678
|
+
* middleware wraps the re-render. While it is unset, applyRewrite
|
|
679
|
+
* (rsc/rewrite-passes.ts) moves a mutation with its body, so the action
|
|
680
|
+
* runs on the target's pass, or refuses it (`disallowMutations()`, or a
|
|
681
|
+
* body middleware read); once set, the request moves to the target, whose
|
|
682
|
+
* pass re-renders from it instead of running the action again (#1145).
|
|
683
|
+
*/
|
|
684
|
+
_actionRan?: {
|
|
685
|
+
kind: "action";
|
|
686
|
+
continuation: ActionContinuation;
|
|
687
|
+
} | {
|
|
688
|
+
kind: "form";
|
|
689
|
+
outcome: FormActionOutcome;
|
|
690
|
+
};
|
|
653
691
|
/**
|
|
654
692
|
* @internal Render barrier for experimental `rendered()` API.
|
|
655
693
|
* Resolves when all non-loader segments have settled and handle data
|
|
@@ -823,7 +861,7 @@ export interface RouteRecordWindow {
|
|
|
823
861
|
* This is the type exported to library consumers. Internal code should
|
|
824
862
|
* use the full RequestContext interface directly.
|
|
825
863
|
*/
|
|
826
|
-
export type PublicRequestContext<TEnv = DefaultEnv, TParams = Record<string, string>> = Omit<RequestContext<TEnv, TParams>, "cookie" | "cookies" | "_readCookie" | "_readCookies" | "setCookie" | "deleteCookie" | "_handleStore" | "_transitionWhenRefs" | "_pprReplayPostMatchReason" | "_cacheStore" | "_prerender" | "_onDemandProducer" | "_searchParamsFilter" | "_shellCaptureRun" | "_shellImplicitCache" | "_shellLoaderSeed" | "_shellCaptureLoaderRecords" | "_shellCaptureUnrecordedLoaderPush" | "_shellCaptureLoaderLanes" | "_resolvedCacheKeys" | "_shellKey" | "_shellForcedMiss" | "_prerenderWarm" | "_runAtRequestEntry" | "_routeRecordWindow" | "_shellFragmentPayload" | "_shellCaptureGuardTripped" | "_shellCaptureGuardTrippedLoaderId" | "_explicitTaggedStores" | "_requestTags" | "_recordTagOwners" | "_recordLoaderTags" | "_cacheProfiles" | "_onResponseCallbacks" | "_pendingBackgroundTasks" | "_themeConfig" | "_readTheme" | "_documentCacheRender" | "_payloadVisitorTheme" | "_payloadDeferred" | "_requestKind" | "_payloadVisitorLocation" | "_locationState" | "_routeName" | "_prevRouteKey" | "_inActionRevalidation" | "_reportedErrors" | "_renderErrors" | "_recoveredHandlerErrors" | "_renderBarrier" | "_resolveRenderBarrier" | "_renderBarrierSegmentOrder" | "_treeHasStreaming" | "_renderBarrierWaiters" | "_handlerLoaderDeps" | "_awaitBeforeFlushLoaderIds" | "_renderBarrierHandleSnapshot" | "_renderBarrierGuardClosed" | "_reportBackgroundError" | "_debugPerformance" | "_metricsStore" | "_renderForeground" | "_activeRoutine" | "_renderDiagnosticsEnabled" | "_handlerStart" | "_tracing" | "_basename" | "_routerId" | "_versions" | "_setStatus" | "_rotateStateCookie" | "_setKeepCacheDirective" | "_freshReads" | "_setFreshReadsCookie" | "_requestRoot" | "_requestStart" | "_responseSent" | "_variables" | "_classifiedRoute" | "_requestMode" | "_cacheSignal" | "_dynamic" | "res">;
|
|
864
|
+
export type PublicRequestContext<TEnv = DefaultEnv, TParams = Record<string, string>> = Omit<RequestContext<TEnv, TParams>, "cookie" | "cookies" | "_readCookie" | "_readCookies" | "setCookie" | "deleteCookie" | "_handleStore" | "_transitionWhenRefs" | "_pprReplayPostMatchReason" | "_cacheStore" | "_prerender" | "_onDemandProducer" | "_searchParamsFilter" | "_shellCaptureRun" | "_shellCaptureForVisitor" | "_shellImplicitCache" | "_shellLoaderSeed" | "_shellCaptureLoaderRecords" | "_shellCaptureUnrecordedLoaderPush" | "_shellCaptureLoaderLanes" | "_resolvedCacheKeys" | "_shellKey" | "_shellForcedMiss" | "_prerenderWarm" | "_runAtRequestEntry" | "_routeRecordWindow" | "_shellFragmentPayload" | "_shellCaptureGuardTripped" | "_shellCaptureGuardTrippedLoaderId" | "_explicitTaggedStores" | "_requestTags" | "_recordTagOwners" | "_recordLoaderTags" | "_cacheProfiles" | "_onResponseCallbacks" | "_pendingBackgroundTasks" | "_themeConfig" | "_readTheme" | "_documentCacheRender" | "_payloadVisitorTheme" | "_payloadDeferred" | "_requestKind" | "_payloadVisitorLocation" | "_locationState" | "_routeName" | "_prevRouteKey" | "_visitorMoved" | "_inActionRevalidation" | "_actionRan" | "_reportedErrors" | "_renderErrors" | "_recoveredHandlerErrors" | "_renderBarrier" | "_resolveRenderBarrier" | "_renderBarrierSegmentOrder" | "_treeHasStreaming" | "_renderBarrierWaiters" | "_handlerLoaderDeps" | "_awaitBeforeFlushLoaderIds" | "_renderBarrierHandleSnapshot" | "_renderBarrierGuardClosed" | "_reportBackgroundError" | "_debugPerformance" | "_metricsStore" | "_renderForeground" | "_activeRoutine" | "_renderDiagnosticsEnabled" | "_handlerStart" | "_tracing" | "_basename" | "_routerId" | "_versions" | "_setStatus" | "_rotateStateCookie" | "_setKeepCacheDirective" | "_freshReads" | "_setFreshReadsCookie" | "_requestRoot" | "_requestStart" | "_responseSent" | "_variables" | "_classifiedRoute" | "_requestMode" | "_cacheSignal" | "_dynamic" | "res">;
|
|
827
865
|
/**
|
|
828
866
|
* Marker for a waitUntil-scheduled fn whose task promise must NOT enter
|
|
829
867
|
* _pendingBackgroundTasks. Used by the PPR shell capture for its own task:
|
|
@@ -18,6 +18,18 @@
|
|
|
18
18
|
* fill); the rest follow the rule so a new call site cannot drift into one.
|
|
19
19
|
*/
|
|
20
20
|
export declare function requestHeaders(request: Request): Headers;
|
|
21
|
+
/**
|
|
22
|
+
* A copy of `request`'s headers for a bodyless mirror of it (the PE
|
|
23
|
+
* re-render, route middleware around it, a rewrite pass after an action),
|
|
24
|
+
* without the body-framing ones and `content-type`, so a body check gated on
|
|
25
|
+
* the content-type passes over a request that has no body.
|
|
26
|
+
*/
|
|
27
|
+
export declare function bodylessHeaders(request: Request): Headers;
|
|
28
|
+
/**
|
|
29
|
+
* A bodyless mirror of `request` at `url`: `method`, its
|
|
30
|
+
* {@link bodylessHeaders}, the signal and workerd's `cf`.
|
|
31
|
+
*/
|
|
32
|
+
export declare function bodylessRequest(url: string | URL, request: Request, method: string): Request;
|
|
21
33
|
/**
|
|
22
34
|
* Shadow `request.headers` with an own, non-enumerable getter that calls
|
|
23
35
|
* `beforeRead` and returns the request's own Headers (stable per request, so
|