vinext 1.0.0-beta.2 → 1.0.0-beta.3
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 +6 -9
- package/dist/build/client-build-config.js +7 -1
- package/dist/check.js +4 -0
- package/dist/config/config-matchers.js +4 -1
- package/dist/config/next-config.d.ts +12 -3
- package/dist/config/next-config.js +4 -0
- package/dist/entries/app-browser-entry.d.ts +4 -10
- package/dist/entries/app-browser-entry.js +20 -4
- package/dist/entries/app-rsc-entry.js +3 -0
- package/dist/entries/app-rsc-manifest.js +19 -0
- package/dist/entries/pages-client-entry.js +0 -1
- package/dist/entries/pages-server-entry.js +10 -3
- package/dist/index.js +112 -43
- package/dist/init-cloudflare.d.ts +3 -1
- package/dist/init-cloudflare.js +59 -5
- package/dist/plugins/extensionless-dynamic-import.js +23 -18
- package/dist/plugins/ignore-dynamic-requests.js +3 -1
- package/dist/plugins/import-meta-url.js +17 -6
- package/dist/plugins/require-context.js +20 -15
- package/dist/plugins/transform-cache.d.ts +19 -0
- package/dist/plugins/transform-cache.js +36 -0
- package/dist/routing/app-route-graph.d.ts +14 -6
- package/dist/routing/app-route-graph.js +106 -16
- package/dist/server/api-handler.d.ts +2 -0
- package/dist/server/api-handler.js +3 -3
- package/dist/server/app-browser-entry.js +103 -31
- package/dist/server/app-browser-navigation-controller.d.ts +23 -21
- package/dist/server/app-browser-navigation-controller.js +1 -1
- package/dist/server/app-page-cache-finalizer.js +1 -1
- package/dist/server/app-page-cache.d.ts +1 -1
- package/dist/server/app-page-cache.js +16 -2
- package/dist/server/app-page-dispatch.d.ts +8 -0
- package/dist/server/app-page-dispatch.js +31 -6
- package/dist/server/app-page-element-builder.d.ts +2 -0
- package/dist/server/app-page-element-builder.js +33 -7
- package/dist/server/app-page-head.d.ts +3 -3
- package/dist/server/app-page-head.js +58 -13
- package/dist/server/app-page-http-access-fallback-metadata.d.ts +2 -2
- package/dist/server/app-page-http-access-fallback-metadata.js +9 -1
- package/dist/server/app-page-probe.d.ts +4 -0
- package/dist/server/app-page-probe.js +6 -2
- package/dist/server/app-page-request.d.ts +3 -0
- package/dist/server/app-page-request.js +1 -1
- package/dist/server/app-page-response.js +1 -1
- package/dist/server/app-page-route-wiring.d.ts +7 -0
- package/dist/server/app-page-route-wiring.js +211 -49
- package/dist/server/app-pages-bridge.d.ts +1 -1
- package/dist/server/app-pages-bridge.js +2 -1
- package/dist/server/app-route-handler-cache.js +4 -0
- package/dist/server/app-route-handler-dispatch.js +9 -3
- package/dist/server/app-route-handler-response.js +1 -1
- package/dist/server/app-route-module-loader.d.ts +6 -0
- package/dist/server/app-route-module-loader.js +3 -0
- package/dist/server/app-router-entry.js +6 -3
- package/dist/server/app-rsc-errors.js +10 -0
- package/dist/server/app-rsc-handler.js +21 -9
- package/dist/server/app-rsc-route-matching.d.ts +9 -0
- package/dist/server/app-rsc-route-matching.js +6 -0
- package/dist/server/app-ssr-entry.js +4 -4
- package/dist/server/cache-control.d.ts +2 -2
- package/dist/server/cache-control.js +2 -1
- package/dist/server/dev-server.d.ts +3 -1
- package/dist/server/dev-server.js +145 -312
- package/dist/server/headers.d.ts +2 -2
- package/dist/server/headers.js +4 -3
- package/dist/server/isr-cache.d.ts +10 -33
- package/dist/server/isr-cache.js +33 -43
- package/dist/server/isr-decision.d.ts +2 -2
- package/dist/server/pages-api-route.d.ts +2 -0
- package/dist/server/pages-api-route.js +4 -1
- package/dist/server/pages-dev-hydration.js +0 -1
- package/dist/server/pages-get-initial-props.d.ts +1 -1
- package/dist/server/pages-get-initial-props.js +1 -4
- package/dist/server/pages-i18n.js +64 -16
- package/dist/server/pages-node-compat.d.ts +2 -0
- package/dist/server/pages-node-compat.js +7 -3
- package/dist/server/pages-page-data.d.ts +61 -9
- package/dist/server/pages-page-data.js +334 -74
- package/dist/server/pages-page-handler.d.ts +5 -1
- package/dist/server/pages-page-handler.js +115 -19
- package/dist/server/pages-page-response.d.ts +5 -3
- package/dist/server/pages-page-response.js +23 -26
- package/dist/server/pages-request-pipeline.d.ts +7 -0
- package/dist/server/pages-request-pipeline.js +5 -1
- package/dist/server/pages-revalidate.d.ts +1 -1
- package/dist/server/pages-revalidate.js +54 -8
- package/dist/server/pages-router-entry.d.ts +1 -0
- package/dist/server/pages-router-entry.js +10 -4
- package/dist/server/prod-server.d.ts +2 -1
- package/dist/server/prod-server.js +37 -13
- package/dist/server/revalidation-host.d.ts +11 -0
- package/dist/server/revalidation-host.js +19 -0
- package/dist/server/worker-revalidation-context.d.ts +13 -0
- package/dist/server/worker-revalidation-context.js +29 -0
- package/dist/shims/cache-handler.d.ts +1 -1
- package/dist/shims/cache-handler.js +10 -7
- package/dist/shims/cache-runtime.d.ts +6 -0
- package/dist/shims/cache-runtime.js +4 -1
- package/dist/shims/cache.js +1 -1
- package/dist/shims/error.js +1 -1
- package/dist/shims/fetch-cache.js +1 -1
- package/dist/shims/font-google-base.js +17 -8
- package/dist/shims/font-local.js +41 -10
- package/dist/shims/headers.d.ts +10 -13
- package/dist/shims/headers.js +85 -36
- package/dist/shims/internal/cookie-serialize.d.ts +10 -9
- package/dist/shims/internal/cookie-serialize.js +9 -8
- package/dist/shims/internal/interpolate-as.d.ts +15 -1
- package/dist/shims/internal/interpolate-as.js +27 -2
- package/dist/shims/link.js +18 -6
- package/dist/shims/metadata.d.ts +7 -17
- package/dist/shims/metadata.js +74 -24
- package/dist/shims/navigation.js +1 -1
- package/dist/shims/request-context.d.ts +4 -1
- package/dist/shims/router.js +18 -7
- package/dist/shims/script.js +1 -1
- package/dist/shims/server.d.ts +7 -6
- package/dist/shims/server.js +156 -57
- package/dist/shims/unified-request-context.d.ts +21 -2
- package/dist/shims/unified-request-context.js +82 -1
- package/dist/utils/cache-control-metadata.d.ts +2 -1
- package/dist/utils/cache-control-metadata.js +5 -1
- package/dist/utils/html-limited-bots.js +1 -1
- package/dist/utils/protocol-headers.d.ts +7 -1
- package/dist/utils/protocol-headers.js +7 -1
- package/package.json +1 -1
package/dist/shims/navigation.js
CHANGED
|
@@ -9,9 +9,9 @@ import { AppRouterContext } from "./internal/app-router-context.js";
|
|
|
9
9
|
import { resolveDirectHybridClientRouteOwner } from "./internal/hybrid-client-route-owner-direct.js";
|
|
10
10
|
import { toBrowserNavigationHref, toSameOriginAppPath, withBasePath } from "./url-utils.js";
|
|
11
11
|
import { retryScrollTo, scrollToHashTarget } from "./hash-scroll.js";
|
|
12
|
+
import { isBotUserAgent } from "../utils/html-limited-bots.js";
|
|
12
13
|
import { GLOBAL_ACCESSORS_KEY, ServerInsertedHTMLContext, _registerStateAccessors, clearClientHydrationContext, clearServerInsertedHTML, flushServerInsertedHTML, getBfcacheIdMapContext, getBfcacheSegmentIdContext, getLayoutSegmentContext, getNavigationContext, registerServerInsertedHTMLCallback, renderServerInsertedHTML, setNavigationContext } from "./navigation-context-state.js";
|
|
13
14
|
import { BailoutToCSRError, DynamicServerError, HTTP_ERROR_FALLBACK_ERROR_CODE, RedirectType, decodeRedirectError, forbidden, getAccessFallbackHTTPStatus, isBailoutToCSRError, isDynamicServerError, isHTTPAccessFallbackError, isNextRouterError, isRedirectError, notFound, permanentRedirect, redirect, unauthorized, unstable_rethrow } from "./navigation-errors.js";
|
|
14
|
-
import { isBotUserAgent } from "../utils/html-limited-bots.js";
|
|
15
15
|
import { clearAppNavigationFailureTarget, stageAppNavigationFailureTarget } from "../client/app-nav-failure-handler.js";
|
|
16
16
|
import { beginAppRouterScrollIntent, clearAppRouterScrollIntent, consumeAppRouterScrollIntent, getPendingAppRouterScrollIntent } from "./app-router-scroll-state.js";
|
|
17
17
|
import { VINEXT_RSC_COMPATIBILITY_ID_HEADER, createRscRequestHeaders, createRscRequestUrl, stripRscCacheBustingSearchParam, stripRscSuffix } from "../server/app-rsc-cache-busting.js";
|
|
@@ -33,7 +33,10 @@ type ExecutionContextLike = {
|
|
|
33
33
|
* execution context. Typed as `unknown` to keep this module runtime-agnostic;
|
|
34
34
|
* CDN cache adapters that know the concrete shape narrow it themselves.
|
|
35
35
|
*/
|
|
36
|
-
cache?: unknown;
|
|
36
|
+
cache?: unknown; /** Server-owned origin for credential-bearing Pages revalidation loopbacks. */
|
|
37
|
+
trustedRevalidateOrigin?: string; /** Worker-owned in-process dispatcher for authenticated Pages revalidation. */
|
|
38
|
+
dispatchPagesRevalidate?: (request: Request) => Promise<Response>; /** Marks a request currently executing through the internal revalidation dispatcher. */
|
|
39
|
+
isInternalPagesRevalidation?: boolean;
|
|
37
40
|
};
|
|
38
41
|
/**
|
|
39
42
|
* Run `fn` with the given `ExecutionContext` available via
|
package/dist/shims/router.js
CHANGED
|
@@ -1159,13 +1159,12 @@ async function renderPagesNavigationTarget(url, target, props, options, assertSt
|
|
|
1159
1159
|
assertStillCurrent();
|
|
1160
1160
|
const React = (await import("react")).default;
|
|
1161
1161
|
assertStillCurrent();
|
|
1162
|
-
const
|
|
1163
|
-
|
|
1162
|
+
const pageProps = Object.assign({}, props.pageProps);
|
|
1163
|
+
props.pageProps = pageProps;
|
|
1164
1164
|
let element;
|
|
1165
1165
|
if (AppComponent) element = React.createElement(AppComponent, {
|
|
1166
1166
|
...props,
|
|
1167
1167
|
Component: PageComponent,
|
|
1168
|
-
pageProps: rawPageProps,
|
|
1169
1168
|
router: singletonRouter
|
|
1170
1169
|
});
|
|
1171
1170
|
else element = React.createElement(PageComponent, pageProps);
|
|
@@ -1312,8 +1311,8 @@ async function navigateClientHtml(url, fetchUrl, controller, navId, assertStillC
|
|
|
1312
1311
|
if (!nextDataJson) scheduleHardNavigationAndThrow(url, "Navigation failed: missing __NEXT_DATA__ in response");
|
|
1313
1312
|
const nextData = parseVinextNextDataJson(nextDataJson);
|
|
1314
1313
|
const props = nextData.props && typeof nextData.props === "object" ? nextData.props : {};
|
|
1315
|
-
const
|
|
1316
|
-
|
|
1314
|
+
const pageProps = Object.assign({}, props.pageProps);
|
|
1315
|
+
props.pageProps = pageProps;
|
|
1317
1316
|
let pageModuleUrl = nextData.__vinext?.pageModuleUrl;
|
|
1318
1317
|
if (!pageModuleUrl) {
|
|
1319
1318
|
const moduleMatch = html.match(/import\("([^"]+)"\);\s*\n\s*const PageComponent/);
|
|
@@ -1355,7 +1354,6 @@ async function navigateClientHtml(url, fetchUrl, controller, navId, assertStillC
|
|
|
1355
1354
|
if (AppComponent) element = React.createElement(AppComponent, {
|
|
1356
1355
|
...props,
|
|
1357
1356
|
Component: PageComponent,
|
|
1358
|
-
pageProps: rawPageProps,
|
|
1359
1357
|
router: singletonRouter
|
|
1360
1358
|
});
|
|
1361
1359
|
else element = React.createElement(PageComponent, pageProps);
|
|
@@ -1647,7 +1645,20 @@ async function performNavigation(url, as, options, mode, onStateUpdate) {
|
|
|
1647
1645
|
const hashStr = extractHash(resolved);
|
|
1648
1646
|
resolved = normalizePathTrailingSlash(`${projection.href.split(/[?#]/, 1)[0]}${searchStr ? `?${searchStr}` : ""}${hashStr}`, __trailingSlash);
|
|
1649
1647
|
}
|
|
1650
|
-
} else
|
|
1648
|
+
} else {
|
|
1649
|
+
const missingParams = projection ? routePatternParts(projection.routePathname).filter((part) => part.startsWith(":") && !part.endsWith("*")).map((part) => part.slice(1, part.endsWith("+") ? -1 : void 0)).filter((paramName) => {
|
|
1650
|
+
const value = projection.query[paramName];
|
|
1651
|
+
return value === void 0 || value === "" || Array.isArray(value) && value.length === 0;
|
|
1652
|
+
}) : [];
|
|
1653
|
+
const hasExplicitHrefPathname = typeof url === "string" || url.pathname !== void 0;
|
|
1654
|
+
const isMiddlewareMatch = options?.shallow !== true && getPagesMiddlewareDataHref(resolved, __basePath) !== null;
|
|
1655
|
+
if (missingParams.length > 0 && hasExplicitHrefPathname && !isMiddlewareMatch) {
|
|
1656
|
+
const asPathname = stripHash(resolved).split("?", 1)[0];
|
|
1657
|
+
const routePathname = projection?.routePathname ?? stripHash(resolvedRoute).split("?", 1)[0];
|
|
1658
|
+
throw new HrefInterpolationError(asPathname === routePathname ? `The provided \`href\` (${resolvedRoute}) value is missing query values (${missingParams.join(", ")}) to be interpolated properly. Read more: https://nextjs.org/docs/messages/href-interpolation-failed` : `The provided \`as\` value (${asPathname}) is incompatible with the \`href\` value (${routePathname}). Read more: https://nextjs.org/docs/messages/incompatible-href-as`);
|
|
1659
|
+
}
|
|
1660
|
+
interpolatedRoute = resolved;
|
|
1661
|
+
}
|
|
1651
1662
|
}
|
|
1652
1663
|
const full = normalizePathTrailingSlash(toBrowserNavigationHref(resolved, window.location.href, __basePath), __trailingSlash);
|
|
1653
1664
|
const fullRouteUrl = interpolatedRoute !== resolved ? normalizePathTrailingSlash(toBrowserNavigationHref(interpolatedRoute, window.location.href, __basePath), __trailingSlash) : full;
|
package/dist/shims/script.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import { escapeInlineContent } from "./head.js";
|
|
3
2
|
import { useScriptNonce } from "./script-nonce-context.js";
|
|
4
3
|
import { hasAppNavigationRuntimeBootstrap } from "../client/navigation-runtime.js";
|
|
5
4
|
import { useBeforeInteractiveRegister } from "./before-interactive-context.js";
|
|
5
|
+
import { escapeInlineContent } from "./head.js";
|
|
6
6
|
import React, { useEffect, useRef } from "react";
|
|
7
7
|
import * as ReactDOM from "react-dom";
|
|
8
8
|
//#region src/shims/script.tsx
|
package/dist/shims/server.d.ts
CHANGED
|
@@ -230,15 +230,16 @@ declare class ResponseCookies {
|
|
|
230
230
|
}]): this;
|
|
231
231
|
get(...args: [name: string] | [options: {
|
|
232
232
|
name: string;
|
|
233
|
-
}]):
|
|
233
|
+
}]): ResponseCookieEntry | undefined;
|
|
234
234
|
has(name: string): boolean;
|
|
235
235
|
getAll(...args: [name: string] | [options: {
|
|
236
236
|
name: string;
|
|
237
|
-
}] | []):
|
|
237
|
+
}] | []): ResponseCookieEntry[];
|
|
238
238
|
delete(...args: [name: string] | [options: Omit<CookieOptions & {
|
|
239
239
|
name: string;
|
|
240
240
|
}, "maxAge" | "expires">]): this;
|
|
241
|
-
[Symbol.iterator](): MapIterator<[string,
|
|
241
|
+
[Symbol.iterator](): MapIterator<[string, ResponseCookieEntry]>;
|
|
242
|
+
toString(): string;
|
|
242
243
|
/** Delete all Set-Cookie headers and re-append from the internal map. */
|
|
243
244
|
private _syncHeaders;
|
|
244
245
|
}
|
|
@@ -249,10 +250,11 @@ type CookieOptions = {
|
|
|
249
250
|
expires?: Date | number;
|
|
250
251
|
httpOnly?: boolean;
|
|
251
252
|
secure?: boolean;
|
|
252
|
-
sameSite?: true | false | "strict" | "lax" | "none"
|
|
253
|
+
sameSite?: true | false | "strict" | "lax" | "none";
|
|
253
254
|
partitioned?: boolean;
|
|
254
255
|
priority?: "low" | "medium" | "high";
|
|
255
256
|
};
|
|
257
|
+
type ResponseCookieEntry = CookieEntry & CookieOptions;
|
|
256
258
|
type MiddlewareResponseInit = {
|
|
257
259
|
request?: {
|
|
258
260
|
headers?: Headers;
|
|
@@ -323,8 +325,7 @@ type UserAgent = {
|
|
|
323
325
|
*
|
|
324
326
|
* Uses the platform's `waitUntil` (via the per-request ExecutionContext) when
|
|
325
327
|
* available so the task survives past the response on Cloudflare Workers.
|
|
326
|
-
*
|
|
327
|
-
* context (e.g. Node.js dev server).
|
|
328
|
+
* Node.js dev drains callbacks from its response finish/close lifecycle.
|
|
328
329
|
*
|
|
329
330
|
* Throws when called inside a cached scope — request-specific
|
|
330
331
|
* side-effects must not leak into cached results.
|
package/dist/shims/server.js
CHANGED
|
@@ -1,9 +1,10 @@
|
|
|
1
|
+
import { bindRequestContextSnapshot, getRequestContext, isInsideUnifiedScope, queueAfterCallback } from "./unified-request-context.js";
|
|
1
2
|
import { hasBasePath, stripBasePath } from "../utils/base-path.js";
|
|
2
3
|
import { getRequestExecutionContext } from "./request-context.js";
|
|
3
4
|
import { MIDDLEWARE_SET_COOKIE_HEADER } from "../utils/protocol-headers.js";
|
|
4
5
|
import { MIDDLEWARE_NEXT_HEADER, MIDDLEWARE_REWRITE_HEADER } from "../server/headers.js";
|
|
5
6
|
import { encodeMiddlewareRequestHeaders } from "../utils/middleware-request-headers.js";
|
|
6
|
-
import {
|
|
7
|
+
import { validateCookieAttributeValue, validateCookieName } from "./internal/cookie-serialize.js";
|
|
7
8
|
import { parseEdgeRequestCookieHeader } from "../utils/parse-cookie.js";
|
|
8
9
|
import { assertSafeNavigationUrl } from "./url-safety.js";
|
|
9
10
|
//#region src/shims/server.ts
|
|
@@ -158,12 +159,8 @@ var NextResponse = class NextResponse extends Response {
|
|
|
158
159
|
* Create a JSON response.
|
|
159
160
|
*/
|
|
160
161
|
static json(body, init) {
|
|
161
|
-
const
|
|
162
|
-
|
|
163
|
-
return new NextResponse(JSON.stringify(body), {
|
|
164
|
-
...init,
|
|
165
|
-
headers
|
|
166
|
-
});
|
|
162
|
+
const response = Response.json(body, init);
|
|
163
|
+
return new NextResponse(response.body, response);
|
|
167
164
|
}
|
|
168
165
|
/**
|
|
169
166
|
* Create a redirect response.
|
|
@@ -417,7 +414,7 @@ var NextURL = class NextURL {
|
|
|
417
414
|
};
|
|
418
415
|
if (this._trailingSlash) nextConfig.trailingSlash = true;
|
|
419
416
|
const config = {
|
|
420
|
-
basePath: this.
|
|
417
|
+
basePath: this._configBasePath,
|
|
421
418
|
nextConfig: Object.keys(nextConfig).length > 0 ? nextConfig : void 0
|
|
422
419
|
};
|
|
423
420
|
return new NextURL(this.href, void 0, config);
|
|
@@ -554,79 +551,54 @@ var ResponseCookies = class {
|
|
|
554
551
|
_parsed = /* @__PURE__ */ new Map();
|
|
555
552
|
constructor(headers) {
|
|
556
553
|
this._headers = headers;
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
const
|
|
561
|
-
|
|
562
|
-
const raw = header.slice(eq + 1, semi === -1 ? void 0 : semi);
|
|
563
|
-
let value;
|
|
564
|
-
try {
|
|
565
|
-
value = decodeURIComponent(raw);
|
|
566
|
-
} catch {
|
|
567
|
-
value = raw;
|
|
568
|
-
}
|
|
569
|
-
this._parsed.set(cookieName, {
|
|
570
|
-
serialized: header,
|
|
571
|
-
entry: {
|
|
572
|
-
name: cookieName,
|
|
573
|
-
value
|
|
574
|
-
}
|
|
575
|
-
});
|
|
554
|
+
const setCookie = headers.getSetCookie?.() ?? headers.get("set-cookie") ?? [];
|
|
555
|
+
const cookieStrings = Array.isArray(setCookie) ? setCookie : splitSetCookieString(setCookie);
|
|
556
|
+
for (const header of cookieStrings) {
|
|
557
|
+
const entry = parseSetCookieHeader(header);
|
|
558
|
+
if (entry) this._parsed.set(entry.name, entry);
|
|
576
559
|
}
|
|
577
560
|
}
|
|
578
561
|
set(...args) {
|
|
579
562
|
const [name, value, opts] = parseCookieSetArgs(args);
|
|
580
563
|
validateCookieName(name);
|
|
581
|
-
const
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
expires: typeof opts?.expires === "number" ? new Date(opts.expires) : opts?.expires,
|
|
585
|
-
sameSite
|
|
586
|
-
});
|
|
587
|
-
this._parsed.set(name, {
|
|
588
|
-
serialized,
|
|
589
|
-
entry: {
|
|
590
|
-
name,
|
|
591
|
-
value
|
|
592
|
-
}
|
|
593
|
-
});
|
|
564
|
+
const entry = normalizeResponseCookie(name, value, opts);
|
|
565
|
+
validateResponseCookieAttributes(entry);
|
|
566
|
+
this._parsed.set(name, entry);
|
|
594
567
|
this._syncHeaders();
|
|
595
568
|
return this;
|
|
596
569
|
}
|
|
597
570
|
get(...args) {
|
|
598
571
|
const key = typeof args[0] === "string" ? args[0] : args[0].name;
|
|
599
|
-
return this._parsed.get(key)
|
|
572
|
+
return this._parsed.get(key);
|
|
600
573
|
}
|
|
601
574
|
has(name) {
|
|
602
575
|
return this._parsed.has(name);
|
|
603
576
|
}
|
|
604
577
|
getAll(...args) {
|
|
605
|
-
const all = [...this._parsed.values()]
|
|
578
|
+
const all = [...this._parsed.values()];
|
|
606
579
|
if (args.length === 0) return all;
|
|
607
580
|
const key = typeof args[0] === "string" ? args[0] : args[0].name;
|
|
608
581
|
return all.filter((c) => c.name === key);
|
|
609
582
|
}
|
|
610
583
|
delete(...args) {
|
|
611
|
-
const [name,
|
|
584
|
+
const [name, options] = typeof args[0] === "string" ? [args[0], void 0] : [args[0].name, args[0]];
|
|
612
585
|
return this.set({
|
|
586
|
+
...options,
|
|
613
587
|
name,
|
|
614
588
|
value: "",
|
|
615
|
-
expires: /* @__PURE__ */ new Date(0)
|
|
616
|
-
path: opts?.path,
|
|
617
|
-
domain: opts?.domain,
|
|
618
|
-
httpOnly: opts?.httpOnly,
|
|
619
|
-
secure: opts?.secure,
|
|
620
|
-
sameSite: opts?.sameSite
|
|
589
|
+
expires: /* @__PURE__ */ new Date(0)
|
|
621
590
|
});
|
|
622
591
|
}
|
|
623
592
|
[Symbol.iterator]() {
|
|
624
|
-
return new Map([...this._parsed.values()].map((
|
|
593
|
+
return new Map([...this._parsed.values()].map((entry) => [entry.name, entry])).entries();
|
|
594
|
+
}
|
|
595
|
+
toString() {
|
|
596
|
+
return [...this._parsed.values()].map(stringifyResponseCookie).join("; ");
|
|
625
597
|
}
|
|
626
598
|
/** Delete all Set-Cookie headers and re-append from the internal map. */
|
|
627
599
|
_syncHeaders() {
|
|
628
600
|
this._headers.delete("Set-Cookie");
|
|
629
|
-
for (const
|
|
601
|
+
for (const entry of this._parsed.values()) this._headers.append("Set-Cookie", stringifyResponseCookie(entry));
|
|
630
602
|
}
|
|
631
603
|
};
|
|
632
604
|
var MiddlewareResponseCookies = class extends ResponseCookies {
|
|
@@ -654,6 +626,115 @@ var MiddlewareResponseCookies = class extends ResponseCookies {
|
|
|
654
626
|
this._responseHeaders.set(MIDDLEWARE_SET_COOKIE_HEADER, cookies.join(","));
|
|
655
627
|
}
|
|
656
628
|
};
|
|
629
|
+
function normalizeResponseCookie(name, value, options) {
|
|
630
|
+
const cookie = {
|
|
631
|
+
name,
|
|
632
|
+
value,
|
|
633
|
+
...options
|
|
634
|
+
};
|
|
635
|
+
if (typeof cookie.expires === "number") cookie.expires = new Date(cookie.expires);
|
|
636
|
+
if (cookie.maxAge) cookie.expires = new Date(Date.now() + cookie.maxAge * 1e3);
|
|
637
|
+
if (cookie.path == null) cookie.path = "/";
|
|
638
|
+
return cookie;
|
|
639
|
+
}
|
|
640
|
+
function parseSetCookieHeader(header) {
|
|
641
|
+
if (!header) return void 0;
|
|
642
|
+
const [[name, value], ...attributes] = parseResponseCookiePairs(header);
|
|
643
|
+
const { domain, expires, httponly, maxage, path, samesite, secure, partitioned, priority } = Object.fromEntries(attributes.map(([key, attributeValue]) => [key.toLowerCase().replaceAll("-", ""), attributeValue]));
|
|
644
|
+
return compactResponseCookie({
|
|
645
|
+
name,
|
|
646
|
+
value: decodeURIComponent(value),
|
|
647
|
+
domain,
|
|
648
|
+
...expires && { expires: new Date(expires) },
|
|
649
|
+
...httponly && { httpOnly: true },
|
|
650
|
+
...typeof maxage === "string" && { maxAge: Number(maxage) },
|
|
651
|
+
path,
|
|
652
|
+
...samesite && { sameSite: parseResponseCookieSameSite(samesite) },
|
|
653
|
+
...secure && { secure: true },
|
|
654
|
+
...priority && { priority: parseResponseCookiePriority(priority) },
|
|
655
|
+
...partitioned && { partitioned: true }
|
|
656
|
+
});
|
|
657
|
+
}
|
|
658
|
+
function parseResponseCookiePairs(cookie) {
|
|
659
|
+
const map = /* @__PURE__ */ new Map();
|
|
660
|
+
for (const pair of cookie.split(/; */)) {
|
|
661
|
+
if (!pair) continue;
|
|
662
|
+
const splitAt = pair.indexOf("=");
|
|
663
|
+
if (splitAt === -1) {
|
|
664
|
+
map.set(pair, "true");
|
|
665
|
+
continue;
|
|
666
|
+
}
|
|
667
|
+
const key = pair.slice(0, splitAt);
|
|
668
|
+
const value = pair.slice(splitAt + 1);
|
|
669
|
+
try {
|
|
670
|
+
map.set(key, decodeURIComponent(value ?? "true"));
|
|
671
|
+
} catch {}
|
|
672
|
+
}
|
|
673
|
+
return map;
|
|
674
|
+
}
|
|
675
|
+
function compactResponseCookie(cookie) {
|
|
676
|
+
const compact = {};
|
|
677
|
+
for (const key in cookie) if (cookie[key]) compact[key] = cookie[key];
|
|
678
|
+
return compact;
|
|
679
|
+
}
|
|
680
|
+
function parseResponseCookieSameSite(value) {
|
|
681
|
+
const sameSite = value.toLowerCase();
|
|
682
|
+
return sameSite === "strict" || sameSite === "lax" || sameSite === "none" ? sameSite : void 0;
|
|
683
|
+
}
|
|
684
|
+
function parseResponseCookiePriority(value) {
|
|
685
|
+
const priority = value.toLowerCase();
|
|
686
|
+
return priority === "low" || priority === "medium" || priority === "high" ? priority : void 0;
|
|
687
|
+
}
|
|
688
|
+
function validateResponseCookieAttributes(cookie) {
|
|
689
|
+
if (cookie.path) validateCookieAttributeValue(cookie.path, "Path");
|
|
690
|
+
if (cookie.domain) validateCookieAttributeValue(cookie.domain, "Domain");
|
|
691
|
+
}
|
|
692
|
+
function stringifyResponseCookie(cookie) {
|
|
693
|
+
const attributes = [
|
|
694
|
+
cookie.path && `Path=${cookie.path}`,
|
|
695
|
+
(cookie.expires || cookie.expires === 0) && `Expires=${(typeof cookie.expires === "number" ? new Date(cookie.expires) : cookie.expires).toUTCString()}`,
|
|
696
|
+
typeof cookie.maxAge === "number" && `Max-Age=${cookie.maxAge}`,
|
|
697
|
+
cookie.domain && `Domain=${cookie.domain}`,
|
|
698
|
+
cookie.secure && "Secure",
|
|
699
|
+
cookie.httpOnly && "HttpOnly",
|
|
700
|
+
cookie.sameSite && `SameSite=${cookie.sameSite}`,
|
|
701
|
+
cookie.partitioned && "Partitioned",
|
|
702
|
+
cookie.priority && `Priority=${cookie.priority}`
|
|
703
|
+
].filter(Boolean);
|
|
704
|
+
const stringified = `${cookie.name}=${encodeURIComponent(cookie.value ?? "")}`;
|
|
705
|
+
return attributes.length === 0 ? stringified : `${stringified}; ${attributes.join("; ")}`;
|
|
706
|
+
}
|
|
707
|
+
function splitSetCookieString(value) {
|
|
708
|
+
const cookies = [];
|
|
709
|
+
let position = 0;
|
|
710
|
+
let start = 0;
|
|
711
|
+
const skipWhitespace = () => {
|
|
712
|
+
while (position < value.length && /\s/.test(value.charAt(position))) position++;
|
|
713
|
+
return position < value.length;
|
|
714
|
+
};
|
|
715
|
+
while (position < value.length) {
|
|
716
|
+
start = position;
|
|
717
|
+
let separatorFound = false;
|
|
718
|
+
while (skipWhitespace()) {
|
|
719
|
+
if (value.charAt(position) !== ",") {
|
|
720
|
+
position++;
|
|
721
|
+
continue;
|
|
722
|
+
}
|
|
723
|
+
const lastComma = position++;
|
|
724
|
+
skipWhitespace();
|
|
725
|
+
const nextStart = position;
|
|
726
|
+
while (position < value.length && !"=;,".includes(value.charAt(position))) position++;
|
|
727
|
+
if (position < value.length && value.charAt(position) === "=") {
|
|
728
|
+
separatorFound = true;
|
|
729
|
+
position = nextStart;
|
|
730
|
+
cookies.push(value.substring(start, lastComma));
|
|
731
|
+
start = position;
|
|
732
|
+
} else position = lastComma + 1;
|
|
733
|
+
}
|
|
734
|
+
if (!separatorFound || position >= value.length) cookies.push(value.substring(start));
|
|
735
|
+
}
|
|
736
|
+
return cookies;
|
|
737
|
+
}
|
|
657
738
|
/**
|
|
658
739
|
* Parse the overloaded arguments for ResponseCookies.set():
|
|
659
740
|
* - (name, value, options?) — positional form
|
|
@@ -730,18 +811,36 @@ function userAgent({ headers }) {
|
|
|
730
811
|
*
|
|
731
812
|
* Uses the platform's `waitUntil` (via the per-request ExecutionContext) when
|
|
732
813
|
* available so the task survives past the response on Cloudflare Workers.
|
|
733
|
-
*
|
|
734
|
-
* context (e.g. Node.js dev server).
|
|
814
|
+
* Node.js dev drains callbacks from its response finish/close lifecycle.
|
|
735
815
|
*
|
|
736
816
|
* Throws when called inside a cached scope — request-specific
|
|
737
817
|
* side-effects must not leak into cached results.
|
|
738
818
|
*/
|
|
739
819
|
function after(task) {
|
|
740
820
|
_throwIfInsideCacheScope("after()");
|
|
741
|
-
const
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
821
|
+
const requestContext = isInsideUnifiedScope() ? getRequestContext() : null;
|
|
822
|
+
if (!requestContext) {
|
|
823
|
+
const executionContext = getRequestExecutionContext();
|
|
824
|
+
if (executionContext) {
|
|
825
|
+
if (typeof task !== "function" && (task == null || typeof task.then !== "function")) throw new TypeError("`after()`: Argument must be a promise or a function");
|
|
826
|
+
const promise = typeof task === "function" ? Promise.resolve().then(task) : task;
|
|
827
|
+
const guarded = Promise.resolve(promise).catch((error) => {
|
|
828
|
+
console.error("[vinext] after() task failed:", error);
|
|
829
|
+
});
|
|
830
|
+
executionContext.waitUntil(guarded);
|
|
831
|
+
return;
|
|
832
|
+
}
|
|
833
|
+
throw new Error("`after()` was called outside a request scope");
|
|
834
|
+
}
|
|
835
|
+
if (typeof task !== "function") {
|
|
836
|
+
if (task == null || typeof task.then !== "function") throw new TypeError("`after()`: Argument must be a promise or a function");
|
|
837
|
+
const guarded = Promise.resolve(task).catch((error) => {
|
|
838
|
+
console.error("[vinext] after() task failed:", error);
|
|
839
|
+
});
|
|
840
|
+
getRequestExecutionContext()?.waitUntil(guarded);
|
|
841
|
+
return;
|
|
842
|
+
}
|
|
843
|
+
queueAfterCallback(requestContext, bindRequestContextSnapshot(requestContext, task));
|
|
745
844
|
}
|
|
746
845
|
/**
|
|
747
846
|
* connection() — signals that the response requires a live connection
|
|
@@ -18,13 +18,32 @@ import { NavigationState } from "./navigation-state.js";
|
|
|
18
18
|
*/
|
|
19
19
|
type UnifiedRequestContext = {
|
|
20
20
|
/** Cloudflare Workers ExecutionContext, or null on Node.js dev. */executionContext: ExecutionContextLike | null; /** Per-request cache for cacheForRequest(). Keyed by factory function reference. */
|
|
21
|
-
requestCache: WeakMap<(...args: any[]) => any, unknown>;
|
|
21
|
+
requestCache: WeakMap<(...args: any[]) => any, unknown>; /** Shared lifecycle state for work deferred until the response closes. */
|
|
22
|
+
afterContext: AfterRequestContext;
|
|
22
23
|
} & VinextHeadersShimState & I18nState & NavigationState & CacheState & PrivateCacheState & FetchCacheState & RouterState & HeadState & RootParamsState;
|
|
24
|
+
type AfterRequestContext = {
|
|
25
|
+
callbacks: Array<() => unknown>;
|
|
26
|
+
responseClosed: boolean;
|
|
27
|
+
pendingCallbacks: number;
|
|
28
|
+
completion: Promise<void> | null;
|
|
29
|
+
resolveCompletion: (() => void) | null;
|
|
30
|
+
};
|
|
23
31
|
/**
|
|
24
32
|
* Create a fresh `UnifiedRequestContext` with defaults for all fields.
|
|
25
33
|
* Pass partial overrides for the fields you need to pre-populate.
|
|
26
34
|
*/
|
|
27
35
|
declare function createRequestContext(opts?: Partial<UnifiedRequestContext>): UnifiedRequestContext;
|
|
36
|
+
/** Queue a callback until response close, or start it immediately once closed. */
|
|
37
|
+
declare function queueAfterCallback(ctx: UnifiedRequestContext, callback: () => unknown): void;
|
|
38
|
+
/** Bind a callback to every AsyncLocalStorage context active at registration. */
|
|
39
|
+
declare function bindRequestContextSnapshot<T>(ctx: UnifiedRequestContext, callback: () => T): () => T;
|
|
40
|
+
/**
|
|
41
|
+
* Release function-form `after()` work once the response body has closed.
|
|
42
|
+
* All queued callbacks start together, matching Next.js' unbounded PromiseQueue.
|
|
43
|
+
*/
|
|
44
|
+
declare function closeAfterResponse(ctx: UnifiedRequestContext): Promise<void>;
|
|
45
|
+
/** Wrap a response so deferred callbacks start on stream completion or cancellation. */
|
|
46
|
+
declare function closeAfterResponseWithBody(response: Response, ctx: UnifiedRequestContext): Response;
|
|
28
47
|
/**
|
|
29
48
|
* Run `fn` within a unified request context scope.
|
|
30
49
|
* All shim modules will read/write their state from `ctx` for the
|
|
@@ -65,4 +84,4 @@ declare function getRequestContext(): UnifiedRequestContext;
|
|
|
65
84
|
*/
|
|
66
85
|
declare function isInsideUnifiedScope(): boolean;
|
|
67
86
|
//#endregion
|
|
68
|
-
export { UnifiedRequestContext, createRequestContext, getRequestContext, isInsideUnifiedScope, runWithRequestContext, runWithUnifiedStateMutation };
|
|
87
|
+
export { AfterRequestContext, UnifiedRequestContext, bindRequestContextSnapshot, closeAfterResponse, closeAfterResponseWithBody, createRequestContext, getRequestContext, isInsideUnifiedScope, queueAfterCallback, runWithRequestContext, runWithUnifiedStateMutation };
|
|
@@ -43,6 +43,13 @@ function createRequestContext(opts) {
|
|
|
43
43
|
currentFetchDedupeEntries: /* @__PURE__ */ new Map(),
|
|
44
44
|
executionContext: _getInheritedExecutionContext(),
|
|
45
45
|
requestCache: /* @__PURE__ */ new WeakMap(),
|
|
46
|
+
afterContext: {
|
|
47
|
+
callbacks: [],
|
|
48
|
+
responseClosed: false,
|
|
49
|
+
pendingCallbacks: 0,
|
|
50
|
+
completion: null,
|
|
51
|
+
resolveCompletion: null
|
|
52
|
+
},
|
|
46
53
|
ssrContext: null,
|
|
47
54
|
ssrHeadChildren: [],
|
|
48
55
|
documentInitialHead: [],
|
|
@@ -50,6 +57,80 @@ function createRequestContext(opts) {
|
|
|
50
57
|
...opts
|
|
51
58
|
};
|
|
52
59
|
}
|
|
60
|
+
function ensureAfterCompletion(ctx) {
|
|
61
|
+
const state = ctx.afterContext;
|
|
62
|
+
if (state.resolveCompletion && state.completion) return;
|
|
63
|
+
let resolveCompletion;
|
|
64
|
+
const completion = new Promise((resolve) => {
|
|
65
|
+
resolveCompletion = resolve;
|
|
66
|
+
});
|
|
67
|
+
state.completion = completion;
|
|
68
|
+
state.resolveCompletion = resolveCompletion;
|
|
69
|
+
ctx.executionContext?.waitUntil(completion);
|
|
70
|
+
}
|
|
71
|
+
function finishAfterCallbacksIfIdle(ctx) {
|
|
72
|
+
const state = ctx.afterContext;
|
|
73
|
+
if (!state.responseClosed || state.pendingCallbacks !== 0 || state.callbacks.length !== 0 || !state.resolveCompletion) return;
|
|
74
|
+
const resolveCompletion = state.resolveCompletion;
|
|
75
|
+
state.resolveCompletion = null;
|
|
76
|
+
resolveCompletion();
|
|
77
|
+
}
|
|
78
|
+
function startAfterCallback(ctx, callback) {
|
|
79
|
+
const state = ctx.afterContext;
|
|
80
|
+
ensureAfterCompletion(ctx);
|
|
81
|
+
state.pendingCallbacks += 1;
|
|
82
|
+
Promise.resolve().then(callback).catch((error) => {
|
|
83
|
+
console.error("[vinext] after() task failed:", error);
|
|
84
|
+
}).finally(() => {
|
|
85
|
+
state.pendingCallbacks -= 1;
|
|
86
|
+
finishAfterCallbacksIfIdle(ctx);
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
/** Queue a callback until response close, or start it immediately once closed. */
|
|
90
|
+
function queueAfterCallback(ctx, callback) {
|
|
91
|
+
ensureAfterCompletion(ctx);
|
|
92
|
+
if (ctx.afterContext.responseClosed) startAfterCallback(ctx, callback);
|
|
93
|
+
else ctx.afterContext.callbacks.push(callback);
|
|
94
|
+
}
|
|
95
|
+
/** Bind a callback to every AsyncLocalStorage context active at registration. */
|
|
96
|
+
function bindRequestContextSnapshot(ctx, callback) {
|
|
97
|
+
const constructor = _als.constructor;
|
|
98
|
+
try {
|
|
99
|
+
const runInSnapshot = constructor.snapshot?.();
|
|
100
|
+
if (runInSnapshot) return () => runInSnapshot(callback);
|
|
101
|
+
} catch {}
|
|
102
|
+
return () => _als.run(ctx, callback);
|
|
103
|
+
}
|
|
104
|
+
/**
|
|
105
|
+
* Release function-form `after()` work once the response body has closed.
|
|
106
|
+
* All queued callbacks start together, matching Next.js' unbounded PromiseQueue.
|
|
107
|
+
*/
|
|
108
|
+
async function closeAfterResponse(ctx) {
|
|
109
|
+
const state = ctx.afterContext;
|
|
110
|
+
if (!state.responseClosed) {
|
|
111
|
+
state.responseClosed = true;
|
|
112
|
+
const callbacks = state.callbacks.splice(0);
|
|
113
|
+
for (const callback of callbacks) startAfterCallback(ctx, callback);
|
|
114
|
+
finishAfterCallbacksIfIdle(ctx);
|
|
115
|
+
}
|
|
116
|
+
return state.completion ?? Promise.resolve();
|
|
117
|
+
}
|
|
118
|
+
/** Wrap a response so deferred callbacks start on stream completion or cancellation. */
|
|
119
|
+
function closeAfterResponseWithBody(response, ctx) {
|
|
120
|
+
if (!response.body) {
|
|
121
|
+
queueMicrotask(() => void closeAfterResponse(ctx));
|
|
122
|
+
return response;
|
|
123
|
+
}
|
|
124
|
+
const passthrough = new TransformStream();
|
|
125
|
+
response.body.pipeTo(passthrough.writable).then(() => void closeAfterResponse(ctx), () => void closeAfterResponse(ctx));
|
|
126
|
+
const wrapped = new Response(passthrough.readable, {
|
|
127
|
+
status: response.status,
|
|
128
|
+
statusText: response.statusText,
|
|
129
|
+
headers: response.headers
|
|
130
|
+
});
|
|
131
|
+
wrapped.__vinextStreamedHtmlResponse = response.__vinextStreamedHtmlResponse;
|
|
132
|
+
return wrapped;
|
|
133
|
+
}
|
|
53
134
|
function runWithRequestContext(ctx, fn) {
|
|
54
135
|
return _als.run(ctx, fn);
|
|
55
136
|
}
|
|
@@ -86,4 +167,4 @@ function isInsideUnifiedScope() {
|
|
|
86
167
|
return _als.getStore() != null;
|
|
87
168
|
}
|
|
88
169
|
//#endregion
|
|
89
|
-
export { createRequestContext, getRequestContext, isInsideUnifiedScope, runWithRequestContext, runWithUnifiedStateMutation };
|
|
170
|
+
export { bindRequestContextSnapshot, closeAfterResponse, closeAfterResponseWithBody, createRequestContext, getRequestContext, isInsideUnifiedScope, queueAfterCallback, runWithRequestContext, runWithUnifiedStateMutation };
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
//#region src/utils/cache-control-metadata.d.ts
|
|
2
2
|
declare function readCacheControlNumberField(ctx: Record<string, unknown> | undefined, field: string): number | undefined;
|
|
3
|
+
declare function readCacheControlRevalidateField(ctx: Record<string, unknown> | undefined): number | false | undefined;
|
|
3
4
|
//#endregion
|
|
4
|
-
export { readCacheControlNumberField };
|
|
5
|
+
export { readCacheControlNumberField, readCacheControlRevalidateField };
|
|
@@ -8,5 +8,9 @@ function readCacheControlNumberField(ctx, field) {
|
|
|
8
8
|
const value = readRecordField(ctx, "cacheControl")?.[field] ?? ctx?.[field];
|
|
9
9
|
return typeof value === "number" ? value : void 0;
|
|
10
10
|
}
|
|
11
|
+
function readCacheControlRevalidateField(ctx) {
|
|
12
|
+
const value = readRecordField(ctx, "cacheControl")?.revalidate ?? ctx?.revalidate;
|
|
13
|
+
return typeof value === "number" || value === false ? value : void 0;
|
|
14
|
+
}
|
|
11
15
|
//#endregion
|
|
12
|
-
export { readCacheControlNumberField };
|
|
16
|
+
export { readCacheControlNumberField, readCacheControlRevalidateField };
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
//#region src/utils/html-limited-bots.ts
|
|
2
|
-
const HTML_LIMITED_BOT_UA_RE_STRING = String.raw`[\w-]+-Google|Google-[\w-]+|Chrome-Lighthouse|Slurp|DuckDuckBot|baiduspider|yandex|sogou|bitlybot|tumblr|vkShare|quora link preview|redditbot|ia_archiver|Bingbot|BingPreview|applebot|facebookexternalhit|facebookcatalog|Twitterbot|LinkedInBot|Slackbot|Discordbot|WhatsApp|SkypeUriPreview|Yeti|googleweblight`;
|
|
2
|
+
const HTML_LIMITED_BOT_UA_RE_STRING = String.raw`[\w-]+-Google|Google-[\w-]+|Chrome-Lighthouse|Slurp|DuckDuckBot|baiduspider|yandex|sogou|bitlybot|tumblr|vkShare|quora link preview|redditbot|ia_archiver|Bingbot|BingPreview|applebot|facebookexternalhit|facebookcatalog|meta-externalagent|meta-externalfetcher|Twitterbot|LinkedInBot|Slackbot|Discordbot|WhatsApp|SkypeUriPreview|Yeti|googleweblight`;
|
|
3
3
|
const HEADLESS_BROWSER_BOT_UA_RE = /Googlebot(?!-)|Googlebot$/i;
|
|
4
4
|
const htmlLimitedBotRegexCache = /* @__PURE__ */ new Map();
|
|
5
5
|
function getHtmlLimitedBotRegex(htmlLimitedBots) {
|
|
@@ -7,6 +7,8 @@ declare const VINEXT_PRERENDER_SECRET_HEADER = "x-vinext-prerender-secret";
|
|
|
7
7
|
declare const VINEXT_PRERENDER_ROUTE_PARAMS_HEADER = "x-vinext-prerender-route-params";
|
|
8
8
|
/** Indicates a build-time prerender render is probing whether a route can be static. */
|
|
9
9
|
declare const VINEXT_PRERENDER_SPECULATIVE_HEADER = "x-vinext-prerender-speculative";
|
|
10
|
+
/** Logical hostname carried only by authenticated Node revalidation loopbacks. */
|
|
11
|
+
declare const VINEXT_REVALIDATE_HOST_HEADER = "x-vinext-revalidate-host";
|
|
10
12
|
/** Prefix for forwarded request headers (e.g. `x-middleware-request-cookie`). */
|
|
11
13
|
declare const MIDDLEWARE_REQUEST_HEADER_PREFIX = "x-middleware-request-";
|
|
12
14
|
/** Comma-separated list of header names that middleware wants to override. */
|
|
@@ -19,5 +21,9 @@ declare const MIDDLEWARE_CACHE_HEADER = "x-middleware-cache";
|
|
|
19
21
|
declare const MIDDLEWARE_SKIP_HEADER = "x-middleware-skip";
|
|
20
22
|
/** Generic prefix for all middleware internal headers. */
|
|
21
23
|
declare const MIDDLEWARE_HEADER_PREFIX = "x-middleware-";
|
|
24
|
+
/** Authenticates an internal Pages Router on-demand revalidation request. */
|
|
25
|
+
declare const PRERENDER_REVALIDATE_HEADER = "x-prerender-revalidate";
|
|
26
|
+
/** Restricts on-demand revalidation to paths that were already generated. */
|
|
27
|
+
declare const PRERENDER_REVALIDATE_ONLY_GENERATED_HEADER = "x-prerender-revalidate-if-generated";
|
|
22
28
|
//#endregion
|
|
23
|
-
export { MIDDLEWARE_CACHE_HEADER, MIDDLEWARE_HEADER_PREFIX, MIDDLEWARE_OVERRIDE_HEADERS, MIDDLEWARE_REQUEST_HEADER_PREFIX, MIDDLEWARE_SET_COOKIE_HEADER, MIDDLEWARE_SKIP_HEADER, VINEXT_MW_CTX_HEADER, VINEXT_PRERENDER_ROUTE_PARAMS_HEADER, VINEXT_PRERENDER_SECRET_HEADER, VINEXT_PRERENDER_SPECULATIVE_HEADER };
|
|
29
|
+
export { MIDDLEWARE_CACHE_HEADER, MIDDLEWARE_HEADER_PREFIX, MIDDLEWARE_OVERRIDE_HEADERS, MIDDLEWARE_REQUEST_HEADER_PREFIX, MIDDLEWARE_SET_COOKIE_HEADER, MIDDLEWARE_SKIP_HEADER, PRERENDER_REVALIDATE_HEADER, PRERENDER_REVALIDATE_ONLY_GENERATED_HEADER, VINEXT_MW_CTX_HEADER, VINEXT_PRERENDER_ROUTE_PARAMS_HEADER, VINEXT_PRERENDER_SECRET_HEADER, VINEXT_PRERENDER_SPECULATIVE_HEADER, VINEXT_REVALIDATE_HOST_HEADER };
|
|
@@ -7,6 +7,8 @@ const VINEXT_PRERENDER_SECRET_HEADER = "x-vinext-prerender-secret";
|
|
|
7
7
|
const VINEXT_PRERENDER_ROUTE_PARAMS_HEADER = "x-vinext-prerender-route-params";
|
|
8
8
|
/** Indicates a build-time prerender render is probing whether a route can be static. */
|
|
9
9
|
const VINEXT_PRERENDER_SPECULATIVE_HEADER = "x-vinext-prerender-speculative";
|
|
10
|
+
/** Logical hostname carried only by authenticated Node revalidation loopbacks. */
|
|
11
|
+
const VINEXT_REVALIDATE_HOST_HEADER = "x-vinext-revalidate-host";
|
|
10
12
|
/** Prefix for forwarded request headers (e.g. `x-middleware-request-cookie`). */
|
|
11
13
|
const MIDDLEWARE_REQUEST_HEADER_PREFIX = "x-middleware-request-";
|
|
12
14
|
/** Comma-separated list of header names that middleware wants to override. */
|
|
@@ -19,5 +21,9 @@ const MIDDLEWARE_CACHE_HEADER = "x-middleware-cache";
|
|
|
19
21
|
const MIDDLEWARE_SKIP_HEADER = "x-middleware-skip";
|
|
20
22
|
/** Generic prefix for all middleware internal headers. */
|
|
21
23
|
const MIDDLEWARE_HEADER_PREFIX = "x-middleware-";
|
|
24
|
+
/** Authenticates an internal Pages Router on-demand revalidation request. */
|
|
25
|
+
const PRERENDER_REVALIDATE_HEADER = "x-prerender-revalidate";
|
|
26
|
+
/** Restricts on-demand revalidation to paths that were already generated. */
|
|
27
|
+
const PRERENDER_REVALIDATE_ONLY_GENERATED_HEADER = "x-prerender-revalidate-if-generated";
|
|
22
28
|
//#endregion
|
|
23
|
-
export { MIDDLEWARE_CACHE_HEADER, MIDDLEWARE_HEADER_PREFIX, MIDDLEWARE_OVERRIDE_HEADERS, MIDDLEWARE_REQUEST_HEADER_PREFIX, MIDDLEWARE_SET_COOKIE_HEADER, MIDDLEWARE_SKIP_HEADER, VINEXT_MW_CTX_HEADER, VINEXT_PRERENDER_ROUTE_PARAMS_HEADER, VINEXT_PRERENDER_SECRET_HEADER, VINEXT_PRERENDER_SPECULATIVE_HEADER };
|
|
29
|
+
export { MIDDLEWARE_CACHE_HEADER, MIDDLEWARE_HEADER_PREFIX, MIDDLEWARE_OVERRIDE_HEADERS, MIDDLEWARE_REQUEST_HEADER_PREFIX, MIDDLEWARE_SET_COOKIE_HEADER, MIDDLEWARE_SKIP_HEADER, PRERENDER_REVALIDATE_HEADER, PRERENDER_REVALIDATE_ONLY_GENERATED_HEADER, VINEXT_MW_CTX_HEADER, VINEXT_PRERENDER_ROUTE_PARAMS_HEADER, VINEXT_PRERENDER_SECRET_HEADER, VINEXT_PRERENDER_SPECULATIVE_HEADER, VINEXT_REVALIDATE_HOST_HEADER };
|