vinext 0.0.39 → 0.0.40

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (50) hide show
  1. package/dist/build/standalone.js +7 -0
  2. package/dist/build/standalone.js.map +1 -1
  3. package/dist/entries/app-rsc-entry.d.ts +2 -1
  4. package/dist/entries/app-rsc-entry.js +131 -245
  5. package/dist/entries/app-rsc-entry.js.map +1 -1
  6. package/dist/index.d.ts +32 -1
  7. package/dist/index.js +80 -6
  8. package/dist/index.js.map +1 -1
  9. package/dist/plugins/server-externals-manifest.d.ts +11 -1
  10. package/dist/plugins/server-externals-manifest.js +10 -3
  11. package/dist/plugins/server-externals-manifest.js.map +1 -1
  12. package/dist/routing/app-router.d.ts +10 -2
  13. package/dist/routing/app-router.js +37 -22
  14. package/dist/routing/app-router.js.map +1 -1
  15. package/dist/server/app-page-response.d.ts +12 -1
  16. package/dist/server/app-page-response.js +26 -7
  17. package/dist/server/app-page-response.js.map +1 -1
  18. package/dist/server/app-page-route-wiring.d.ts +79 -0
  19. package/dist/server/app-page-route-wiring.js +165 -0
  20. package/dist/server/app-page-route-wiring.js.map +1 -0
  21. package/dist/server/app-page-stream.js +3 -0
  22. package/dist/server/app-page-stream.js.map +1 -1
  23. package/dist/server/app-route-handler-response.js +4 -1
  24. package/dist/server/app-route-handler-response.js.map +1 -1
  25. package/dist/server/app-router-entry.d.ts +6 -1
  26. package/dist/server/app-router-entry.js +9 -2
  27. package/dist/server/app-router-entry.js.map +1 -1
  28. package/dist/server/prod-server.d.ts +1 -1
  29. package/dist/server/prod-server.js +37 -11
  30. package/dist/server/prod-server.js.map +1 -1
  31. package/dist/server/worker-utils.d.ts +4 -1
  32. package/dist/server/worker-utils.js +31 -1
  33. package/dist/server/worker-utils.js.map +1 -1
  34. package/dist/shims/error-boundary.d.ts +13 -4
  35. package/dist/shims/error-boundary.js +23 -3
  36. package/dist/shims/error-boundary.js.map +1 -1
  37. package/dist/shims/head.js.map +1 -1
  38. package/dist/shims/navigation.d.ts +16 -1
  39. package/dist/shims/navigation.js +18 -3
  40. package/dist/shims/navigation.js.map +1 -1
  41. package/dist/shims/router.js +127 -38
  42. package/dist/shims/router.js.map +1 -1
  43. package/dist/shims/script.js.map +1 -1
  44. package/dist/shims/server.d.ts +17 -4
  45. package/dist/shims/server.js +91 -73
  46. package/dist/shims/server.js.map +1 -1
  47. package/dist/shims/slot.d.ts +28 -0
  48. package/dist/shims/slot.js +49 -0
  49. package/dist/shims/slot.js.map +1 -0
  50. package/package.json +1 -2
@@ -1 +1 @@
1
- {"version":3,"file":"app-rsc-entry.js","names":[],"sources":["../../src/entries/app-rsc-entry.ts"],"sourcesContent":["/**\n * App Router RSC entry generator.\n *\n * Generates the virtual RSC entry module for the App Router.\n * The RSC entry does route matching and renders the component tree,\n * then delegates to the SSR entry for HTML generation.\n *\n * Previously housed in server/app-dev-server.ts.\n */\nimport fs from \"node:fs\";\nimport { resolveEntryPath } from \"./runtime-entry-module.js\";\nimport type {\n NextHeader,\n NextI18nConfig,\n NextRedirect,\n NextRewrite,\n} from \"../config/next-config.js\";\nimport type { AppRoute } from \"../routing/app-router.js\";\nimport { generateDevOriginCheckCode } from \"../server/dev-origin-check.js\";\nimport type { MetadataFileRoute } from \"../server/metadata-routes.js\";\nimport {\n generateMiddlewareMatcherCode,\n generateNormalizePathCode,\n generateSafeRegExpCode,\n generateRouteMatchNormalizationCode,\n} from \"../server/middleware-codegen.js\";\nimport { isProxyFile } from \"../server/middleware.js\";\n\n// Pre-computed absolute paths for generated-code imports. The virtual RSC\n// entry can't use relative imports (it has no real file location), so we\n// resolve these at code-generation time and embed them as absolute paths.\nconst configMatchersPath = resolveEntryPath(\"../config/config-matchers.js\", import.meta.url);\nconst requestPipelinePath = resolveEntryPath(\"../server/request-pipeline.js\", import.meta.url);\nconst requestContextShimPath = resolveEntryPath(\"../shims/request-context.js\", import.meta.url);\nconst normalizePathModulePath = resolveEntryPath(\"../server/normalize-path.js\", import.meta.url);\nconst appRouteHandlerRuntimePath = resolveEntryPath(\n \"../server/app-route-handler-runtime.js\",\n import.meta.url,\n);\nconst appRouteHandlerPolicyPath = resolveEntryPath(\n \"../server/app-route-handler-policy.js\",\n import.meta.url,\n);\nconst appRouteHandlerExecutionPath = resolveEntryPath(\n \"../server/app-route-handler-execution.js\",\n import.meta.url,\n);\nconst appRouteHandlerCachePath = resolveEntryPath(\n \"../server/app-route-handler-cache.js\",\n import.meta.url,\n);\nconst appPageCachePath = resolveEntryPath(\"../server/app-page-cache.js\", import.meta.url);\nconst appPageExecutionPath = resolveEntryPath(\"../server/app-page-execution.js\", import.meta.url);\nconst appPageBoundaryRenderPath = resolveEntryPath(\n \"../server/app-page-boundary-render.js\",\n import.meta.url,\n);\nconst appPageRenderPath = resolveEntryPath(\"../server/app-page-render.js\", import.meta.url);\nconst appPageRequestPath = resolveEntryPath(\"../server/app-page-request.js\", import.meta.url);\nconst appRouteHandlerResponsePath = resolveEntryPath(\n \"../server/app-route-handler-response.js\",\n import.meta.url,\n);\nconst routeTriePath = resolveEntryPath(\"../routing/route-trie.js\", import.meta.url);\nconst metadataRoutesPath = resolveEntryPath(\"../server/metadata-routes.js\", import.meta.url);\n\n/**\n * Resolved config options relevant to App Router request handling.\n * Passed from the Vite plugin where the full next.config.js is loaded.\n */\nexport type AppRouterConfig = {\n redirects?: NextRedirect[];\n rewrites?: {\n beforeFiles: NextRewrite[];\n afterFiles: NextRewrite[];\n fallback: NextRewrite[];\n };\n headers?: NextHeader[];\n /** Extra origins allowed for server action CSRF checks (from experimental.serverActions.allowedOrigins). */\n allowedOrigins?: string[];\n /** Extra origins allowed for dev server access (from allowedDevOrigins). */\n allowedDevOrigins?: string[];\n /** Body size limit for server actions in bytes (from experimental.serverActions.bodySizeLimit). */\n bodySizeLimit?: number;\n /** Internationalization routing config for middleware matcher locale handling. */\n i18n?: NextI18nConfig | null;\n /**\n * When true, the project has a `pages/` directory alongside the App Router.\n * The generated RSC entry exposes `/__vinext/prerender/pages-static-paths`\n * so `prerenderPages` can call `getStaticPaths` via `wrangler unstable_startWorker`\n * in CF Workers builds. `pageRoutes` is loaded from the SSR environment via\n * `import(\"./ssr/index.js\")`, which re-exports it from\n * `virtual:vinext-server-entry` when this flag is set.\n */\n hasPagesDir?: boolean;\n};\n\n/**\n * Generate the virtual RSC entry module.\n *\n * This runs in the `rsc` Vite environment (react-server condition).\n * It matches the incoming request URL to an app route, builds the\n * nested layout + page tree, and renders it to an RSC stream.\n */\nexport function generateRscEntry(\n appDir: string,\n routes: AppRoute[],\n middlewarePath?: string | null,\n metadataRoutes?: MetadataFileRoute[],\n globalErrorPath?: string | null,\n basePath?: string,\n trailingSlash?: boolean,\n config?: AppRouterConfig,\n instrumentationPath?: string | null,\n): string {\n const bp = basePath ?? \"\";\n const ts = trailingSlash ?? false;\n const redirects = config?.redirects ?? [];\n const rewrites = config?.rewrites ?? { beforeFiles: [], afterFiles: [], fallback: [] };\n const headers = config?.headers ?? [];\n const allowedOrigins = config?.allowedOrigins ?? [];\n const bodySizeLimit = config?.bodySizeLimit ?? 1 * 1024 * 1024;\n const i18nConfig = config?.i18n ?? null;\n const hasPagesDir = config?.hasPagesDir ?? false;\n // Build import map for all page and layout files\n const imports: string[] = [];\n const importMap: Map<string, string> = new Map();\n let importIdx = 0;\n\n function getImportVar(filePath: string): string {\n if (importMap.has(filePath)) return importMap.get(filePath)!;\n const varName = `mod_${importIdx++}`;\n const absPath = filePath.replace(/\\\\/g, \"/\");\n imports.push(`import * as ${varName} from ${JSON.stringify(absPath)};`);\n importMap.set(filePath, varName);\n return varName;\n }\n\n // Pre-register all modules\n for (const route of routes) {\n if (route.pagePath) getImportVar(route.pagePath);\n if (route.routePath) getImportVar(route.routePath);\n for (const layout of route.layouts) getImportVar(layout);\n for (const tmpl of route.templates) getImportVar(tmpl);\n if (route.loadingPath) getImportVar(route.loadingPath);\n if (route.errorPath) getImportVar(route.errorPath);\n if (route.layoutErrorPaths)\n for (const ep of route.layoutErrorPaths) {\n if (ep) getImportVar(ep);\n }\n if (route.notFoundPath) getImportVar(route.notFoundPath);\n for (const nfp of route.notFoundPaths || []) {\n if (nfp) getImportVar(nfp);\n }\n if (route.forbiddenPath) getImportVar(route.forbiddenPath);\n if (route.unauthorizedPath) getImportVar(route.unauthorizedPath);\n // Register parallel slot modules\n for (const slot of route.parallelSlots) {\n if (slot.pagePath) getImportVar(slot.pagePath);\n if (slot.defaultPath) getImportVar(slot.defaultPath);\n if (slot.layoutPath) getImportVar(slot.layoutPath);\n if (slot.loadingPath) getImportVar(slot.loadingPath);\n if (slot.errorPath) getImportVar(slot.errorPath);\n // Register intercepting route page modules\n for (const ir of slot.interceptingRoutes) {\n getImportVar(ir.pagePath);\n }\n }\n }\n\n // Build route table as serialized JS\n const routeEntries = routes.map((route) => {\n const layoutVars = route.layouts.map((l) => getImportVar(l));\n const templateVars = route.templates.map((t) => getImportVar(t));\n const notFoundVars = (route.notFoundPaths || []).map((nf) => (nf ? getImportVar(nf) : \"null\"));\n const slotEntries = route.parallelSlots.map((slot) => {\n const interceptEntries = slot.interceptingRoutes.map(\n (ir) => ` {\n convention: ${JSON.stringify(ir.convention)},\n targetPattern: ${JSON.stringify(ir.targetPattern)},\n page: ${getImportVar(ir.pagePath)},\n params: ${JSON.stringify(ir.params)},\n }`,\n );\n return ` ${JSON.stringify(slot.name)}: {\n page: ${slot.pagePath ? getImportVar(slot.pagePath) : \"null\"},\n default: ${slot.defaultPath ? getImportVar(slot.defaultPath) : \"null\"},\n layout: ${slot.layoutPath ? getImportVar(slot.layoutPath) : \"null\"},\n loading: ${slot.loadingPath ? getImportVar(slot.loadingPath) : \"null\"},\n error: ${slot.errorPath ? getImportVar(slot.errorPath) : \"null\"},\n layoutIndex: ${slot.layoutIndex},\n intercepts: [\n${interceptEntries.join(\",\\n\")}\n ],\n }`;\n });\n const layoutErrorVars = (route.layoutErrorPaths || []).map((ep) =>\n ep ? getImportVar(ep) : \"null\",\n );\n return ` {\n pattern: ${JSON.stringify(route.pattern)},\n patternParts: ${JSON.stringify(route.patternParts)},\n isDynamic: ${route.isDynamic},\n params: ${JSON.stringify(route.params)},\n page: ${route.pagePath ? getImportVar(route.pagePath) : \"null\"},\n routeHandler: ${route.routePath ? getImportVar(route.routePath) : \"null\"},\n layouts: [${layoutVars.join(\", \")}],\n routeSegments: ${JSON.stringify(route.routeSegments)},\n layoutTreePositions: ${JSON.stringify(route.layoutTreePositions)},\n templates: [${templateVars.join(\", \")}],\n errors: [${layoutErrorVars.join(\", \")}],\n slots: {\n${slotEntries.join(\",\\n\")}\n },\n loading: ${route.loadingPath ? getImportVar(route.loadingPath) : \"null\"},\n error: ${route.errorPath ? getImportVar(route.errorPath) : \"null\"},\n notFound: ${route.notFoundPath ? getImportVar(route.notFoundPath) : \"null\"},\n notFounds: [${notFoundVars.join(\", \")}],\n forbidden: ${route.forbiddenPath ? getImportVar(route.forbiddenPath) : \"null\"},\n unauthorized: ${route.unauthorizedPath ? getImportVar(route.unauthorizedPath) : \"null\"},\n }`;\n });\n\n // Find root not-found/forbidden/unauthorized pages and root layouts for global error handling\n const rootRoute = routes.find((r) => r.pattern === \"/\");\n const rootNotFoundVar = rootRoute?.notFoundPath ? getImportVar(rootRoute.notFoundPath) : null;\n const rootForbiddenVar = rootRoute?.forbiddenPath ? getImportVar(rootRoute.forbiddenPath) : null;\n const rootUnauthorizedVar = rootRoute?.unauthorizedPath\n ? getImportVar(rootRoute.unauthorizedPath)\n : null;\n const rootLayoutVars = rootRoute ? rootRoute.layouts.map((l) => getImportVar(l)) : [];\n\n // Global error boundary (app/global-error.tsx)\n const globalErrorVar = globalErrorPath ? getImportVar(globalErrorPath) : null;\n\n // Build metadata route handling\n const effectiveMetaRoutes = metadataRoutes ?? [];\n const dynamicMetaRoutes = effectiveMetaRoutes.filter((r) => r.isDynamic);\n\n // Import dynamic metadata modules\n for (const mr of dynamicMetaRoutes) {\n getImportVar(mr.filePath);\n }\n\n // Build metadata route table\n // For static metadata files, read the file content at code-generation time\n // and embed it as base64. This ensures static metadata files work on runtimes\n // without filesystem access (e.g., Cloudflare Workers).\n //\n // For metadata routes in dynamic segments (e.g., /blog/[slug]/opengraph-image),\n // generate patternParts so the runtime can use matchPattern() instead of strict\n // equality — the same matching used for intercept routes.\n const metaRouteEntries = effectiveMetaRoutes.map((mr) => {\n // Convert dynamic segments in servedUrl to matchPattern format.\n // Keep in sync with routing/app-router.ts patternParts generation.\n // [param] → :param\n // [...param] → :param+\n // [[...param]] → :param*\n const patternParts =\n mr.isDynamic && mr.servedUrl.includes(\"[\")\n ? JSON.stringify(\n mr.servedUrl\n .split(\"/\")\n .filter(Boolean)\n .map((seg) => {\n if (seg.startsWith(\"[[...\") && seg.endsWith(\"]]\"))\n return \":\" + seg.slice(5, -2) + \"*\";\n if (seg.startsWith(\"[...\") && seg.endsWith(\"]\"))\n return \":\" + seg.slice(4, -1) + \"+\";\n if (seg.startsWith(\"[\") && seg.endsWith(\"]\")) return \":\" + seg.slice(1, -1);\n return seg;\n }),\n )\n : null;\n\n if (mr.isDynamic) {\n return ` {\n type: ${JSON.stringify(mr.type)},\n isDynamic: true,\n servedUrl: ${JSON.stringify(mr.servedUrl)},\n contentType: ${JSON.stringify(mr.contentType)},\n module: ${getImportVar(mr.filePath)},${patternParts ? `\\n patternParts: ${patternParts},` : \"\"}\n }`;\n }\n // Static: read file and embed as base64\n let fileDataBase64 = \"\";\n try {\n const buf = fs.readFileSync(mr.filePath);\n fileDataBase64 = buf.toString(\"base64\");\n } catch {\n // File unreadable — will serve empty response at runtime\n }\n return ` {\n type: ${JSON.stringify(mr.type)},\n isDynamic: false,\n servedUrl: ${JSON.stringify(mr.servedUrl)},\n contentType: ${JSON.stringify(mr.contentType)},\n fileDataBase64: ${JSON.stringify(fileDataBase64)},\n }`;\n });\n\n return `\nimport {\n renderToReadableStream as _renderToReadableStream,\n decodeReply,\n loadServerAction,\n createTemporaryReferenceSet,\n} from \"@vitejs/plugin-rsc/rsc\";\nimport { AsyncLocalStorage } from \"node:async_hooks\";\n\n// React Flight emits HL hints with \"stylesheet\" for CSS, but the HTML spec\n// requires \"style\" for <link rel=\"preload\">. Fix at the source so every\n// consumer (SSR embed, client-side navigation, server actions) gets clean data.\n//\n// Flight lines are newline-delimited, so we buffer partial lines across chunks\n// to guarantee the regex never sees a split hint.\nfunction renderToReadableStream(model, options) {\n const _hlFixRe = /(\\\\d*:HL\\\\[.*?),\"stylesheet\"(\\\\]|,)/g;\n const stream = _renderToReadableStream(model, options);\n const decoder = new TextDecoder();\n const encoder = new TextEncoder();\n let carry = \"\";\n return stream.pipeThrough(new TransformStream({\n transform(chunk, controller) {\n const text = carry + decoder.decode(chunk, { stream: true });\n const lastNl = text.lastIndexOf(\"\\\\n\");\n if (lastNl === -1) {\n carry = text;\n return;\n }\n carry = text.slice(lastNl + 1);\n controller.enqueue(encoder.encode(text.slice(0, lastNl + 1).replace(_hlFixRe, '$1,\"style\"$2')));\n },\n flush(controller) {\n const text = carry + decoder.decode();\n if (text) controller.enqueue(encoder.encode(text.replace(_hlFixRe, '$1,\"style\"$2')));\n }\n }));\n}\nimport { createElement, Suspense, Fragment } from \"react\";\nimport { setNavigationContext as _setNavigationContextOrig, getNavigationContext as _getNavigationContext } from \"next/navigation\";\nimport { setHeadersContext, headersContextFromRequest, getDraftModeCookieHeader, getAndClearPendingCookies, consumeDynamicUsage, markDynamicUsage, applyMiddlewareRequestHeaders, getHeadersContext, setHeadersAccessPhase } from \"next/headers\";\nimport { NextRequest, NextFetchEvent } from \"next/server\";\nimport { ErrorBoundary, NotFoundBoundary } from \"vinext/error-boundary\";\nimport { LayoutSegmentProvider } from \"vinext/layout-segment-context\";\nimport { MetadataHead, mergeMetadata, resolveModuleMetadata, ViewportHead, mergeViewport, resolveModuleViewport } from \"vinext/metadata\";\n${middlewarePath ? `import * as middlewareModule from ${JSON.stringify(middlewarePath.replace(/\\\\/g, \"/\"))};` : \"\"}\n${instrumentationPath ? `import * as _instrumentation from ${JSON.stringify(instrumentationPath.replace(/\\\\/g, \"/\"))};` : \"\"}\n${effectiveMetaRoutes.length > 0 ? `import { sitemapToXml, robotsToText, manifestToJson } from ${JSON.stringify(metadataRoutesPath)};` : \"\"}\nimport { requestContextFromRequest, normalizeHost, matchRedirect, matchRewrite, matchHeaders, isExternalUrl, proxyExternalRequest, sanitizeDestination } from ${JSON.stringify(configMatchersPath)};\nimport { decodePathParams as __decodePathParams } from ${JSON.stringify(normalizePathModulePath)};\nimport { validateCsrfOrigin, validateImageUrl, guardProtocolRelativeUrl, hasBasePath, stripBasePath, normalizeTrailingSlash, processMiddlewareHeaders } from ${JSON.stringify(requestPipelinePath)};\nimport {\n isKnownDynamicAppRoute as __isKnownDynamicAppRoute,\n} from ${JSON.stringify(appRouteHandlerRuntimePath)};\nimport {\n getAppRouteHandlerRevalidateSeconds as __getAppRouteHandlerRevalidateSeconds,\n hasAppRouteHandlerDefaultExport as __hasAppRouteHandlerDefaultExport,\n resolveAppRouteHandlerMethod as __resolveAppRouteHandlerMethod,\n shouldReadAppRouteHandlerCache as __shouldReadAppRouteHandlerCache,\n} from ${JSON.stringify(appRouteHandlerPolicyPath)};\nimport {\n executeAppRouteHandler as __executeAppRouteHandler,\n} from ${JSON.stringify(appRouteHandlerExecutionPath)};\nimport { readAppRouteHandlerCacheResponse as __readAppRouteHandlerCacheResponse } from ${JSON.stringify(appRouteHandlerCachePath)};\nimport { readAppPageCacheResponse as __readAppPageCacheResponse } from ${JSON.stringify(appPageCachePath)};\nimport {\n buildAppPageFontLinkHeader as __buildAppPageFontLinkHeader,\n buildAppPageSpecialErrorResponse as __buildAppPageSpecialErrorResponse,\n readAppPageTextStream as __readAppPageTextStream,\n resolveAppPageSpecialError as __resolveAppPageSpecialError,\n teeAppPageRscStreamForCapture as __teeAppPageRscStreamForCapture,\n} from ${JSON.stringify(appPageExecutionPath)};\nimport {\n renderAppPageErrorBoundary as __renderAppPageErrorBoundary,\n renderAppPageHttpAccessFallback as __renderAppPageHttpAccessFallback,\n} from ${JSON.stringify(appPageBoundaryRenderPath)};\nimport {\n renderAppPageLifecycle as __renderAppPageLifecycle,\n} from ${JSON.stringify(appPageRenderPath)};\nimport {\n buildAppPageElement as __buildAppPageElement,\n resolveAppPageIntercept as __resolveAppPageIntercept,\n validateAppPageDynamicParams as __validateAppPageDynamicParams,\n} from ${JSON.stringify(appPageRequestPath)};\nimport {\n applyRouteHandlerMiddlewareContext as __applyRouteHandlerMiddlewareContext,\n} from ${JSON.stringify(appRouteHandlerResponsePath)};\nimport { _consumeRequestScopedCacheLife, getCacheHandler } from \"next/cache\";\nimport { getRequestExecutionContext as _getRequestExecutionContext } from ${JSON.stringify(requestContextShimPath)};\nimport { ensureFetchPatch as _ensureFetchPatch, getCollectedFetchTags } from \"vinext/fetch-cache\";\nimport { buildRouteTrie as _buildRouteTrie, trieMatch as _trieMatch } from ${JSON.stringify(routeTriePath)};\n// Import server-only state module to register ALS-backed accessors.\nimport \"vinext/navigation-state\";\nimport { runWithRequestContext as _runWithUnifiedCtx, createRequestContext as _createUnifiedCtx } from \"vinext/unified-request-context\";\nimport { reportRequestError as _reportRequestError } from \"vinext/instrumentation\";\nimport { getSSRFontLinks as _getSSRFontLinks, getSSRFontStyles as _getSSRFontStylesGoogle, getSSRFontPreloads as _getSSRFontPreloadsGoogle } from \"next/font/google\";\nimport { getSSRFontStyles as _getSSRFontStylesLocal, getSSRFontPreloads as _getSSRFontPreloadsLocal } from \"next/font/local\";\nfunction _getSSRFontStyles() { return [..._getSSRFontStylesGoogle(), ..._getSSRFontStylesLocal()]; }\nfunction _getSSRFontPreloads() { return [..._getSSRFontPreloadsGoogle(), ..._getSSRFontPreloadsLocal()]; }\n${hasPagesDir ? `// Note: pageRoutes loaded lazily via SSR env in /__vinext/prerender/pages-static-paths handler` : \"\"}\n\n// ALS used to suppress the expected \"Invalid hook call\" dev warning when\n// layout/page components are probed outside React's render cycle. Patching\n// console.error once at module load (instead of per-request) avoids the\n// concurrent-request issue where request A's suppression filter could\n// swallow real errors from request B.\nconst _suppressHookWarningAls = new AsyncLocalStorage();\nconst _origConsoleError = console.error;\nconsole.error = (...args) => {\n if (_suppressHookWarningAls.getStore() === true &&\n typeof args[0] === \"string\" &&\n args[0].includes(\"Invalid hook call\")) return;\n _origConsoleError.apply(console, args);\n};\n\n// Set navigation context in the ALS-backed store. \"use client\" components\n// rendered during SSR need the pathname/searchParams/params but the SSR\n// environment has a separate module instance of next/navigation.\n// Use _getNavigationContext() to read the current context — never cache\n// it in a module-level variable (that would leak between concurrent requests).\nfunction setNavigationContext(ctx) {\n _setNavigationContextOrig(ctx);\n}\n\n// ISR cache is disabled in dev mode — every request re-renders fresh,\n// matching Next.js dev behavior. Cache-Control headers are still emitted\n// based on export const revalidate for testing purposes.\n// Production ISR uses the MemoryCacheHandler (or configured KV handler).\n//\n// These helpers are inlined instead of imported from isr-cache.js because\n// the virtual RSC entry module runs in the RSC Vite environment which\n// cannot use dynamic imports at the module-evaluation level for server-only\n// modules, and direct imports must use the pre-computed absolute paths.\nasync function __isrGet(key) {\n const handler = getCacheHandler();\n const result = await handler.get(key);\n if (!result || !result.value) return null;\n return { value: result, isStale: result.cacheState === \"stale\" };\n}\nasync function __isrSet(key, data, revalidateSeconds, tags) {\n const handler = getCacheHandler();\n await handler.set(key, data, { revalidate: revalidateSeconds, tags: Array.isArray(tags) ? tags : [] });\n}\nfunction __pageCacheTags(pathname, extraTags) {\n const tags = [pathname, \"_N_T_\" + pathname];\n // Layout hierarchy tags — matches Next.js getDerivedTags.\n tags.push(\"_N_T_/layout\");\n const segments = pathname.split(\"/\");\n let built = \"\";\n for (let i = 1; i < segments.length; i++) {\n if (segments[i]) {\n built += \"/\" + segments[i];\n tags.push(\"_N_T_\" + built + \"/layout\");\n }\n }\n // Leaf page tag — revalidatePath(path, \"page\") targets this.\n tags.push(\"_N_T_\" + built + \"/page\");\n if (Array.isArray(extraTags)) {\n for (const tag of extraTags) {\n if (!tags.includes(tag)) tags.push(tag);\n }\n }\n return tags;\n}\n// Note: cache entries are written with \\`headers: undefined\\`. Next.js stores\n// response headers (e.g. set-cookie from cookies().set() during render) in the\n// cache entry so they can be replayed on HIT. We don't do this because:\n// 1. Pages that call cookies().set() during render trigger dynamicUsedDuringRender,\n// which opts them out of ISR caching before we reach the write path.\n// 2. Custom response headers set via next/headers are not yet captured separately\n// from the live Response object in vinext's server pipeline.\n// In practice this means ISR-cached responses won't replay render-time set-cookie\n// headers — but that case is already prevented by the dynamic-usage opt-out.\n// TODO: capture render-time response headers for full Next.js parity.\nconst __pendingRegenerations = new Map();\nfunction __triggerBackgroundRegeneration(key, renderFn) {\n if (__pendingRegenerations.has(key)) return;\n const promise = renderFn()\n .catch((err) => console.error(\"[vinext] ISR regen failed for \" + key + \":\", err))\n .finally(() => __pendingRegenerations.delete(key));\n __pendingRegenerations.set(key, promise);\n const ctx = _getRequestExecutionContext();\n if (ctx && typeof ctx.waitUntil === \"function\") ctx.waitUntil(promise);\n}\n// HTML and RSC are stored under separate keys — matching Next.js's file-system\n// layout (.html / .rsc) — so each request type reads and writes its own key\n// independently with no races or partial-entry sentinels.\n//\n// Key format: \"app:<buildId>:<pathname>:<suffix>\"\n// Long-pathname fallback: \"app:<buildId>:__hash:<fnv1a64(pathname)>:<suffix>\"\n// Without buildId (should not happen in production): \"app:<pathname>:<suffix>\"\n// The 200-char threshold keeps the full key well under Cloudflare KV's 512-byte limit\n// even after adding the build ID and suffix. FNV-1a 64 is used for the hash (two\n// 32-bit rounds) to give a ~64-bit output with negligible collision probability for\n// realistic pathname lengths.\n// Keep prefix construction and hashing logic in sync with isrCacheKey() in server/isr-cache.ts.\nfunction __isrFnv1a64(s) {\n // h1 uses the standard FNV-1a 32-bit offset basis (0x811c9dc5).\n let h1 = 0x811c9dc5;\n for (let i = 0; i < s.length; i++) { h1 ^= s.charCodeAt(i); h1 = (h1 * 0x01000193) >>> 0; }\n // h2 uses a different seed (0x050c5d1f — the FNV-1a hash of the string \"vinext\")\n // so the two rounds are independently seeded and their outputs are decorrelated.\n // Concatenating two independently-seeded 32-bit FNV-1a hashes gives an effective\n // 64-bit hash. A random non-standard seed would also work; we derive it from a\n // fixed string so the choice is auditable and deterministic across rebuilds.\n let h2 = 0x050c5d1f;\n for (let i = 0; i < s.length; i++) { h2 ^= s.charCodeAt(i); h2 = (h2 * 0x01000193) >>> 0; }\n return h1.toString(36) + h2.toString(36);\n}\nfunction __isrCacheKey(pathname, suffix) {\n const normalized = pathname === \"/\" ? \"/\" : pathname.replace(/\\\\/$/, \"\");\n // __VINEXT_BUILD_ID is replaced at compile time by Vite's define plugin.\n const buildId = process.env.__VINEXT_BUILD_ID;\n const prefix = buildId ? \"app:\" + buildId : \"app\";\n const key = prefix + \":\" + normalized + \":\" + suffix;\n if (key.length <= 200) return key;\n // Pathname too long — hash it to keep under KV's 512-byte key limit.\n return prefix + \":__hash:\" + __isrFnv1a64(normalized) + \":\" + suffix;\n}\nfunction __isrHtmlKey(pathname) { return __isrCacheKey(pathname, \"html\"); }\nfunction __isrRscKey(pathname) { return __isrCacheKey(pathname, \"rsc\"); }\nfunction __isrRouteKey(pathname) { return __isrCacheKey(pathname, \"route\"); }\n// Verbose cache logging — opt in with NEXT_PRIVATE_DEBUG_CACHE=1.\n// Matches the env var Next.js uses for its own cache debug output so operators\n// have a single knob for all cache tracing.\nconst __isrDebug = process.env.NEXT_PRIVATE_DEBUG_CACHE\n ? console.debug.bind(console, \"[vinext] ISR:\")\n : undefined;\n\n// Normalize null-prototype objects from matchPattern() into thenable objects\n// that work both as Promises (for Next.js 15+ async params) and as plain\n// objects with synchronous property access (for pre-15 code like params.id).\n//\n// matchPattern() uses Object.create(null), producing objects without\n// Object.prototype. The RSC serializer rejects these. Spreading ({...obj})\n// restores a normal prototype. Object.assign onto the Promise preserves\n// synchronous property access (params.id, params.slug) that existing\n// components and test fixtures rely on.\nfunction makeThenableParams(obj) {\n const plain = { ...obj };\n return Object.assign(Promise.resolve(plain), plain);\n}\n\n// Resolve route tree segments to actual values using matched params.\n// Dynamic segments like [id] are replaced with param values, catch-all\n// segments like [...slug] are joined with \"/\", and route groups are kept as-is.\nfunction __resolveChildSegments(routeSegments, treePosition, params) {\n var raw = routeSegments.slice(treePosition);\n var result = [];\n for (var j = 0; j < raw.length; j++) {\n var seg = raw[j];\n // Optional catch-all: [[...param]]\n if (seg.indexOf(\"[[...\") === 0 && seg.charAt(seg.length - 1) === \"]\" && seg.charAt(seg.length - 2) === \"]\") {\n var pn = seg.slice(5, -2);\n var v = params[pn];\n // Skip empty optional catch-all (e.g., visiting /blog on [[...slug]] route)\n if (Array.isArray(v) && v.length === 0) continue;\n if (v == null) continue;\n result.push(Array.isArray(v) ? v.join(\"/\") : v);\n // Catch-all: [...param]\n } else if (seg.indexOf(\"[...\") === 0 && seg.charAt(seg.length - 1) === \"]\") {\n var pn2 = seg.slice(4, -1);\n var v2 = params[pn2];\n result.push(Array.isArray(v2) ? v2.join(\"/\") : (v2 || seg));\n // Dynamic: [param]\n } else if (seg.charAt(0) === \"[\" && seg.charAt(seg.length - 1) === \"]\" && seg.indexOf(\".\") === -1) {\n var pn3 = seg.slice(1, -1);\n result.push(params[pn3] || seg);\n } else {\n result.push(seg);\n }\n }\n return result;\n}\n\n// djb2 hash — matches Next.js's stringHash for digest generation.\n// Produces a stable numeric string from error message + stack.\nfunction __errorDigest(str) {\n let hash = 5381;\n for (let i = str.length - 1; i >= 0; i--) {\n hash = (hash * 33) ^ str.charCodeAt(i);\n }\n return (hash >>> 0).toString();\n}\n\n// Sanitize an error for client consumption. In production, replaces the error\n// with a generic Error that only carries a digest hash (matching Next.js\n// behavior). In development, returns the original error for debugging.\n// Navigation errors (redirect, notFound, etc.) are always passed through\n// unchanged since their digests are used for client-side routing.\nfunction __sanitizeErrorForClient(error) {\n // Navigation errors must pass through with their digest intact\n if (__resolveAppPageSpecialError(error)) {\n return error;\n }\n // In development, pass through the original error for debugging\n if (process.env.NODE_ENV !== \"production\") {\n return error;\n }\n // In production, create a sanitized error with only a digest hash\n const msg = error instanceof Error ? error.message : String(error);\n const stack = error instanceof Error ? (error.stack || \"\") : \"\";\n const sanitized = new Error(\n \"An error occurred in the Server Components render. \" +\n \"The specific message is omitted in production builds to avoid leaking sensitive details. \" +\n \"A digest property is included on this error instance which may provide additional details about the nature of the error.\"\n );\n sanitized.digest = __errorDigest(msg + stack);\n return sanitized;\n}\n\n// onError callback for renderToReadableStream — preserves the digest for\n// Next.js navigation errors (redirect, notFound, forbidden, unauthorized)\n// thrown during RSC streaming (e.g. inside Suspense boundaries).\n// For non-navigation errors in production, generates a digest hash so the\n// error can be correlated with server logs without leaking details.\nfunction rscOnError(error, requestInfo, errorContext) {\n if (error && typeof error === \"object\" && \"digest\" in error) {\n return String(error.digest);\n }\n\n // In dev, detect the \"Only plain objects\" RSC serialization error and emit\n // an actionable hint. This error occurs when a Server Component passes a\n // class instance, ES module namespace object, or null-prototype object as a\n // prop to a Client Component.\n //\n // Root cause: Vite bundles modules as true ESM (module namespace objects\n // have a null-like internal slot), while Next.js's webpack build produces\n // plain CJS-wrapped objects with __esModule:true. React's RSC serializer\n // accepts the latter as plain objects but rejects the former — which means\n // code that accidentally passes \"import * as X\" works in webpack/Next.js\n // but correctly fails in vinext.\n //\n // Common triggers:\n // - \"import * as utils from './utils'\" passed as a prop\n // - class instances (new Foo()) passed as props\n // - Date / Map / Set instances passed as props\n // - Objects with Object.create(null) (null prototype)\n if (\n process.env.NODE_ENV !== \"production\" &&\n error instanceof Error &&\n error.message.includes(\"Only plain objects, and a few built-ins, can be passed to Client Components\")\n ) {\n console.error(\n \"[vinext] RSC serialization error: a non-plain object was passed from a Server Component to a Client Component.\\\\n\" +\n \"\\\\n\" +\n \"Common causes:\\\\n\" +\n \" * Passing a module namespace (import * as X) directly as a prop.\\\\n\" +\n \" Unlike Next.js (webpack), Vite produces real ESM module namespace objects\\\\n\" +\n \" which are not serializable. Fix: pass individual values instead,\\\\n\" +\n \" e.g. <Comp value={module.value} />\\\\n\" +\n \" * Passing a class instance (new Foo()) as a prop.\\\\n\" +\n \" Fix: convert to a plain object, e.g. { id: foo.id, name: foo.name }\\\\n\" +\n \" * Passing a Date, Map, or Set. Use .toISOString(), [...map.entries()], etc.\\\\n\" +\n \" * Passing Object.create(null). Use { ...obj } to restore a prototype.\\\\n\" +\n \"\\\\n\" +\n \"Original error:\",\n error.message,\n );\n return undefined;\n }\n\n if (requestInfo && errorContext && error) {\n _reportRequestError(\n error instanceof Error ? error : new Error(String(error)),\n requestInfo,\n errorContext,\n );\n }\n\n // In production, generate a digest hash for non-navigation errors\n if (process.env.NODE_ENV === \"production\" && error) {\n const msg = error instanceof Error ? error.message : String(error);\n const stack = error instanceof Error ? (error.stack || \"\") : \"\";\n return __errorDigest(msg + stack);\n }\n return undefined;\n}\n\nfunction createRscOnErrorHandler(request, pathname, routePath) {\n const requestInfo = {\n path: pathname,\n method: request.method,\n headers: Object.fromEntries(request.headers.entries()),\n };\n const errorContext = {\n routerKind: \"App Router\",\n routePath: routePath || pathname,\n routeType: \"render\",\n };\n return function(error) {\n return rscOnError(error, requestInfo, errorContext);\n };\n}\n\n${imports.join(\"\\n\")}\n\n${\n instrumentationPath\n ? `// Run instrumentation register() exactly once, lazily on the first request.\n// Previously this was a top-level await, which blocked the entire module graph\n// from finishing initialization until register() resolved — adding that latency\n// to every cold start. Moving it here preserves the \"runs before any request is\n// handled\" guarantee while not blocking V8 isolate initialization.\n// On Cloudflare Workers, module evaluation happens synchronously in the isolate\n// startup phase; a top-level await extends that phase and increases cold-start\n// wall time for all requests, not just the first.\nlet __instrumentationInitialized = false;\nlet __instrumentationInitPromise = null;\nasync function __ensureInstrumentation() {\n if (process.env.VINEXT_PRERENDER === \"1\") return;\n if (__instrumentationInitialized) return;\n if (__instrumentationInitPromise) return __instrumentationInitPromise;\n __instrumentationInitPromise = (async () => {\n if (typeof _instrumentation.register === \"function\") {\n await _instrumentation.register();\n }\n // Store the onRequestError handler on globalThis so it is visible to\n // reportRequestError() (imported as _reportRequestError above) regardless\n // of which Vite environment module graph it is called from. With\n // @vitejs/plugin-rsc the RSC and SSR environments run in the same Node.js\n // process and share globalThis. With @cloudflare/vite-plugin everything\n // runs inside the Worker so globalThis is the Worker's global — also correct.\n if (typeof _instrumentation.onRequestError === \"function\") {\n globalThis.__VINEXT_onRequestErrorHandler__ = _instrumentation.onRequestError;\n }\n __instrumentationInitialized = true;\n })();\n return __instrumentationInitPromise;\n}`\n : \"\"\n}\n\nconst routes = [\n${routeEntries.join(\",\\n\")}\n];\nconst _routeTrie = _buildRouteTrie(routes);\n\nconst metadataRoutes = [\n${metaRouteEntries.join(\",\\n\")}\n];\n\nconst rootNotFoundModule = ${rootNotFoundVar ? rootNotFoundVar : \"null\"};\nconst rootForbiddenModule = ${rootForbiddenVar ? rootForbiddenVar : \"null\"};\nconst rootUnauthorizedModule = ${rootUnauthorizedVar ? rootUnauthorizedVar : \"null\"};\nconst rootLayouts = [${rootLayoutVars.join(\", \")}];\n\n/**\n * Render an HTTP access fallback page (not-found/forbidden/unauthorized) with layouts and noindex meta.\n * Returns null if no matching component is available.\n *\n * @param opts.boundaryComponent - Override the boundary component (for layout-level notFound)\n * @param opts.layouts - Override the layouts to wrap with (for layout-level notFound, excludes the throwing layout)\n */\nasync function renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, opts) {\n return __renderAppPageHttpAccessFallback({\n boundaryComponent: opts?.boundaryComponent ?? null,\n buildFontLinkHeader: __buildAppPageFontLinkHeader,\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n createRscOnErrorHandler(pathname, routePath) {\n return createRscOnErrorHandler(request, pathname, routePath);\n },\n getFontLinks: _getSSRFontLinks,\n getFontPreloads: _getSSRFontPreloads,\n getFontStyles: _getSSRFontStyles,\n getNavigationContext: _getNavigationContext,\n globalErrorModule: ${globalErrorVar ? globalErrorVar : \"null\"},\n isRscRequest,\n layoutModules: opts?.layouts ?? null,\n loadSsrHandler() {\n return import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n },\n makeThenableParams,\n matchedParams: opts?.matchedParams ?? route?.params ?? {},\n requestUrl: request.url,\n resolveChildSegments: __resolveChildSegments,\n rootForbiddenModule: rootForbiddenModule,\n rootLayouts: rootLayouts,\n rootNotFoundModule: rootNotFoundModule,\n rootUnauthorizedModule: rootUnauthorizedModule,\n route,\n renderToReadableStream,\n statusCode,\n });\n}\n\n/** Convenience: render a not-found page (404) */\nasync function renderNotFoundPage(route, isRscRequest, request, matchedParams) {\n return renderHTTPAccessFallbackPage(route, 404, isRscRequest, request, { matchedParams });\n}\n\n/**\n * Render an error.tsx boundary page when a server component or generateMetadata() throws.\n * Returns null if no error boundary component is available for this route.\n *\n * Next.js returns HTTP 200 when error.tsx catches an error (the error is \"handled\"\n * by the boundary). This matches that behavior intentionally.\n */\nasync function renderErrorBoundaryPage(route, error, isRscRequest, request, matchedParams) {\n return __renderAppPageErrorBoundary({\n buildFontLinkHeader: __buildAppPageFontLinkHeader,\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n createRscOnErrorHandler(pathname, routePath) {\n return createRscOnErrorHandler(request, pathname, routePath);\n },\n error,\n getFontLinks: _getSSRFontLinks,\n getFontPreloads: _getSSRFontPreloads,\n getFontStyles: _getSSRFontStyles,\n getNavigationContext: _getNavigationContext,\n globalErrorModule: ${globalErrorVar ? globalErrorVar : \"null\"},\n isRscRequest,\n loadSsrHandler() {\n return import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n },\n makeThenableParams,\n matchedParams: matchedParams ?? route?.params ?? {},\n requestUrl: request.url,\n resolveChildSegments: __resolveChildSegments,\n rootLayouts: rootLayouts,\n route,\n renderToReadableStream,\n sanitizeErrorForClient: __sanitizeErrorForClient,\n });\n}\n\nfunction matchRoute(url) {\n const pathname = url.split(\"?\")[0];\n let normalizedUrl = pathname === \"/\" ? \"/\" : pathname.replace(/\\\\/$/, \"\");\n // NOTE: Do NOT decodeURIComponent here. The caller is responsible for decoding\n // the pathname exactly once at the request entry point. Decoding again here\n // would cause inconsistent path matching between middleware and routing.\n const urlParts = normalizedUrl.split(\"/\").filter(Boolean);\n return _trieMatch(_routeTrie, urlParts);\n}\n\n// matchPattern is kept for findIntercept (linear scan over small interceptLookup array).\nfunction matchPattern(urlParts, patternParts) {\n const params = Object.create(null);\n for (let i = 0; i < patternParts.length; i++) {\n const pp = patternParts[i];\n if (pp.endsWith(\"+\")) {\n if (i !== patternParts.length - 1) return null;\n const paramName = pp.slice(1, -1);\n const remaining = urlParts.slice(i);\n if (remaining.length === 0) return null;\n params[paramName] = remaining;\n return params;\n }\n if (pp.endsWith(\"*\")) {\n if (i !== patternParts.length - 1) return null;\n const paramName = pp.slice(1, -1);\n params[paramName] = urlParts.slice(i);\n return params;\n }\n if (pp.startsWith(\":\")) {\n if (i >= urlParts.length) return null;\n params[pp.slice(1)] = urlParts[i];\n continue;\n }\n if (i >= urlParts.length || urlParts[i] !== pp) return null;\n }\n if (urlParts.length !== patternParts.length) return null;\n return params;\n}\n\n// Build a global intercepting route lookup for RSC navigation.\n// Maps target URL patterns to { sourceRouteIndex, slotName, interceptPage, params }.\nconst interceptLookup = [];\nfor (let ri = 0; ri < routes.length; ri++) {\n const r = routes[ri];\n if (!r.slots) continue;\n for (const [slotName, slotMod] of Object.entries(r.slots)) {\n if (!slotMod.intercepts) continue;\n for (const intercept of slotMod.intercepts) {\n interceptLookup.push({\n sourceRouteIndex: ri,\n slotName,\n targetPattern: intercept.targetPattern,\n targetPatternParts: intercept.targetPattern.split(\"/\").filter(Boolean),\n page: intercept.page,\n params: intercept.params,\n });\n }\n }\n}\n\n/**\n * Check if a pathname matches any intercepting route.\n * Returns the match info or null.\n */\nfunction findIntercept(pathname) {\n const urlParts = pathname.split(\"/\").filter(Boolean);\n for (const entry of interceptLookup) {\n const params = matchPattern(urlParts, entry.targetPatternParts);\n if (params !== null) {\n return { ...entry, matchedParams: params };\n }\n }\n return null;\n}\n\nasync function buildPageElement(route, params, opts, searchParams) {\n const PageComponent = route.page?.default;\n if (!PageComponent) {\n return createElement(\"div\", null, \"Page has no default export\");\n }\n\n // Resolve metadata and viewport from layouts and page.\n //\n // generateMetadata() accepts a \"parent\" (Promise of ResolvedMetadata) as its\n // second argument (Next.js 13+). The parent resolves to the accumulated\n // merged metadata of all ancestor segments, enabling patterns like:\n //\n // const previousImages = (await parent).openGraph?.images ?? []\n // return { openGraph: { images: ['/new-image.jpg', ...previousImages] } }\n //\n // Next.js uses an eager-execution-with-serial-resolution approach:\n // all generateMetadata() calls are kicked off concurrently, but each\n // segment's \"parent\" promise resolves only after the preceding segment's\n // metadata is resolved and merged. This preserves concurrency for I/O-bound\n // work while guaranteeing that parent data is available when needed.\n //\n // We build a chain: layoutParentPromises[0] = Promise.resolve({}) (no parent\n // for root layout), layoutParentPromises[i+1] resolves to merge(layouts[0..i]),\n // and pageParentPromise resolves to merge(all layouts).\n //\n // IMPORTANT: Layout metadata errors are swallowed (.catch(() => null)) because\n // a layout's generateMetadata() failing should not crash the page.\n // Page metadata errors are NOT swallowed — if the page's generateMetadata()\n // throws, the error propagates out of buildPageElement() so the caller can\n // route it to the nearest error.tsx boundary (or global-error.tsx).\n const layoutMods = route.layouts.filter(Boolean);\n\n // Build the parent promise chain and kick off metadata resolution in one pass.\n // Each layout module is called exactly once. layoutMetaPromises[i] is the\n // promise for layout[i]'s own metadata result.\n //\n // All calls are kicked off immediately (concurrent I/O), but each layout's\n // \"parent\" promise only resolves after the preceding layout's metadata is done.\n const layoutMetaPromises = [];\n let accumulatedMetaPromise = Promise.resolve({});\n for (let i = 0; i < layoutMods.length; i++) {\n const parentForThisLayout = accumulatedMetaPromise;\n // Kick off this layout's metadata resolution now (concurrent with others).\n const metaPromise = resolveModuleMetadata(layoutMods[i], params, undefined, parentForThisLayout)\n .catch((err) => { console.error(\"[vinext] Layout generateMetadata() failed:\", err); return null; });\n layoutMetaPromises.push(metaPromise);\n // Advance accumulator: resolves to merged(layouts[0..i]) once layout[i] is done.\n accumulatedMetaPromise = metaPromise.then(async (result) =>\n result ? mergeMetadata([await parentForThisLayout, result]) : await parentForThisLayout\n );\n }\n // Page's parent is the fully-accumulated layout metadata.\n const pageParentPromise = accumulatedMetaPromise;\n\n // Convert URLSearchParams → plain object so we can pass it to\n // resolveModuleMetadata (which expects Record<string, string | string[]>).\n // This same object is reused for pageProps.searchParams below.\n const spObj = {};\n let hasSearchParams = false;\n if (searchParams && searchParams.forEach) {\n searchParams.forEach(function(v, k) {\n hasSearchParams = true;\n if (k in spObj) {\n spObj[k] = Array.isArray(spObj[k]) ? spObj[k].concat(v) : [spObj[k], v];\n } else {\n spObj[k] = v;\n }\n });\n }\n\n const [layoutMetaResults, layoutVpResults, pageMeta, pageVp] = await Promise.all([\n Promise.all(layoutMetaPromises),\n Promise.all(layoutMods.map((mod) => resolveModuleViewport(mod, params).catch((err) => { console.error(\"[vinext] Layout generateViewport() failed:\", err); return null; }))),\n route.page ? resolveModuleMetadata(route.page, params, spObj, pageParentPromise) : Promise.resolve(null),\n route.page ? resolveModuleViewport(route.page, params) : Promise.resolve(null),\n ]);\n\n const metadataList = [...layoutMetaResults.filter(Boolean), ...(pageMeta ? [pageMeta] : [])];\n const viewportList = [...layoutVpResults.filter(Boolean), ...(pageVp ? [pageVp] : [])];\n const resolvedMetadata = metadataList.length > 0 ? mergeMetadata(metadataList) : null;\n const resolvedViewport = mergeViewport(viewportList);\n\n // Build nested layout tree from outermost to innermost.\n // Next.js 16 passes params/searchParams as Promises (async pattern)\n // but pre-16 code accesses them as plain objects (params.id).\n // makeThenableParams() normalises null-prototype + preserves both patterns.\n const asyncParams = makeThenableParams(params);\n const pageProps = { params: asyncParams };\n if (searchParams) {\n // Always provide searchParams prop when the URL object is available, even\n // when the query string is empty -- pages that do \"await searchParams\" need\n // it to be a thenable rather than undefined.\n pageProps.searchParams = makeThenableParams(spObj);\n // If the URL has query parameters, mark the page as dynamic.\n // In Next.js, only accessing the searchParams prop signals dynamic usage,\n // but a Proxy-based approach doesn't work here because React's RSC debug\n // serializer accesses properties on all props (e.g. $$typeof check in\n // isClientReference), triggering the Proxy even when user code doesn't\n // read searchParams. Checking for non-empty query params is a safe\n // approximation: pages with query params in the URL are almost always\n // dynamic, and this avoids false positives from React internals.\n if (hasSearchParams) markDynamicUsage();\n }\n let element = createElement(PageComponent, pageProps);\n\n // Wrap page with empty segment provider so useSelectedLayoutSegments()\n // returns [] when called from inside a page component (leaf node).\n element = createElement(LayoutSegmentProvider, { segmentMap: { children: [] } }, element);\n\n // Add metadata + viewport head tags (React 19 hoists title/meta/link to <head>)\n // Next.js always injects charset and default viewport even when no metadata/viewport\n // is exported. We replicate that by always emitting these essential head elements.\n {\n const headElements = [];\n // Always emit <meta charset=\"utf-8\"> — Next.js includes this on every page\n headElements.push(createElement(\"meta\", { charSet: \"utf-8\" }));\n if (resolvedMetadata) headElements.push(createElement(MetadataHead, { metadata: resolvedMetadata }));\n headElements.push(createElement(ViewportHead, { viewport: resolvedViewport }));\n element = createElement(Fragment, null, ...headElements, element);\n }\n\n // Wrap with loading.tsx Suspense if present\n if (route.loading?.default) {\n element = createElement(\n Suspense,\n { fallback: createElement(route.loading.default) },\n element,\n );\n }\n\n // Wrap with the leaf's error.tsx ErrorBoundary if it's not already covered\n // by a per-layout error boundary (i.e., the leaf has error.tsx but no layout).\n // Per-layout error boundaries are interleaved with layouts below.\n {\n const lastLayoutError = route.errors ? route.errors[route.errors.length - 1] : null;\n if (route.error?.default && route.error !== lastLayoutError) {\n element = createElement(ErrorBoundary, {\n fallback: route.error.default,\n children: element,\n });\n }\n }\n\n // Wrap with NotFoundBoundary so client-side notFound() renders not-found.tsx\n // instead of crashing the React tree. Must be above ErrorBoundary since\n // ErrorBoundary re-throws notFound errors.\n // Pre-render the not-found component as a React element since it may be a\n // server component (not a client reference) and can't be passed as a function prop.\n {\n const NotFoundComponent = route.notFound?.default ?? ${rootNotFoundVar ? `${rootNotFoundVar}?.default` : \"null\"};\n if (NotFoundComponent) {\n element = createElement(NotFoundBoundary, {\n fallback: createElement(NotFoundComponent),\n children: element,\n });\n }\n }\n\n // Wrap with templates (innermost first, then outer)\n // Templates are like layouts but re-mount on navigation (client-side concern).\n // On the server, they just wrap the content like layouts do.\n if (route.templates) {\n for (let i = route.templates.length - 1; i >= 0; i--) {\n const TemplateComponent = route.templates[i]?.default;\n if (TemplateComponent) {\n element = createElement(TemplateComponent, { children: element, params });\n }\n }\n }\n\n // Wrap with layouts (innermost first, then outer).\n // At each layout level, first wrap with that level's error boundary (if any)\n // so the boundary is inside the layout and catches errors from children.\n // This matches Next.js behavior: Layout > ErrorBoundary > children.\n // Parallel slots are passed as named props to the innermost layout\n // (the layout at the same directory level as the page/slots)\n for (let i = route.layouts.length - 1; i >= 0; i--) {\n // Wrap with per-layout error boundary before wrapping with layout.\n // This places the ErrorBoundary inside the layout, catching errors\n // from child segments (matching Next.js per-segment error handling).\n if (route.errors && route.errors[i]?.default) {\n element = createElement(ErrorBoundary, {\n fallback: route.errors[i].default,\n children: element,\n });\n }\n\n const LayoutComponent = route.layouts[i]?.default;\n if (LayoutComponent) {\n // Per-layout NotFoundBoundary: wraps this layout's children so that\n // notFound() thrown from a child layout is caught here.\n // Matches Next.js behavior where each segment has its own boundary.\n // The boundary at level N catches errors from Layout[N+1] and below,\n // but NOT from Layout[N] itself (which propagates to level N-1).\n {\n const LayoutNotFound = route.notFounds?.[i]?.default;\n if (LayoutNotFound) {\n element = createElement(NotFoundBoundary, {\n fallback: createElement(LayoutNotFound),\n children: element,\n });\n }\n }\n\n const layoutProps = { children: element, params: makeThenableParams(params) };\n\n // Add parallel slot elements to the layout that defines them.\n // Each slot has a layoutIndex indicating which layout it belongs to.\n if (route.slots) {\n for (const [slotName, slotMod] of Object.entries(route.slots)) {\n // Attach slot to the layout at its layoutIndex, or to the innermost layout if -1\n const targetIdx = slotMod.layoutIndex >= 0 ? slotMod.layoutIndex : route.layouts.length - 1;\n if (i !== targetIdx) continue;\n // Check if this slot has an intercepting route that should activate\n let SlotPage = null;\n let slotParams = params;\n\n if (opts && opts.interceptSlot === slotName && opts.interceptPage) {\n // Use the intercepting route's page component\n SlotPage = opts.interceptPage.default;\n slotParams = opts.interceptParams || params;\n } else {\n SlotPage = slotMod.page?.default || slotMod.default?.default;\n }\n\n if (SlotPage) {\n let slotElement = createElement(SlotPage, { params: makeThenableParams(slotParams) });\n // Wrap with slot-specific layout if present.\n // In Next.js, @slot/layout.tsx wraps the slot's page content\n // before it is passed as a prop to the parent layout.\n const SlotLayout = slotMod.layout?.default;\n if (SlotLayout) {\n slotElement = createElement(SlotLayout, {\n children: slotElement,\n params: makeThenableParams(slotParams),\n });\n }\n // Wrap with slot-specific loading if present\n if (slotMod.loading?.default) {\n slotElement = createElement(Suspense,\n { fallback: createElement(slotMod.loading.default) },\n slotElement,\n );\n }\n // Wrap with slot-specific error boundary if present\n if (slotMod.error?.default) {\n slotElement = createElement(ErrorBoundary, {\n fallback: slotMod.error.default,\n children: slotElement,\n });\n }\n layoutProps[slotName] = slotElement;\n }\n }\n }\n\n element = createElement(LayoutComponent, layoutProps);\n\n // Wrap the layout with LayoutSegmentProvider so useSelectedLayoutSegments()\n // called INSIDE this layout gets the correct child segments. We resolve the\n // route tree segments using actual param values and pass them through context.\n // We wrap the layout (not just children) because hooks are called from\n // components rendered inside the layout's own JSX.\n const treePos = route.layoutTreePositions ? route.layoutTreePositions[i] : 0;\n const childSegs = __resolveChildSegments(route.routeSegments || [], treePos, params);\n element = createElement(LayoutSegmentProvider, { segmentMap: { children: childSegs } }, element);\n }\n }\n\n // Wrap with global error boundary if app/global-error.tsx exists.\n // This must be present in both HTML and RSC paths so the component tree\n // structure matches — otherwise React reconciliation on client-side navigation\n // would see a mismatched tree and destroy/recreate the DOM.\n //\n // For RSC requests (client-side nav), this provides error recovery on the client.\n // For HTML requests (initial page load), the ErrorBoundary catches during SSR\n // but produces double <html>/<body> (root layout + global-error). The request\n // handler detects this via the rscOnError flag and re-renders without layouts.\n ${\n globalErrorVar\n ? `\n const GlobalErrorComponent = ${globalErrorVar}.default;\n if (GlobalErrorComponent) {\n element = createElement(ErrorBoundary, {\n fallback: GlobalErrorComponent,\n children: element,\n });\n }\n `\n : \"\"\n }\n\n return element;\n}\n\n${middlewarePath ? generateMiddlewareMatcherCode(\"modern\") : \"\"}\n\nconst __basePath = ${JSON.stringify(bp)};\nconst __trailingSlash = ${JSON.stringify(ts)};\nconst __i18nConfig = ${JSON.stringify(i18nConfig)};\nconst __configRedirects = ${JSON.stringify(redirects)};\nconst __configRewrites = ${JSON.stringify(rewrites)};\nconst __configHeaders = ${JSON.stringify(headers)};\nconst __allowedOrigins = ${JSON.stringify(allowedOrigins)};\n\n${generateDevOriginCheckCode(config?.allowedDevOrigins)}\n\n// ── ReDoS-safe regex compilation (still needed for middleware matching) ──\n${generateSafeRegExpCode(\"modern\")}\n\n// ── Path normalization ──────────────────────────────────────────────────\n${generateNormalizePathCode(\"modern\")}\n${generateRouteMatchNormalizationCode(\"modern\")}\n\n// ── Config pattern matching, redirects, rewrites, headers, CSRF validation,\n// external URL proxy, cookie parsing, and request context are imported from\n// config-matchers.ts and request-pipeline.ts (see import statements above).\n// This eliminates ~250 lines of duplicated inline code and ensures the\n// single-pass tokenizer in config-matchers.ts is used consistently\n// (fixing the chained .replace() divergence flagged by CodeQL).\n\n/**\n * Build a request context from the live ALS HeadersContext, which reflects\n * any x-middleware-request-* header mutations applied by middleware.\n * Used for afterFiles and fallback rewrite has/missing evaluation — these\n * run after middleware in the App Router execution order.\n */\nfunction __buildPostMwRequestContext(request) {\n const url = new URL(request.url);\n const ctx = getHeadersContext();\n if (!ctx) return requestContextFromRequest(request);\n // ctx.cookies is a Map<string, string> (HeadersContext), but RequestContext\n // requires a plain Record<string, string> for has/missing cookie evaluation\n // (config-matchers.ts uses obj[key] not Map.get()). Convert here.\n const cookiesRecord = Object.fromEntries(ctx.cookies);\n return {\n headers: ctx.headers,\n cookies: cookiesRecord,\n query: url.searchParams,\n host: normalizeHost(ctx.headers.get(\"host\"), url.hostname),\n };\n}\n\n/**\n * Maximum server-action request body size.\n * Configurable via experimental.serverActions.bodySizeLimit in next.config.\n * Defaults to 1MB, matching the Next.js default.\n * @see https://nextjs.org/docs/app/api-reference/config/next-config-js/serverActions#bodysizelimit\n * Prevents unbounded request body buffering.\n */\nvar __MAX_ACTION_BODY_SIZE = ${JSON.stringify(bodySizeLimit)};\n\n/**\n * Read a request body as text with a size limit.\n * Enforces the limit on the actual byte stream to prevent bypasses\n * via chunked transfer-encoding where Content-Length is absent or spoofed.\n */\nasync function __readBodyWithLimit(request, maxBytes) {\n if (!request.body) return \"\";\n var reader = request.body.getReader();\n var decoder = new TextDecoder();\n var chunks = [];\n var totalSize = 0;\n for (;;) {\n var result = await reader.read();\n if (result.done) break;\n totalSize += result.value.byteLength;\n if (totalSize > maxBytes) {\n reader.cancel();\n throw new Error(\"Request body too large\");\n }\n chunks.push(decoder.decode(result.value, { stream: true }));\n }\n chunks.push(decoder.decode());\n return chunks.join(\"\");\n}\n\n/**\n * Read a request body as FormData with a size limit.\n * Consumes the body stream with a byte counter and then parses the\n * collected bytes as multipart form data via the Response constructor.\n */\nasync function __readFormDataWithLimit(request, maxBytes) {\n if (!request.body) return new FormData();\n var reader = request.body.getReader();\n var chunks = [];\n var totalSize = 0;\n for (;;) {\n var result = await reader.read();\n if (result.done) break;\n totalSize += result.value.byteLength;\n if (totalSize > maxBytes) {\n reader.cancel();\n throw new Error(\"Request body too large\");\n }\n chunks.push(result.value);\n }\n // Reconstruct a Response with the original Content-Type so that\n // the FormData parser can handle multipart boundaries correctly.\n var combined = new Uint8Array(totalSize);\n var offset = 0;\n for (var chunk of chunks) {\n combined.set(chunk, offset);\n offset += chunk.byteLength;\n }\n var contentType = request.headers.get(\"content-type\") || \"\";\n return new Response(combined, { headers: { \"Content-Type\": contentType } }).formData();\n}\n\n// Map from route pattern to generateStaticParams function.\n// Used by the prerender phase to enumerate dynamic route URLs without\n// loading route modules via the dev server.\nexport const generateStaticParamsMap = {\n// TODO: layout-level generateStaticParams — this map only includes routes that\n// have a pagePath (leaf pages). Layout segments can also export generateStaticParams\n// to provide parent params for nested dynamic routes, but they don't have a pagePath\n// so they are excluded here. Supporting layout-level generateStaticParams requires\n// scanning layout.tsx files separately and including them in this map.\n${routes\n .filter((r) => r.isDynamic && r.pagePath)\n .map(\n (r) =>\n ` ${JSON.stringify(r.pattern)}: ${getImportVar(r.pagePath!)}?.generateStaticParams ?? null,`,\n )\n .join(\"\\n\")}\n};\n\nexport default async function handler(request, ctx) {\n ${\n instrumentationPath\n ? `// Ensure instrumentation.register() has run before handling the first request.\n // This is a no-op after the first call (guarded by __instrumentationInitialized).\n await __ensureInstrumentation();\n `\n : \"\"\n }\n // Wrap the entire request in a single unified ALS scope for per-request\n // isolation. All state modules (headers, navigation, cache, fetch-cache,\n // execution-context) read from this store via isInsideUnifiedScope().\n const headersCtx = headersContextFromRequest(request);\n const __uCtx = _createUnifiedCtx({\n headersContext: headersCtx,\n executionContext: ctx ?? _getRequestExecutionContext() ?? null,\n });\n return _runWithUnifiedCtx(__uCtx, async () => {\n _ensureFetchPatch();\n const __reqCtx = requestContextFromRequest(request);\n // Per-request container for middleware state. Passed into\n // _handleRequest which fills in .headers and .status;\n // avoids module-level variables that race on Workers.\n const _mwCtx = { headers: null, status: null };\n const response = await _handleRequest(request, __reqCtx, _mwCtx);\n // Apply custom headers from next.config.js to non-redirect responses.\n // Skip redirects (3xx) because Response.redirect() creates immutable headers,\n // and Next.js doesn't apply custom headers to redirects anyway.\n if (response && response.headers && !(response.status >= 300 && response.status < 400)) {\n if (__configHeaders.length) {\n const url = new URL(request.url);\n let pathname;\n try { pathname = __normalizePath(__normalizePathnameForRouteMatch(url.pathname)); } catch { pathname = url.pathname; }\n ${bp ? `if (pathname.startsWith(${JSON.stringify(bp)})) pathname = pathname.slice(${JSON.stringify(bp)}.length) || \"/\";` : \"\"}\n const extraHeaders = matchHeaders(pathname, __configHeaders, __reqCtx);\n for (const h of extraHeaders) {\n // Use append() for headers where multiple values must coexist\n // (Vary, Set-Cookie). Using set() on these would destroy\n // existing values like \"Vary: RSC, Accept\" which are critical\n // for correct CDN caching behavior.\n const lk = h.key.toLowerCase();\n if (lk === \"vary\" || lk === \"set-cookie\") {\n response.headers.append(h.key, h.value);\n } else if (!response.headers.has(lk)) {\n // Middleware headers take precedence: skip config keys already\n // set by middleware so middleware headers always win.\n response.headers.set(h.key, h.value);\n }\n }\n }\n }\n return response;\n });\n}\n\nasync function _handleRequest(request, __reqCtx, _mwCtx) {\n const __reqStart = process.env.NODE_ENV !== \"production\" ? performance.now() : 0;\n // __reqStart is included in the timing header so the Node logging middleware\n // can compute true compile time as: handlerStart - middlewareStart.\n // Format: \"handlerStart,compileMs,renderMs\" - all as integers (ms). Dev-only.\n const url = new URL(request.url);\n\n // ── Cross-origin request protection (dev only) ─────────────────────\n // Block requests from non-localhost origins to prevent data exfiltration.\n // Skipped in production — Vite replaces NODE_ENV at build time.\n if (process.env.NODE_ENV !== \"production\") {\n const __originBlock = __validateDevRequestOrigin(request);\n if (__originBlock) return __originBlock;\n }\n\n // Guard against protocol-relative URL open redirects (see request-pipeline.ts).\n const __protoGuard = guardProtocolRelativeUrl(url.pathname);\n if (__protoGuard) return __protoGuard;\n\n // Decode percent-encoding segment-wise and normalize pathname to canonical form.\n // This preserves encoded path delimiters like %2F within a single segment.\n // __normalizePath collapses //foo///bar → /foo/bar, resolves . and .. segments.\n let decodedUrlPathname;\n try { decodedUrlPathname = __normalizePathnameForRouteMatchStrict(url.pathname); } catch (e) {\n return new Response(\"Bad Request\", { status: 400 });\n }\n let pathname = __normalizePath(decodedUrlPathname);\n\n ${\n bp\n ? `\n // Strip basePath prefix\n pathname = stripBasePath(pathname, __basePath);\n `\n : \"\"\n }\n\n // ── Prerender: static-params endpoint ────────────────────────────────\n // Internal endpoint used by prerenderApp() during build to fetch\n // generateStaticParams results via wrangler unstable_startWorker.\n // Gated on VINEXT_PRERENDER=1 to prevent exposure in normal deployments.\n // For Node builds, process.env.VINEXT_PRERENDER is set directly by the\n // prerender orchestrator. For CF Workers builds, wrangler unstable_startWorker\n // injects VINEXT_PRERENDER as a binding which Miniflare exposes via process.env\n // in bundled workers. The /__vinext/ prefix ensures no user route ever conflicts.\n if (pathname === \"/__vinext/prerender/static-params\") {\n if (process.env.VINEXT_PRERENDER !== \"1\") {\n return new Response(\"Not Found\", { status: 404 });\n }\n const pattern = url.searchParams.get(\"pattern\");\n if (!pattern) return new Response(\"missing pattern\", { status: 400 });\n const fn = generateStaticParamsMap[pattern];\n if (typeof fn !== \"function\") return new Response(\"null\", { status: 200, headers: { \"content-type\": \"application/json\" } });\n try {\n const parentParams = url.searchParams.get(\"parentParams\");\n const raw = parentParams ? JSON.parse(parentParams) : {};\n // Ensure params is a plain object — reject primitives, arrays, and null\n // so user-authored generateStaticParams always receives { params: {} }\n // rather than { params: 5 } or similar if input is malformed.\n const params = (typeof raw === \"object\" && raw !== null && !Array.isArray(raw)) ? raw : {};\n const result = await fn({ params });\n return new Response(JSON.stringify(result), { status: 200, headers: { \"content-type\": \"application/json\" } });\n } catch (e) {\n return new Response(JSON.stringify({ error: String(e) }), { status: 500, headers: { \"content-type\": \"application/json\" } });\n }\n }\n\n ${\n hasPagesDir\n ? `\n // ── Prerender: pages-static-paths endpoint ───────────────────────────\n // Internal endpoint used by prerenderPages() during a CF Workers hybrid\n // build to call getStaticPaths() for dynamic Pages Router routes via\n // wrangler unstable_startWorker. Returns JSON-serialised getStaticPaths result.\n // Gated on VINEXT_PRERENDER=1 to prevent exposure in normal deployments.\n // See static-params endpoint above for process.env vs CF vars notes.\n //\n // pageRoutes lives in the SSR environment (virtual:vinext-server-entry).\n // We load it lazily via import.meta.viteRsc.loadModule — the same pattern\n // used by handleSsr() elsewhere in this template. At build time, Vite's RSC\n // plugin transforms this call into a bundled cross-environment import, so it\n // works correctly in the CF Workers production bundle running in Miniflare.\n if (pathname === \"/__vinext/prerender/pages-static-paths\") {\n if (process.env.VINEXT_PRERENDER !== \"1\") {\n return new Response(\"Not Found\", { status: 404 });\n }\n const __gspPattern = url.searchParams.get(\"pattern\");\n if (!__gspPattern) return new Response(\"missing pattern\", { status: 400 });\n try {\n const __gspSsrEntry = await import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n const __pagesRoutes = __gspSsrEntry.pageRoutes;\n const __gspRoute = Array.isArray(__pagesRoutes)\n ? __pagesRoutes.find((r) => r.pattern === __gspPattern)\n : undefined;\n if (!__gspRoute || typeof __gspRoute.module?.getStaticPaths !== \"function\") {\n return new Response(\"null\", { status: 200, headers: { \"content-type\": \"application/json\" } });\n }\n const __localesParam = url.searchParams.get(\"locales\");\n const __locales = __localesParam ? JSON.parse(__localesParam) : [];\n const __defaultLocale = url.searchParams.get(\"defaultLocale\") ?? \"\";\n const __gspResult = await __gspRoute.module.getStaticPaths({ locales: __locales, defaultLocale: __defaultLocale });\n return new Response(JSON.stringify(__gspResult), { status: 200, headers: { \"content-type\": \"application/json\" } });\n } catch (e) {\n return new Response(JSON.stringify({ error: String(e) }), { status: 500, headers: { \"content-type\": \"application/json\" } });\n }\n }\n `\n : \"\"\n }\n\n // Trailing slash normalization (redirect to canonical form)\n const __tsRedirect = normalizeTrailingSlash(pathname, __basePath, __trailingSlash, url.search);\n if (__tsRedirect) return __tsRedirect;\n\n // ── Apply redirects from next.config.js ───────────────────────────────\n if (__configRedirects.length) {\n // Strip .rsc suffix before matching redirect rules - RSC (client-side nav) requests\n // arrive as /some/path.rsc but redirect patterns are defined without it (e.g.\n // /some/path). Without this, soft-nav fetches bypass all config redirects.\n const __redirPathname = pathname.endsWith(\".rsc\") ? pathname.slice(0, -4) : pathname;\n const __redir = matchRedirect(__redirPathname, __configRedirects, __reqCtx);\n if (__redir) {\n const __redirDest = sanitizeDestination(\n __basePath &&\n !isExternalUrl(__redir.destination) &&\n !hasBasePath(__redir.destination, __basePath)\n ? __basePath + __redir.destination\n : __redir.destination\n );\n return new Response(null, {\n status: __redir.permanent ? 308 : 307,\n headers: { Location: __redirDest },\n });\n }\n }\n\n const isRscRequest = pathname.endsWith(\".rsc\") || request.headers.get(\"accept\")?.includes(\"text/x-component\");\n let cleanPathname = pathname.replace(/\\\\.rsc$/, \"\");\n\n // Middleware response headers and custom rewrite status are stored in\n // _mwCtx (per-request container) so handler() can merge them into\n // every response path without module-level state that races on Workers.\n\n ${\n middlewarePath\n ? `\n // In hybrid app+pages dev mode the connect handler already ran middleware\n // and forwarded the results via x-vinext-mw-ctx. Reconstruct _mwCtx from\n // the forwarded data instead of re-running the middleware function.\n // Guarded by NODE_ENV because this header only exists in dev (the connect\n // handler sets it). In production there is no connect handler, so an\n // attacker-supplied header must not be trusted.\n let __mwCtxApplied = false;\n if (process.env.NODE_ENV !== \"production\") {\n const __mwCtxHeader = request.headers.get(\"x-vinext-mw-ctx\");\n if (__mwCtxHeader) {\n try {\n const __mwCtxData = JSON.parse(__mwCtxHeader);\n if (__mwCtxData.h && __mwCtxData.h.length > 0) {\n // Note: h may include x-middleware-request-* internal headers so\n // applyMiddlewareRequestHeaders() can unpack them below.\n // processMiddlewareHeaders() strips them before any response.\n _mwCtx.headers = new Headers();\n for (const [key, value] of __mwCtxData.h) {\n _mwCtx.headers.append(key, value);\n }\n }\n if (__mwCtxData.s != null) {\n _mwCtx.status = __mwCtxData.s;\n }\n // Apply forwarded middleware rewrite so routing uses the rewritten path.\n // The RSC plugin constructs its Request from the original HTTP request,\n // not from req.url, so the connect handler's req.url rewrite is invisible.\n if (__mwCtxData.r) {\n const __rewriteParsed = new URL(__mwCtxData.r, request.url);\n cleanPathname = __rewriteParsed.pathname;\n url.search = __rewriteParsed.search;\n }\n // Flag set after full context application — if any step fails (e.g. malformed\n // rewrite URL), we fall back to re-running middleware as a safety net.\n __mwCtxApplied = true;\n } catch (e) {\n console.error(\"[vinext] Failed to parse forwarded middleware context:\", e);\n }\n }\n }\n if (!__mwCtxApplied) {\n // Run proxy/middleware if present and path matches.\n // Validate exports match the file type (proxy.ts vs middleware.ts), matching Next.js behavior.\n // https://github.com/vercel/next.js/blob/canary/test/e2e/app-dir/proxy-missing-export/proxy-missing-export.test.ts\n const _isProxy = ${JSON.stringify(isProxyFile(middlewarePath))};\n const middlewareFn = _isProxy\n ? (middlewareModule.proxy ?? middlewareModule.default)\n : (middlewareModule.middleware ?? middlewareModule.default);\n if (typeof middlewareFn !== \"function\") {\n const _fileType = _isProxy ? \"Proxy\" : \"Middleware\";\n const _expectedExport = _isProxy ? \"proxy\" : \"middleware\";\n throw new Error(\"The \" + _fileType + \" file must export a function named \\`\" + _expectedExport + \"\\` or a \\`default\\` function.\");\n }\n const middlewareMatcher = middlewareModule.config?.matcher;\n if (matchesMiddleware(cleanPathname, middlewareMatcher, request, __i18nConfig)) {\n try {\n // Wrap in NextRequest so middleware gets .nextUrl, .cookies, .geo, .ip, etc.\n // Always construct a new Request with the fully decoded + normalized pathname\n // so middleware and the router see the same canonical path.\n const mwUrl = new URL(request.url);\n mwUrl.pathname = cleanPathname;\n const mwRequest = new Request(mwUrl, request);\n const __mwNextConfig = (__basePath || __i18nConfig) ? { basePath: __basePath, i18n: __i18nConfig ?? undefined } : undefined;\n const nextRequest = mwRequest instanceof NextRequest ? mwRequest : new NextRequest(mwRequest, __mwNextConfig ? { nextConfig: __mwNextConfig } : undefined);\n const mwFetchEvent = new NextFetchEvent({ page: cleanPathname });\n let mwResponse;\n try {\n mwResponse = await middlewareFn(nextRequest, mwFetchEvent);\n } finally {\n const _mwWaitUntil = mwFetchEvent.drainWaitUntil();\n const _mwExecCtx = _getRequestExecutionContext();\n if (_mwExecCtx && typeof _mwExecCtx.waitUntil === \"function\") { _mwExecCtx.waitUntil(_mwWaitUntil); }\n }\n if (mwResponse) {\n // Check for x-middleware-next (continue)\n if (mwResponse.headers.get(\"x-middleware-next\") === \"1\") {\n // Middleware wants to continue — collect all headers except the two\n // control headers we've already consumed. x-middleware-request-*\n // headers are kept so applyMiddlewareRequestHeaders() can unpack them;\n // the blanket strip loop after that call removes every remaining\n // x-middleware-* header before the set is merged into the response.\n _mwCtx.headers = new Headers();\n for (const [key, value] of mwResponse.headers) {\n if (key !== \"x-middleware-next\" && key !== \"x-middleware-rewrite\") {\n _mwCtx.headers.append(key, value);\n }\n }\n } else {\n // Check for redirect\n if (mwResponse.status >= 300 && mwResponse.status < 400) {\n return mwResponse;\n }\n // Check for rewrite\n const rewriteUrl = mwResponse.headers.get(\"x-middleware-rewrite\");\n if (rewriteUrl) {\n const rewriteParsed = new URL(rewriteUrl, request.url);\n cleanPathname = rewriteParsed.pathname;\n // Carry over query params from the rewrite URL so that\n // searchParams props, useSearchParams(), and navigation context\n // reflect the rewrite destination, not the original request.\n url.search = rewriteParsed.search;\n // Capture custom status code from rewrite (e.g. NextResponse.rewrite(url, { status: 403 }))\n if (mwResponse.status !== 200) {\n _mwCtx.status = mwResponse.status;\n }\n // Also save any other headers from the rewrite response\n _mwCtx.headers = new Headers();\n for (const [key, value] of mwResponse.headers) {\n if (key !== \"x-middleware-next\" && key !== \"x-middleware-rewrite\") {\n _mwCtx.headers.append(key, value);\n }\n }\n } else {\n // Middleware returned a custom response\n return mwResponse;\n }\n }\n }\n } catch (err) {\n console.error(\"[vinext] Middleware error:\", err);\n return new Response(\"Internal Server Error\", { status: 500 });\n }\n }\n } // end of if (!__mwCtxApplied)\n\n // Unpack x-middleware-request-* headers into the request context so that\n // headers() returns the middleware-modified headers instead of the original\n // request headers. Strip ALL x-middleware-* headers from the set that will\n // be merged into the outgoing HTTP response — this prefix is reserved for\n // internal routing signals and must never reach clients.\n if (_mwCtx.headers) {\n applyMiddlewareRequestHeaders(_mwCtx.headers);\n processMiddlewareHeaders(_mwCtx.headers);\n }\n `\n : \"\"\n }\n\n // Build post-middleware request context for afterFiles/fallback rewrites.\n // These run after middleware in the App Router execution order and should\n // evaluate has/missing conditions against middleware-modified headers.\n // When no middleware is present, this falls back to requestContextFromRequest.\n const __postMwReqCtx = __buildPostMwRequestContext(request);\n\n // ── Apply beforeFiles rewrites from next.config.js ────────────────────\n // In App Router execution order, beforeFiles runs after middleware so that\n // has/missing conditions can evaluate against middleware-modified headers.\n if (__configRewrites.beforeFiles && __configRewrites.beforeFiles.length) {\n const __rewritten = matchRewrite(cleanPathname, __configRewrites.beforeFiles, __postMwReqCtx);\n if (__rewritten) {\n if (isExternalUrl(__rewritten)) {\n setHeadersContext(null);\n setNavigationContext(null);\n return proxyExternalRequest(request, __rewritten);\n }\n cleanPathname = __rewritten;\n }\n }\n\n // ── Image optimization passthrough (dev mode — no transformation) ───────\n if (cleanPathname === \"/_vinext/image\") {\n const __imgResult = validateImageUrl(url.searchParams.get(\"url\"), request.url);\n if (__imgResult instanceof Response) return __imgResult;\n // In dev, redirect to the original asset URL so Vite's static serving handles it.\n return Response.redirect(new URL(__imgResult, url.origin).href, 302);\n }\n\n // Handle metadata routes (sitemap.xml, robots.txt, manifest.webmanifest, etc.)\n for (const metaRoute of metadataRoutes) {\n // generateSitemaps() support — paginated sitemaps at /{prefix}/sitemap/{id}.xml\n // When a sitemap module exports generateSitemaps, the base URL (e.g. /products/sitemap.xml)\n // is no longer served. Instead, individual sitemaps are served at /products/sitemap/{id}.xml.\n if (\n metaRoute.type === \"sitemap\" &&\n metaRoute.isDynamic &&\n typeof metaRoute.module.generateSitemaps === \"function\"\n ) {\n const sitemapPrefix = metaRoute.servedUrl.slice(0, -4); // strip \".xml\"\n // Match exactly /{prefix}/{id}.xml — one segment only (no slashes in id)\n if (cleanPathname.startsWith(sitemapPrefix + \"/\") && cleanPathname.endsWith(\".xml\")) {\n const rawId = cleanPathname.slice(sitemapPrefix.length + 1, -4);\n if (rawId.includes(\"/\")) continue; // multi-segment — not a paginated sitemap\n const sitemaps = await metaRoute.module.generateSitemaps();\n const matched = sitemaps.find(function(s) { return String(s.id) === rawId; });\n if (!matched) return new Response(\"Not Found\", { status: 404 });\n // Pass the original typed id from generateSitemaps() so numeric IDs stay numeric.\n // TODO: wrap with makeThenableParams-style Promise when upgrading to Next.js 16\n // full-Promise param semantics (id becomes Promise<string> in v16).\n const result = await metaRoute.module.default({ id: matched.id });\n if (result instanceof Response) return result;\n return new Response(sitemapToXml(result), {\n headers: { \"Content-Type\": metaRoute.contentType },\n });\n }\n // Skip — the base servedUrl is not served when generateSitemaps exists\n continue;\n }\n // Match metadata route — use pattern matching for dynamic segments,\n // strict equality for static paths.\n var _metaParams = null;\n if (metaRoute.patternParts) {\n var _metaUrlParts = cleanPathname.split(\"/\").filter(Boolean);\n _metaParams = matchPattern(_metaUrlParts, metaRoute.patternParts);\n if (!_metaParams) continue;\n } else if (cleanPathname !== metaRoute.servedUrl) {\n continue;\n }\n if (metaRoute.isDynamic) {\n // Dynamic metadata route — call the default export and serialize\n const metaFn = metaRoute.module.default;\n if (typeof metaFn === \"function\") {\n const result = await metaFn({ params: makeThenableParams(_metaParams || {}) });\n let body;\n // If it's already a Response (e.g., ImageResponse), return directly\n if (result instanceof Response) return result;\n // Serialize based on type\n if (metaRoute.type === \"sitemap\") body = sitemapToXml(result);\n else if (metaRoute.type === \"robots\") body = robotsToText(result);\n else if (metaRoute.type === \"manifest\") body = manifestToJson(result);\n else body = JSON.stringify(result);\n return new Response(body, {\n headers: { \"Content-Type\": metaRoute.contentType },\n });\n }\n } else {\n // Static metadata file — decode from embedded base64 data\n try {\n const binary = atob(metaRoute.fileDataBase64);\n const bytes = new Uint8Array(binary.length);\n for (let i = 0; i < binary.length; i++) bytes[i] = binary.charCodeAt(i);\n return new Response(bytes, {\n headers: {\n \"Content-Type\": metaRoute.contentType,\n \"Cache-Control\": \"public, max-age=0, must-revalidate\",\n },\n });\n } catch {\n return new Response(\"Not Found\", { status: 404 });\n }\n }\n }\n\n // Set navigation context for Server Components.\n // Note: Headers context is already set by runWithRequestContext in the handler wrapper.\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: url.searchParams,\n params: {},\n });\n\n // Handle server action POST requests\n const actionId = request.headers.get(\"x-rsc-action\");\n if (request.method === \"POST\" && actionId) {\n // ── CSRF protection ─────────────────────────────────────────────────\n // Verify that the Origin header matches the Host header to prevent\n // cross-site request forgery, matching Next.js server action behavior.\n const csrfResponse = validateCsrfOrigin(request, __allowedOrigins);\n if (csrfResponse) return csrfResponse;\n\n // ── Body size limit ─────────────────────────────────────────────────\n // Reject payloads larger than the configured limit.\n // Check Content-Length as a fast path, then enforce on the actual\n // stream to prevent bypasses via chunked transfer-encoding.\n const contentLength = parseInt(request.headers.get(\"content-length\") || \"0\", 10);\n if (contentLength > __MAX_ACTION_BODY_SIZE) {\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Payload Too Large\", { status: 413 });\n }\n\n try {\n const contentType = request.headers.get(\"content-type\") || \"\";\n let body;\n try {\n body = contentType.startsWith(\"multipart/form-data\")\n ? await __readFormDataWithLimit(request, __MAX_ACTION_BODY_SIZE)\n : await __readBodyWithLimit(request, __MAX_ACTION_BODY_SIZE);\n } catch (sizeErr) {\n if (sizeErr && sizeErr.message === \"Request body too large\") {\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Payload Too Large\", { status: 413 });\n }\n throw sizeErr;\n }\n const temporaryReferences = createTemporaryReferenceSet();\n const args = await decodeReply(body, { temporaryReferences });\n const action = await loadServerAction(actionId);\n let returnValue;\n let actionRedirect = null;\n const previousHeadersPhase = setHeadersAccessPhase(\"action\");\n try {\n try {\n const data = await action.apply(null, args);\n returnValue = { ok: true, data };\n } catch (e) {\n // Detect redirect() / permanentRedirect() called inside the action.\n // These throw errors with digest \"NEXT_REDIRECT;replace;url[;status]\".\n // The URL is encodeURIComponent-encoded to prevent semicolons in the URL\n // from corrupting the delimiter-based digest format.\n if (e && typeof e === \"object\" && \"digest\" in e) {\n const digest = String(e.digest);\n if (digest.startsWith(\"NEXT_REDIRECT;\")) {\n const parts = digest.split(\";\");\n actionRedirect = {\n url: decodeURIComponent(parts[2]),\n type: parts[1] || \"replace\", // \"push\" or \"replace\"\n status: parts[3] ? parseInt(parts[3], 10) : 307,\n };\n returnValue = { ok: true, data: undefined };\n } else if (digest === \"NEXT_NOT_FOUND\" || digest.startsWith(\"NEXT_HTTP_ERROR_FALLBACK;\")) {\n // notFound() / forbidden() / unauthorized() in action — package as error\n returnValue = { ok: false, data: e };\n } else {\n // Non-navigation digest error — sanitize in production to avoid\n // leaking internal details (connection strings, paths, etc.)\n console.error(\"[vinext] Server action error:\", e);\n returnValue = { ok: false, data: __sanitizeErrorForClient(e) };\n }\n } else {\n // Unhandled error — sanitize in production to avoid leaking\n // internal details (database errors, file paths, stack traces, etc.)\n console.error(\"[vinext] Server action error:\", e);\n returnValue = { ok: false, data: __sanitizeErrorForClient(e) };\n }\n }\n } finally {\n setHeadersAccessPhase(previousHeadersPhase);\n }\n\n // If the action called redirect(), signal the client to navigate.\n // We can't use a real HTTP redirect (the fetch would follow it automatically\n // and receive a page HTML instead of RSC stream). Instead, we return a 200\n // with x-action-redirect header that the client entry detects and handles.\n if (actionRedirect) {\n const actionPendingCookies = getAndClearPendingCookies();\n const actionDraftCookie = getDraftModeCookieHeader();\n setHeadersContext(null);\n setNavigationContext(null);\n const redirectHeaders = new Headers({\n \"Content-Type\": \"text/x-component; charset=utf-8\",\n \"Vary\": \"RSC, Accept\",\n \"x-action-redirect\": actionRedirect.url,\n \"x-action-redirect-type\": actionRedirect.type,\n \"x-action-redirect-status\": String(actionRedirect.status),\n });\n for (const cookie of actionPendingCookies) {\n redirectHeaders.append(\"Set-Cookie\", cookie);\n }\n if (actionDraftCookie) redirectHeaders.append(\"Set-Cookie\", actionDraftCookie);\n // Send an empty RSC-like body (client will navigate instead of parsing)\n return new Response(\"\", { status: 200, headers: redirectHeaders });\n }\n\n // After the action, re-render the current page so the client\n // gets an updated React tree reflecting any mutations.\n const match = matchRoute(cleanPathname);\n let element;\n if (match) {\n const { route: actionRoute, params: actionParams } = match;\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: url.searchParams,\n params: actionParams,\n });\n element = buildPageElement(actionRoute, actionParams, undefined, url.searchParams);\n } else {\n element = createElement(\"div\", null, \"Page not found\");\n }\n\n const onRenderError = createRscOnErrorHandler(\n request,\n cleanPathname,\n match ? match.route.pattern : cleanPathname,\n );\n const rscStream = renderToReadableStream(\n { root: element, returnValue },\n { temporaryReferences, onError: onRenderError },\n );\n\n // Collect cookies set during the action synchronously (before stream is consumed).\n // Do NOT clear headers/navigation context here — the RSC stream is consumed lazily\n // by the client, and async server components that run during consumption need the\n // context to still be live. The AsyncLocalStorage scope from runWithRequestContext\n // handles cleanup naturally when all async continuations complete.\n const actionPendingCookies = getAndClearPendingCookies();\n const actionDraftCookie = getDraftModeCookieHeader();\n\n const actionHeaders = { \"Content-Type\": \"text/x-component; charset=utf-8\", \"Vary\": \"RSC, Accept\" };\n const actionResponse = new Response(rscStream, { headers: actionHeaders });\n if (actionPendingCookies.length > 0 || actionDraftCookie) {\n for (const cookie of actionPendingCookies) {\n actionResponse.headers.append(\"Set-Cookie\", cookie);\n }\n if (actionDraftCookie) actionResponse.headers.append(\"Set-Cookie\", actionDraftCookie);\n }\n return actionResponse;\n } catch (err) {\n getAndClearPendingCookies(); // Clear pending cookies on error\n console.error(\"[vinext] Server action error:\", err);\n _reportRequestError(\n err instanceof Error ? err : new Error(String(err)),\n { path: cleanPathname, method: request.method, headers: Object.fromEntries(request.headers.entries()) },\n { routerKind: \"App Router\", routePath: cleanPathname, routeType: \"action\" },\n );\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\n process.env.NODE_ENV === \"production\"\n ? \"Internal Server Error\"\n : \"Server action failed: \" + (err && err.message ? err.message : String(err)),\n { status: 500 },\n );\n }\n }\n\n // ── Apply afterFiles rewrites from next.config.js ──────────────────────\n if (__configRewrites.afterFiles && __configRewrites.afterFiles.length) {\n const __afterRewritten = matchRewrite(cleanPathname, __configRewrites.afterFiles, __postMwReqCtx);\n if (__afterRewritten) {\n if (isExternalUrl(__afterRewritten)) {\n setHeadersContext(null);\n setNavigationContext(null);\n return proxyExternalRequest(request, __afterRewritten);\n }\n cleanPathname = __afterRewritten;\n }\n }\n\n let match = matchRoute(cleanPathname);\n\n // ── Fallback rewrites from next.config.js (if no route matched) ───────\n if (!match && __configRewrites.fallback && __configRewrites.fallback.length) {\n const __fallbackRewritten = matchRewrite(cleanPathname, __configRewrites.fallback, __postMwReqCtx);\n if (__fallbackRewritten) {\n if (isExternalUrl(__fallbackRewritten)) {\n setHeadersContext(null);\n setNavigationContext(null);\n return proxyExternalRequest(request, __fallbackRewritten);\n }\n cleanPathname = __fallbackRewritten;\n match = matchRoute(cleanPathname);\n }\n }\n\n if (!match) {\n ${\n hasPagesDir\n ? `\n // ── Pages Router fallback ────────────────────────────────────────────\n // When a request doesn't match any App Router route, delegate to the\n // Pages Router handler (available in the SSR environment). This covers\n // both production request serving and prerender fetches from wrangler.\n // RSC requests (.rsc suffix or Accept: text/x-component) cannot be\n // handled by the Pages Router, so skip the delegation for those.\n if (!isRscRequest) {\n const __pagesEntry = await import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n if (typeof __pagesEntry.renderPage === \"function\") {\n // Use segment-wise decoding to preserve encoded path delimiters (%2F).\n // decodeURIComponent would turn /admin%2Fpanel into /admin/panel,\n // changing the path structure and bypassing middleware matchers.\n // Ported from Next.js: packages/next/src/server/lib/router-utils/decode-path-params.ts\n // https://github.com/vercel/next.js/blob/canary/packages/next/src/server/lib/router-utils/decode-path-params.ts\n const __pagesRes = await __pagesEntry.renderPage(request, __decodePathParams(url.pathname) + (url.search || \"\"), {});\n // Only return the Pages Router response if it matched a route\n // (non-404). A 404 means the path isn't a Pages route either,\n // so fall through to the App Router not-found page below.\n if (__pagesRes.status !== 404) {\n setHeadersContext(null);\n setNavigationContext(null);\n return __pagesRes;\n }\n }\n }\n `\n : \"\"\n }\n // Render custom not-found page if available, otherwise plain 404\n const notFoundResponse = await renderNotFoundPage(null, isRscRequest, request);\n if (notFoundResponse) return notFoundResponse;\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Not Found\", { status: 404 });\n }\n\n const { route, params } = match;\n\n // Update navigation context with matched params\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: url.searchParams,\n params,\n });\n\n // Handle route.ts API handlers\n if (route.routeHandler) {\n const handler = route.routeHandler;\n const method = request.method.toUpperCase();\n const revalidateSeconds = __getAppRouteHandlerRevalidateSeconds(handler);\n if (__hasAppRouteHandlerDefaultExport(handler) && process.env.NODE_ENV === \"development\") {\n console.error(\n \"[vinext] Detected default export in route handler \" + route.pattern + \". Export a named export for each HTTP method instead.\",\n );\n }\n\n const {\n allowHeaderForOptions,\n handlerFn,\n isAutoHead,\n shouldAutoRespondToOptions,\n } = __resolveAppRouteHandlerMethod(handler, method);\n\n if (shouldAutoRespondToOptions) {\n setHeadersContext(null);\n setNavigationContext(null);\n return __applyRouteHandlerMiddlewareContext(\n new Response(null, {\n status: 204,\n headers: { \"Allow\": allowHeaderForOptions },\n }),\n _mwCtx,\n );\n }\n\n // ISR cache read for route handlers (production only).\n // Only GET/HEAD (auto-HEAD) with finite revalidate > 0 are ISR-eligible.\n // Known-dynamic handlers skip the read entirely so stale cache entries\n // from earlier requests do not replay once the process has learned they\n // access request-specific data.\n if (\n __shouldReadAppRouteHandlerCache({\n dynamicConfig: handler.dynamic,\n handlerFn,\n isAutoHead,\n isKnownDynamic: __isKnownDynamicAppRoute(route.pattern),\n isProduction: process.env.NODE_ENV === \"production\",\n method,\n revalidateSeconds,\n })\n ) {\n const __cachedRouteResponse = await __readAppRouteHandlerCacheResponse({\n basePath: __basePath,\n buildPageCacheTags: __pageCacheTags,\n cleanPathname,\n clearRequestContext: function() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n consumeDynamicUsage,\n getCollectedFetchTags,\n handlerFn,\n i18n: __i18nConfig,\n isAutoHead,\n isrDebug: __isrDebug,\n isrGet: __isrGet,\n isrRouteKey: __isrRouteKey,\n isrSet: __isrSet,\n markDynamicUsage,\n middlewareContext: _mwCtx,\n params,\n requestUrl: request.url,\n revalidateSearchParams: url.searchParams,\n revalidateSeconds,\n routePattern: route.pattern,\n runInRevalidationContext: async function(renderFn) {\n const __revalHeadCtx = { headers: new Headers(), cookies: new Map() };\n const __revalUCtx = _createUnifiedCtx({\n headersContext: __revalHeadCtx,\n executionContext: _getRequestExecutionContext(),\n });\n await _runWithUnifiedCtx(__revalUCtx, async () => {\n _ensureFetchPatch();\n await renderFn();\n });\n },\n scheduleBackgroundRegeneration: __triggerBackgroundRegeneration,\n setNavigationContext,\n });\n if (__cachedRouteResponse) {\n return __cachedRouteResponse;\n }\n }\n\n if (typeof handlerFn === \"function\") {\n return __executeAppRouteHandler({\n basePath: __basePath,\n buildPageCacheTags: __pageCacheTags,\n cleanPathname,\n clearRequestContext: function() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n consumeDynamicUsage,\n executionContext: _getRequestExecutionContext(),\n getAndClearPendingCookies,\n getCollectedFetchTags,\n getDraftModeCookieHeader,\n handler,\n handlerFn,\n i18n: __i18nConfig,\n isAutoHead,\n isProduction: process.env.NODE_ENV === \"production\",\n isrDebug: __isrDebug,\n isrRouteKey: __isrRouteKey,\n isrSet: __isrSet,\n markDynamicUsage,\n method,\n middlewareContext: _mwCtx,\n params: makeThenableParams(params),\n reportRequestError: _reportRequestError,\n request,\n revalidateSeconds,\n routePattern: route.pattern,\n setHeadersAccessPhase,\n });\n }\n setHeadersContext(null);\n setNavigationContext(null);\n return __applyRouteHandlerMiddlewareContext(\n new Response(null, {\n status: 405,\n }),\n _mwCtx,\n );\n }\n\n // Build the component tree: layouts wrapping the page\n const PageComponent = route.page?.default;\n if (!PageComponent) {\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Page has no default export\", { status: 500 });\n }\n\n // Read route segment config from page module exports\n let revalidateSeconds = typeof route.page?.revalidate === \"number\" ? route.page.revalidate : null;\n const dynamicConfig = route.page?.dynamic; // 'auto' | 'force-dynamic' | 'force-static' | 'error'\n const dynamicParamsConfig = route.page?.dynamicParams; // true (default) | false\n const isForceStatic = dynamicConfig === \"force-static\";\n const isDynamicError = dynamicConfig === \"error\";\n\n // force-static: replace headers/cookies context with empty values and\n // clear searchParams so dynamic APIs return defaults instead of real data\n if (isForceStatic) {\n setHeadersContext({ headers: new Headers(), cookies: new Map() });\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: new URLSearchParams(),\n params,\n });\n }\n\n // dynamic = 'error': install an access error so request APIs fail with the\n // static-generation message even for legacy sync property access.\n if (isDynamicError) {\n const errorMsg = 'Page with \\`dynamic = \"error\"\\` used a dynamic API. ' +\n 'This page was expected to be fully static, but headers(), cookies(), ' +\n 'or searchParams was accessed. Remove the dynamic API usage or change ' +\n 'the dynamic config to \"auto\" or \"force-dynamic\".';\n setHeadersContext({\n headers: new Headers(),\n cookies: new Map(),\n accessError: new Error(errorMsg),\n });\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: new URLSearchParams(),\n params,\n });\n }\n\n // force-dynamic: set no-store Cache-Control\n const isForceDynamic = dynamicConfig === \"force-dynamic\";\n\n // ── ISR cache read (production only) ─────────────────────────────────────\n // Read from cache BEFORE generateStaticParams and all rendering work.\n // This is the critical performance optimization: on a cache hit we skip\n // ALL expensive work (generateStaticParams, buildPageElement, layout probe,\n // page probe, renderToReadableStream, SSR). Both HTML and RSC requests\n // (client-side navigation / prefetch) are served from cache.\n //\n // HTML and RSC are stored under separate keys (matching Next.js's .html/.rsc\n // file layout) so each request type reads and writes independently — no races,\n // no partial-entry sentinels, no read-before-write hacks needed.\n //\n // force-static and dynamic='error' are compatible with ISR — they control\n // how dynamic APIs behave during rendering, not whether results are cached.\n // Only force-dynamic truly bypasses the ISR cache.\n if (\n process.env.NODE_ENV === \"production\" &&\n !isForceDynamic &&\n revalidateSeconds !== null && revalidateSeconds > 0 && revalidateSeconds !== Infinity\n ) {\n const __cachedPageResponse = await __readAppPageCacheResponse({\n cleanPathname,\n clearRequestContext: function() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n isRscRequest,\n isrDebug: __isrDebug,\n isrGet: __isrGet,\n isrHtmlKey: __isrHtmlKey,\n isrRscKey: __isrRscKey,\n isrSet: __isrSet,\n revalidateSeconds,\n renderFreshPageForCache: async function() {\n // Re-render the page to produce fresh HTML + RSC data for the cache\n // Use an empty headers context for background regeneration — not the original\n // user request — to prevent user-specific cookies/auth headers from leaking\n // into content that is cached and served to all subsequent users.\n const __revalHeadCtx = { headers: new Headers(), cookies: new Map() };\n const __revalUCtx = _createUnifiedCtx({\n headersContext: __revalHeadCtx,\n executionContext: _getRequestExecutionContext(),\n });\n return _runWithUnifiedCtx(__revalUCtx, async () => {\n _ensureFetchPatch();\n setNavigationContext({ pathname: cleanPathname, searchParams: new URLSearchParams(), params });\n const __revalElement = await buildPageElement(route, params, undefined, new URLSearchParams());\n const __revalOnError = createRscOnErrorHandler(request, cleanPathname, route.pattern);\n const __revalRscStream = renderToReadableStream(__revalElement, { onError: __revalOnError });\n const __revalRscCapture = __teeAppPageRscStreamForCapture(__revalRscStream, true);\n const __revalFontData = { links: _getSSRFontLinks(), styles: _getSSRFontStyles(), preloads: _getSSRFontPreloads() };\n const __revalSsrEntry = await import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n const __revalHtmlStream = await __revalSsrEntry.handleSsr(\n __revalRscCapture.responseStream,\n _getNavigationContext(),\n __revalFontData,\n );\n setHeadersContext(null);\n setNavigationContext(null);\n const __freshHtml = await __readAppPageTextStream(__revalHtmlStream);\n const __freshRscData = await __revalRscCapture.capturedRscDataPromise;\n const __pageTags = __pageCacheTags(cleanPathname, getCollectedFetchTags());\n return { html: __freshHtml, rscData: __freshRscData, tags: __pageTags };\n });\n },\n scheduleBackgroundRegeneration: __triggerBackgroundRegeneration,\n });\n if (__cachedPageResponse) {\n return __cachedPageResponse;\n }\n }\n\n // dynamicParams = false: only params from generateStaticParams are allowed.\n // This runs AFTER the ISR cache read so that a cache hit skips this work entirely.\n const __dynamicParamsResponse = await __validateAppPageDynamicParams({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n enforceStaticParamsOnly: dynamicParamsConfig === false,\n generateStaticParams: route.page?.generateStaticParams,\n isDynamicRoute: route.isDynamic,\n logGenerateStaticParamsError(err) {\n console.error(\"[vinext] generateStaticParams error:\", err);\n },\n params,\n });\n if (__dynamicParamsResponse) {\n return __dynamicParamsResponse;\n }\n\n // Check for intercepting routes on RSC requests (client-side navigation).\n // If the target URL matches an intercepting route in a parallel slot,\n // render the source route with the intercepting page in the slot.\n const __interceptResult = await __resolveAppPageIntercept({\n buildPageElement,\n cleanPathname,\n currentRoute: route,\n findIntercept,\n getRoutePattern(sourceRoute) {\n return sourceRoute.pattern;\n },\n getSourceRoute(sourceRouteIndex) {\n return routes[sourceRouteIndex];\n },\n isRscRequest,\n matchSourceRouteParams(pattern) {\n return matchRoute(pattern)?.params ?? {};\n },\n renderInterceptResponse(sourceRoute, interceptElement) {\n const interceptOnError = createRscOnErrorHandler(\n request,\n cleanPathname,\n sourceRoute.pattern,\n );\n const interceptStream = renderToReadableStream(interceptElement, {\n onError: interceptOnError,\n });\n // Do NOT clear headers/navigation context here — the RSC stream is consumed lazily\n // by the client, and async server components that run during consumption need the\n // context to still be live. The AsyncLocalStorage scope from runWithRequestContext\n // handles cleanup naturally when all async continuations complete.\n return new Response(interceptStream, {\n headers: { \"Content-Type\": \"text/x-component; charset=utf-8\", \"Vary\": \"RSC, Accept\" },\n });\n },\n searchParams: url.searchParams,\n setNavigationContext,\n toInterceptOpts(intercept) {\n return {\n interceptSlot: intercept.slotName,\n interceptPage: intercept.page,\n interceptParams: intercept.matchedParams,\n };\n },\n });\n if (__interceptResult.response) {\n return __interceptResult.response;\n }\n const interceptOpts = __interceptResult.interceptOpts;\n\n const __pageBuildResult = await __buildAppPageElement({\n buildPageElement() {\n return buildPageElement(route, params, interceptOpts, url.searchParams);\n },\n renderErrorBoundaryPage(buildErr) {\n return renderErrorBoundaryPage(route, buildErr, isRscRequest, request, params);\n },\n renderSpecialError(__buildSpecialError) {\n return __buildAppPageSpecialErrorResponse({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n renderFallbackPage(statusCode) {\n return renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, {\n matchedParams: params,\n });\n },\n requestUrl: request.url,\n specialError: __buildSpecialError,\n });\n },\n resolveSpecialError: __resolveAppPageSpecialError,\n });\n if (__pageBuildResult.response) {\n return __pageBuildResult.response;\n }\n const element = __pageBuildResult.element;\n\n // Note: CSS is automatically injected by @vitejs/plugin-rsc's\n // rscCssTransform — no manual loadCss() call needed.\n const _hasLoadingBoundary = !!(route.loading && route.loading.default);\n const _asyncLayoutParams = makeThenableParams(params);\n return __renderAppPageLifecycle({\n cleanPathname,\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n consumeDynamicUsage,\n createRscOnErrorHandler(pathname, routePath) {\n return createRscOnErrorHandler(request, pathname, routePath);\n },\n element,\n getDraftModeCookieHeader,\n getFontLinks: _getSSRFontLinks,\n getFontPreloads: _getSSRFontPreloads,\n getFontStyles: _getSSRFontStyles,\n getNavigationContext: _getNavigationContext,\n getPageTags() {\n return __pageCacheTags(cleanPathname, getCollectedFetchTags());\n },\n getRequestCacheLife() {\n return _consumeRequestScopedCacheLife();\n },\n handlerStart: __reqStart,\n hasLoadingBoundary: _hasLoadingBoundary,\n isDynamicError,\n isForceDynamic,\n isForceStatic,\n isProduction: process.env.NODE_ENV === \"production\",\n isRscRequest,\n isrDebug: __isrDebug,\n isrHtmlKey: __isrHtmlKey,\n isrRscKey: __isrRscKey,\n isrSet: __isrSet,\n layoutCount: route.layouts?.length ?? 0,\n loadSsrHandler() {\n return import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n },\n middlewareContext: _mwCtx,\n params,\n probeLayoutAt(li) {\n const LayoutComp = route.layouts[li]?.default;\n if (!LayoutComp) return null;\n return LayoutComp({ params: _asyncLayoutParams, children: null });\n },\n probePage() {\n return PageComponent({ params });\n },\n revalidateSeconds,\n renderErrorBoundaryResponse(renderErr) {\n return renderErrorBoundaryPage(route, renderErr, isRscRequest, request, params);\n },\n async renderLayoutSpecialError(__layoutSpecialError, li) {\n return __buildAppPageSpecialErrorResponse({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n renderFallbackPage(statusCode) {\n // Find the not-found component from the parent level (the boundary that\n // would catch this in Next.js). Walk up from the throwing layout to find\n // the nearest not-found at a parent layout's directory.\n let parentNotFound = null;\n if (route.notFounds) {\n for (let pi = li - 1; pi >= 0; pi--) {\n if (route.notFounds[pi]?.default) {\n parentNotFound = route.notFounds[pi].default;\n break;\n }\n }\n }\n if (!parentNotFound) parentNotFound = ${rootNotFoundVar ? `${rootNotFoundVar}?.default` : \"null\"};\n const parentLayouts = route.layouts.slice(0, li);\n return renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, {\n boundaryComponent: parentNotFound,\n layouts: parentLayouts,\n matchedParams: params,\n });\n },\n requestUrl: request.url,\n specialError: __layoutSpecialError,\n });\n },\n async renderPageSpecialError(specialError) {\n return __buildAppPageSpecialErrorResponse({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n renderFallbackPage(statusCode) {\n return renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, {\n matchedParams: params,\n });\n },\n requestUrl: request.url,\n specialError,\n });\n },\n renderToReadableStream,\n routeHasLocalBoundary: !!(route?.error?.default) || !!(route?.errors && route.errors.some(function(e) { return e?.default; })),\n routePattern: route.pattern,\n runWithSuppressedHookWarning(probe) {\n // Run inside ALS context so the module-level console.error patch suppresses\n // \"Invalid hook call\" only for this request's probe — concurrent requests\n // each have their own ALS store and are unaffected.\n return _suppressHookWarningAls.run(true, probe);\n },\n waitUntil(__cachePromise) {\n _getRequestExecutionContext()?.waitUntil(__cachePromise);\n },\n });\n}\n\nif (import.meta.hot) {\n import.meta.hot.accept();\n}\n`;\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"app-rsc-entry.js","names":[],"sources":["../../src/entries/app-rsc-entry.ts"],"sourcesContent":["/**\n * App Router RSC entry generator.\n *\n * Generates the virtual RSC entry module for the App Router.\n * The RSC entry does route matching and renders the component tree,\n * then delegates to the SSR entry for HTML generation.\n *\n * Previously housed in server/app-dev-server.ts.\n */\nimport fs from \"node:fs\";\nimport { resolveEntryPath } from \"./runtime-entry-module.js\";\nimport type {\n NextHeader,\n NextI18nConfig,\n NextRedirect,\n NextRewrite,\n} from \"../config/next-config.js\";\nimport type { AppRoute } from \"../routing/app-router.js\";\nimport { generateDevOriginCheckCode } from \"../server/dev-origin-check.js\";\nimport type { MetadataFileRoute } from \"../server/metadata-routes.js\";\nimport {\n generateMiddlewareMatcherCode,\n generateNormalizePathCode,\n generateSafeRegExpCode,\n generateRouteMatchNormalizationCode,\n} from \"../server/middleware-codegen.js\";\nimport { isProxyFile } from \"../server/middleware.js\";\n\n// Pre-computed absolute paths for generated-code imports. The virtual RSC\n// entry can't use relative imports (it has no real file location), so we\n// resolve these at code-generation time and embed them as absolute paths.\nconst configMatchersPath = resolveEntryPath(\"../config/config-matchers.js\", import.meta.url);\nconst requestPipelinePath = resolveEntryPath(\"../server/request-pipeline.js\", import.meta.url);\nconst requestContextShimPath = resolveEntryPath(\"../shims/request-context.js\", import.meta.url);\nconst normalizePathModulePath = resolveEntryPath(\"../server/normalize-path.js\", import.meta.url);\nconst appRouteHandlerRuntimePath = resolveEntryPath(\n \"../server/app-route-handler-runtime.js\",\n import.meta.url,\n);\nconst appRouteHandlerPolicyPath = resolveEntryPath(\n \"../server/app-route-handler-policy.js\",\n import.meta.url,\n);\nconst appRouteHandlerExecutionPath = resolveEntryPath(\n \"../server/app-route-handler-execution.js\",\n import.meta.url,\n);\nconst appRouteHandlerCachePath = resolveEntryPath(\n \"../server/app-route-handler-cache.js\",\n import.meta.url,\n);\nconst appPageCachePath = resolveEntryPath(\"../server/app-page-cache.js\", import.meta.url);\nconst appPageExecutionPath = resolveEntryPath(\"../server/app-page-execution.js\", import.meta.url);\nconst appPageBoundaryRenderPath = resolveEntryPath(\n \"../server/app-page-boundary-render.js\",\n import.meta.url,\n);\nconst appPageRouteWiringPath = resolveEntryPath(\n \"../server/app-page-route-wiring.js\",\n import.meta.url,\n);\nconst appPageRenderPath = resolveEntryPath(\"../server/app-page-render.js\", import.meta.url);\nconst appPageResponsePath = resolveEntryPath(\"../server/app-page-response.js\", import.meta.url);\nconst appPageRequestPath = resolveEntryPath(\"../server/app-page-request.js\", import.meta.url);\nconst appRouteHandlerResponsePath = resolveEntryPath(\n \"../server/app-route-handler-response.js\",\n import.meta.url,\n);\nconst routeTriePath = resolveEntryPath(\"../routing/route-trie.js\", import.meta.url);\nconst metadataRoutesPath = resolveEntryPath(\"../server/metadata-routes.js\", import.meta.url);\n\n/**\n * Resolved config options relevant to App Router request handling.\n * Passed from the Vite plugin where the full next.config.js is loaded.\n */\nexport type AppRouterConfig = {\n redirects?: NextRedirect[];\n rewrites?: {\n beforeFiles: NextRewrite[];\n afterFiles: NextRewrite[];\n fallback: NextRewrite[];\n };\n headers?: NextHeader[];\n /** Extra origins allowed for server action CSRF checks (from experimental.serverActions.allowedOrigins). */\n allowedOrigins?: string[];\n /** Extra origins allowed for dev server access (from allowedDevOrigins). */\n allowedDevOrigins?: string[];\n /** Body size limit for server actions in bytes (from experimental.serverActions.bodySizeLimit). */\n bodySizeLimit?: number;\n /** Internationalization routing config for middleware matcher locale handling. */\n i18n?: NextI18nConfig | null;\n /**\n * When true, the project has a `pages/` directory alongside the App Router.\n * The generated RSC entry exposes `/__vinext/prerender/pages-static-paths`\n * so `prerenderPages` can call `getStaticPaths` via `wrangler unstable_startWorker`\n * in CF Workers builds. `pageRoutes` is loaded from the SSR environment via\n * `import(\"./ssr/index.js\")`, which re-exports it from\n * `virtual:vinext-server-entry` when this flag is set.\n */\n hasPagesDir?: boolean;\n /** Exact public/ file routes, using normalized leading-slash pathnames. */\n publicFiles?: string[];\n};\n\n/**\n * Generate the virtual RSC entry module.\n *\n * This runs in the `rsc` Vite environment (react-server condition).\n * It matches the incoming request URL to an app route, builds the\n * nested layout + page tree, and renders it to an RSC stream.\n */\nexport function generateRscEntry(\n appDir: string,\n routes: AppRoute[],\n middlewarePath?: string | null,\n metadataRoutes?: MetadataFileRoute[],\n globalErrorPath?: string | null,\n basePath?: string,\n trailingSlash?: boolean,\n config?: AppRouterConfig,\n instrumentationPath?: string | null,\n): string {\n const bp = basePath ?? \"\";\n const ts = trailingSlash ?? false;\n const redirects = config?.redirects ?? [];\n const rewrites = config?.rewrites ?? { beforeFiles: [], afterFiles: [], fallback: [] };\n const headers = config?.headers ?? [];\n const allowedOrigins = config?.allowedOrigins ?? [];\n const bodySizeLimit = config?.bodySizeLimit ?? 1 * 1024 * 1024;\n const i18nConfig = config?.i18n ?? null;\n const hasPagesDir = config?.hasPagesDir ?? false;\n const publicFiles = config?.publicFiles ?? [];\n // Build import map for all page and layout files\n const imports: string[] = [];\n const importMap: Map<string, string> = new Map();\n let importIdx = 0;\n\n function getImportVar(filePath: string): string {\n if (importMap.has(filePath)) return importMap.get(filePath)!;\n const varName = `mod_${importIdx++}`;\n const absPath = filePath.replace(/\\\\/g, \"/\");\n imports.push(`import * as ${varName} from ${JSON.stringify(absPath)};`);\n importMap.set(filePath, varName);\n return varName;\n }\n\n // Pre-register all modules\n for (const route of routes) {\n if (route.pagePath) getImportVar(route.pagePath);\n if (route.routePath) getImportVar(route.routePath);\n for (const layout of route.layouts) getImportVar(layout);\n for (const tmpl of route.templates) {\n if (tmpl) getImportVar(tmpl);\n }\n if (route.loadingPath) getImportVar(route.loadingPath);\n if (route.errorPath) getImportVar(route.errorPath);\n if (route.layoutErrorPaths)\n for (const ep of route.layoutErrorPaths) {\n if (ep) getImportVar(ep);\n }\n if (route.notFoundPath) getImportVar(route.notFoundPath);\n for (const nfp of route.notFoundPaths || []) {\n if (nfp) getImportVar(nfp);\n }\n if (route.forbiddenPath) getImportVar(route.forbiddenPath);\n if (route.unauthorizedPath) getImportVar(route.unauthorizedPath);\n // Register parallel slot modules\n for (const slot of route.parallelSlots) {\n if (slot.pagePath) getImportVar(slot.pagePath);\n if (slot.defaultPath) getImportVar(slot.defaultPath);\n if (slot.layoutPath) getImportVar(slot.layoutPath);\n if (slot.loadingPath) getImportVar(slot.loadingPath);\n if (slot.errorPath) getImportVar(slot.errorPath);\n // Register intercepting route page modules\n for (const ir of slot.interceptingRoutes) {\n getImportVar(ir.pagePath);\n }\n }\n }\n\n // Build route table as serialized JS\n const routeEntries = routes.map((route) => {\n const layoutVars = route.layouts.map((l) => getImportVar(l));\n const templateVars = route.templates.map((t) => (t ? getImportVar(t) : \"null\"));\n const notFoundVars = (route.notFoundPaths || []).map((nf) => (nf ? getImportVar(nf) : \"null\"));\n const slotEntries = route.parallelSlots.map((slot) => {\n const interceptEntries = slot.interceptingRoutes.map(\n (ir) => ` {\n convention: ${JSON.stringify(ir.convention)},\n targetPattern: ${JSON.stringify(ir.targetPattern)},\n page: ${getImportVar(ir.pagePath)},\n params: ${JSON.stringify(ir.params)},\n }`,\n );\n return ` ${JSON.stringify(slot.name)}: {\n page: ${slot.pagePath ? getImportVar(slot.pagePath) : \"null\"},\n default: ${slot.defaultPath ? getImportVar(slot.defaultPath) : \"null\"},\n layout: ${slot.layoutPath ? getImportVar(slot.layoutPath) : \"null\"},\n loading: ${slot.loadingPath ? getImportVar(slot.loadingPath) : \"null\"},\n error: ${slot.errorPath ? getImportVar(slot.errorPath) : \"null\"},\n layoutIndex: ${slot.layoutIndex},\n routeSegments: ${JSON.stringify(slot.routeSegments)},\n intercepts: [\n${interceptEntries.join(\",\\n\")}\n ],\n }`;\n });\n const layoutErrorVars = (route.layoutErrorPaths || []).map((ep) =>\n ep ? getImportVar(ep) : \"null\",\n );\n return ` {\n pattern: ${JSON.stringify(route.pattern)},\n patternParts: ${JSON.stringify(route.patternParts)},\n isDynamic: ${route.isDynamic},\n params: ${JSON.stringify(route.params)},\n page: ${route.pagePath ? getImportVar(route.pagePath) : \"null\"},\n routeHandler: ${route.routePath ? getImportVar(route.routePath) : \"null\"},\n layouts: [${layoutVars.join(\", \")}],\n routeSegments: ${JSON.stringify(route.routeSegments)},\n layoutTreePositions: ${JSON.stringify(route.layoutTreePositions)},\n templates: [${templateVars.join(\", \")}],\n errors: [${layoutErrorVars.join(\", \")}],\n slots: {\n${slotEntries.join(\",\\n\")}\n },\n loading: ${route.loadingPath ? getImportVar(route.loadingPath) : \"null\"},\n error: ${route.errorPath ? getImportVar(route.errorPath) : \"null\"},\n notFound: ${route.notFoundPath ? getImportVar(route.notFoundPath) : \"null\"},\n notFounds: [${notFoundVars.join(\", \")}],\n forbidden: ${route.forbiddenPath ? getImportVar(route.forbiddenPath) : \"null\"},\n unauthorized: ${route.unauthorizedPath ? getImportVar(route.unauthorizedPath) : \"null\"},\n }`;\n });\n\n // Find root not-found/forbidden/unauthorized pages and root layouts for global error handling\n const rootRoute = routes.find((r) => r.pattern === \"/\");\n const rootNotFoundVar = rootRoute?.notFoundPath ? getImportVar(rootRoute.notFoundPath) : null;\n const rootForbiddenVar = rootRoute?.forbiddenPath ? getImportVar(rootRoute.forbiddenPath) : null;\n const rootUnauthorizedVar = rootRoute?.unauthorizedPath\n ? getImportVar(rootRoute.unauthorizedPath)\n : null;\n const rootLayoutVars = rootRoute ? rootRoute.layouts.map((l) => getImportVar(l)) : [];\n\n // Global error boundary (app/global-error.tsx)\n const globalErrorVar = globalErrorPath ? getImportVar(globalErrorPath) : null;\n\n // Build metadata route handling\n const effectiveMetaRoutes = metadataRoutes ?? [];\n const dynamicMetaRoutes = effectiveMetaRoutes.filter((r) => r.isDynamic);\n\n // Import dynamic metadata modules\n for (const mr of dynamicMetaRoutes) {\n getImportVar(mr.filePath);\n }\n\n // Build metadata route table\n // For static metadata files, read the file content at code-generation time\n // and embed it as base64. This ensures static metadata files work on runtimes\n // without filesystem access (e.g., Cloudflare Workers).\n //\n // For metadata routes in dynamic segments (e.g., /blog/[slug]/opengraph-image),\n // generate patternParts so the runtime can use matchPattern() instead of strict\n // equality — the same matching used for intercept routes.\n const metaRouteEntries = effectiveMetaRoutes.map((mr) => {\n // Convert dynamic segments in servedUrl to matchPattern format.\n // Keep in sync with routing/app-router.ts patternParts generation.\n // [param] → :param\n // [...param] → :param+\n // [[...param]] → :param*\n const patternParts =\n mr.isDynamic && mr.servedUrl.includes(\"[\")\n ? JSON.stringify(\n mr.servedUrl\n .split(\"/\")\n .filter(Boolean)\n .map((seg) => {\n if (seg.startsWith(\"[[...\") && seg.endsWith(\"]]\"))\n return \":\" + seg.slice(5, -2) + \"*\";\n if (seg.startsWith(\"[...\") && seg.endsWith(\"]\"))\n return \":\" + seg.slice(4, -1) + \"+\";\n if (seg.startsWith(\"[\") && seg.endsWith(\"]\")) return \":\" + seg.slice(1, -1);\n return seg;\n }),\n )\n : null;\n\n if (mr.isDynamic) {\n return ` {\n type: ${JSON.stringify(mr.type)},\n isDynamic: true,\n servedUrl: ${JSON.stringify(mr.servedUrl)},\n contentType: ${JSON.stringify(mr.contentType)},\n module: ${getImportVar(mr.filePath)},${patternParts ? `\\n patternParts: ${patternParts},` : \"\"}\n }`;\n }\n // Static: read file and embed as base64\n let fileDataBase64 = \"\";\n try {\n const buf = fs.readFileSync(mr.filePath);\n fileDataBase64 = buf.toString(\"base64\");\n } catch {\n // File unreadable — will serve empty response at runtime\n }\n return ` {\n type: ${JSON.stringify(mr.type)},\n isDynamic: false,\n servedUrl: ${JSON.stringify(mr.servedUrl)},\n contentType: ${JSON.stringify(mr.contentType)},\n fileDataBase64: ${JSON.stringify(fileDataBase64)},\n }`;\n });\n\n return `\nimport {\n renderToReadableStream as _renderToReadableStream,\n decodeReply,\n loadServerAction,\n createTemporaryReferenceSet,\n} from \"@vitejs/plugin-rsc/rsc\";\nimport { AsyncLocalStorage } from \"node:async_hooks\";\n\n// React Flight emits HL hints with \"stylesheet\" for CSS, but the HTML spec\n// requires \"style\" for <link rel=\"preload\">. Fix at the source so every\n// consumer (SSR embed, client-side navigation, server actions) gets clean data.\n//\n// Flight lines are newline-delimited, so we buffer partial lines across chunks\n// to guarantee the regex never sees a split hint.\nfunction renderToReadableStream(model, options) {\n const _hlFixRe = /(\\\\d*:HL\\\\[.*?),\"stylesheet\"(\\\\]|,)/g;\n const stream = _renderToReadableStream(model, options);\n const decoder = new TextDecoder();\n const encoder = new TextEncoder();\n let carry = \"\";\n return stream.pipeThrough(new TransformStream({\n transform(chunk, controller) {\n const text = carry + decoder.decode(chunk, { stream: true });\n const lastNl = text.lastIndexOf(\"\\\\n\");\n if (lastNl === -1) {\n carry = text;\n return;\n }\n carry = text.slice(lastNl + 1);\n controller.enqueue(encoder.encode(text.slice(0, lastNl + 1).replace(_hlFixRe, '$1,\"style\"$2')));\n },\n flush(controller) {\n const text = carry + decoder.decode();\n if (text) controller.enqueue(encoder.encode(text.replace(_hlFixRe, '$1,\"style\"$2')));\n }\n }));\n}\nimport { createElement } from \"react\";\nimport { setNavigationContext as _setNavigationContextOrig, getNavigationContext as _getNavigationContext } from \"next/navigation\";\nimport { setHeadersContext, headersContextFromRequest, getDraftModeCookieHeader, getAndClearPendingCookies, consumeDynamicUsage, markDynamicUsage, applyMiddlewareRequestHeaders, getHeadersContext, setHeadersAccessPhase } from \"next/headers\";\nimport { NextRequest, NextFetchEvent } from \"next/server\";\nimport { mergeMetadata, resolveModuleMetadata, mergeViewport, resolveModuleViewport } from \"vinext/metadata\";\n${middlewarePath ? `import * as middlewareModule from ${JSON.stringify(middlewarePath.replace(/\\\\/g, \"/\"))};` : \"\"}\n${instrumentationPath ? `import * as _instrumentation from ${JSON.stringify(instrumentationPath.replace(/\\\\/g, \"/\"))};` : \"\"}\n${effectiveMetaRoutes.length > 0 ? `import { sitemapToXml, robotsToText, manifestToJson } from ${JSON.stringify(metadataRoutesPath)};` : \"\"}\nimport { requestContextFromRequest, normalizeHost, matchRedirect, matchRewrite, matchHeaders, isExternalUrl, proxyExternalRequest, sanitizeDestination } from ${JSON.stringify(configMatchersPath)};\nimport { decodePathParams as __decodePathParams } from ${JSON.stringify(normalizePathModulePath)};\nimport { validateCsrfOrigin, validateImageUrl, guardProtocolRelativeUrl, hasBasePath, stripBasePath, normalizeTrailingSlash, processMiddlewareHeaders } from ${JSON.stringify(requestPipelinePath)};\nimport {\n isKnownDynamicAppRoute as __isKnownDynamicAppRoute,\n} from ${JSON.stringify(appRouteHandlerRuntimePath)};\nimport {\n getAppRouteHandlerRevalidateSeconds as __getAppRouteHandlerRevalidateSeconds,\n hasAppRouteHandlerDefaultExport as __hasAppRouteHandlerDefaultExport,\n resolveAppRouteHandlerMethod as __resolveAppRouteHandlerMethod,\n shouldReadAppRouteHandlerCache as __shouldReadAppRouteHandlerCache,\n} from ${JSON.stringify(appRouteHandlerPolicyPath)};\nimport {\n executeAppRouteHandler as __executeAppRouteHandler,\n} from ${JSON.stringify(appRouteHandlerExecutionPath)};\nimport { readAppRouteHandlerCacheResponse as __readAppRouteHandlerCacheResponse } from ${JSON.stringify(appRouteHandlerCachePath)};\nimport { readAppPageCacheResponse as __readAppPageCacheResponse } from ${JSON.stringify(appPageCachePath)};\nimport {\n buildAppPageFontLinkHeader as __buildAppPageFontLinkHeader,\n buildAppPageSpecialErrorResponse as __buildAppPageSpecialErrorResponse,\n readAppPageTextStream as __readAppPageTextStream,\n resolveAppPageSpecialError as __resolveAppPageSpecialError,\n teeAppPageRscStreamForCapture as __teeAppPageRscStreamForCapture,\n} from ${JSON.stringify(appPageExecutionPath)};\nimport {\n renderAppPageErrorBoundary as __renderAppPageErrorBoundary,\n renderAppPageHttpAccessFallback as __renderAppPageHttpAccessFallback,\n} from ${JSON.stringify(appPageBoundaryRenderPath)};\nimport {\n buildAppPageRouteElement as __buildAppPageRouteElement,\n resolveAppPageChildSegments as __resolveAppPageChildSegments,\n} from ${JSON.stringify(appPageRouteWiringPath)};\nimport {\n renderAppPageLifecycle as __renderAppPageLifecycle,\n} from ${JSON.stringify(appPageRenderPath)};\nimport {\n mergeMiddlewareResponseHeaders as __mergeMiddlewareResponseHeaders,\n} from ${JSON.stringify(appPageResponsePath)};\nimport {\n buildAppPageElement as __buildAppPageElement,\n resolveAppPageIntercept as __resolveAppPageIntercept,\n validateAppPageDynamicParams as __validateAppPageDynamicParams,\n} from ${JSON.stringify(appPageRequestPath)};\nimport {\n applyRouteHandlerMiddlewareContext as __applyRouteHandlerMiddlewareContext,\n} from ${JSON.stringify(appRouteHandlerResponsePath)};\nimport { _consumeRequestScopedCacheLife, getCacheHandler } from \"next/cache\";\nimport { getRequestExecutionContext as _getRequestExecutionContext } from ${JSON.stringify(requestContextShimPath)};\nimport { ensureFetchPatch as _ensureFetchPatch, getCollectedFetchTags } from \"vinext/fetch-cache\";\nimport { buildRouteTrie as _buildRouteTrie, trieMatch as _trieMatch } from ${JSON.stringify(routeTriePath)};\n// Import server-only state module to register ALS-backed accessors.\nimport \"vinext/navigation-state\";\nimport { runWithRequestContext as _runWithUnifiedCtx, createRequestContext as _createUnifiedCtx } from \"vinext/unified-request-context\";\nimport { reportRequestError as _reportRequestError } from \"vinext/instrumentation\";\nimport { getSSRFontLinks as _getSSRFontLinks, getSSRFontStyles as _getSSRFontStylesGoogle, getSSRFontPreloads as _getSSRFontPreloadsGoogle } from \"next/font/google\";\nimport { getSSRFontStyles as _getSSRFontStylesLocal, getSSRFontPreloads as _getSSRFontPreloadsLocal } from \"next/font/local\";\nfunction _getSSRFontStyles() { return [..._getSSRFontStylesGoogle(), ..._getSSRFontStylesLocal()]; }\nfunction _getSSRFontPreloads() { return [..._getSSRFontPreloadsGoogle(), ..._getSSRFontPreloadsLocal()]; }\n${hasPagesDir ? `// Note: pageRoutes loaded lazily via SSR env in /__vinext/prerender/pages-static-paths handler` : \"\"}\n\n// ALS used to suppress the expected \"Invalid hook call\" dev warning when\n// layout/page components are probed outside React's render cycle. Patching\n// console.error once at module load (instead of per-request) avoids the\n// concurrent-request issue where request A's suppression filter could\n// swallow real errors from request B.\nconst _suppressHookWarningAls = new AsyncLocalStorage();\nconst _origConsoleError = console.error;\nconsole.error = (...args) => {\n if (_suppressHookWarningAls.getStore() === true &&\n typeof args[0] === \"string\" &&\n args[0].includes(\"Invalid hook call\")) return;\n _origConsoleError.apply(console, args);\n};\n\n// Set navigation context in the ALS-backed store. \"use client\" components\n// rendered during SSR need the pathname/searchParams/params but the SSR\n// environment has a separate module instance of next/navigation.\n// Use _getNavigationContext() to read the current context — never cache\n// it in a module-level variable (that would leak between concurrent requests).\nfunction setNavigationContext(ctx) {\n _setNavigationContextOrig(ctx);\n}\n\n// ISR cache is disabled in dev mode — every request re-renders fresh,\n// matching Next.js dev behavior. Cache-Control headers are still emitted\n// based on export const revalidate for testing purposes.\n// Production ISR uses the MemoryCacheHandler (or configured KV handler).\n//\n// These helpers are inlined instead of imported from isr-cache.js because\n// the virtual RSC entry module runs in the RSC Vite environment which\n// cannot use dynamic imports at the module-evaluation level for server-only\n// modules, and direct imports must use the pre-computed absolute paths.\nasync function __isrGet(key) {\n const handler = getCacheHandler();\n const result = await handler.get(key);\n if (!result || !result.value) return null;\n return { value: result, isStale: result.cacheState === \"stale\" };\n}\nasync function __isrSet(key, data, revalidateSeconds, tags) {\n const handler = getCacheHandler();\n await handler.set(key, data, { revalidate: revalidateSeconds, tags: Array.isArray(tags) ? tags : [] });\n}\nfunction __pageCacheTags(pathname, extraTags) {\n const tags = [pathname, \"_N_T_\" + pathname];\n // Layout hierarchy tags — matches Next.js getDerivedTags.\n tags.push(\"_N_T_/layout\");\n const segments = pathname.split(\"/\");\n let built = \"\";\n for (let i = 1; i < segments.length; i++) {\n if (segments[i]) {\n built += \"/\" + segments[i];\n tags.push(\"_N_T_\" + built + \"/layout\");\n }\n }\n // Leaf page tag — revalidatePath(path, \"page\") targets this.\n tags.push(\"_N_T_\" + built + \"/page\");\n if (Array.isArray(extraTags)) {\n for (const tag of extraTags) {\n if (!tags.includes(tag)) tags.push(tag);\n }\n }\n return tags;\n}\n// Note: cache entries are written with \\`headers: undefined\\`. Next.js stores\n// response headers (e.g. set-cookie from cookies().set() during render) in the\n// cache entry so they can be replayed on HIT. We don't do this because:\n// 1. Pages that call cookies().set() during render trigger dynamicUsedDuringRender,\n// which opts them out of ISR caching before we reach the write path.\n// 2. Custom response headers set via next/headers are not yet captured separately\n// from the live Response object in vinext's server pipeline.\n// In practice this means ISR-cached responses won't replay render-time set-cookie\n// headers — but that case is already prevented by the dynamic-usage opt-out.\n// TODO: capture render-time response headers for full Next.js parity.\nconst __pendingRegenerations = new Map();\nfunction __triggerBackgroundRegeneration(key, renderFn) {\n if (__pendingRegenerations.has(key)) return;\n const promise = renderFn()\n .catch((err) => console.error(\"[vinext] ISR regen failed for \" + key + \":\", err))\n .finally(() => __pendingRegenerations.delete(key));\n __pendingRegenerations.set(key, promise);\n const ctx = _getRequestExecutionContext();\n if (ctx && typeof ctx.waitUntil === \"function\") ctx.waitUntil(promise);\n}\n// HTML and RSC are stored under separate keys — matching Next.js's file-system\n// layout (.html / .rsc) — so each request type reads and writes its own key\n// independently with no races or partial-entry sentinels.\n//\n// Key format: \"app:<buildId>:<pathname>:<suffix>\"\n// Long-pathname fallback: \"app:<buildId>:__hash:<fnv1a64(pathname)>:<suffix>\"\n// Without buildId (should not happen in production): \"app:<pathname>:<suffix>\"\n// The 200-char threshold keeps the full key well under Cloudflare KV's 512-byte limit\n// even after adding the build ID and suffix. FNV-1a 64 is used for the hash (two\n// 32-bit rounds) to give a ~64-bit output with negligible collision probability for\n// realistic pathname lengths.\n// Keep prefix construction and hashing logic in sync with isrCacheKey() in server/isr-cache.ts.\nfunction __isrFnv1a64(s) {\n // h1 uses the standard FNV-1a 32-bit offset basis (0x811c9dc5).\n let h1 = 0x811c9dc5;\n for (let i = 0; i < s.length; i++) { h1 ^= s.charCodeAt(i); h1 = (h1 * 0x01000193) >>> 0; }\n // h2 uses a different seed (0x050c5d1f — the FNV-1a hash of the string \"vinext\")\n // so the two rounds are independently seeded and their outputs are decorrelated.\n // Concatenating two independently-seeded 32-bit FNV-1a hashes gives an effective\n // 64-bit hash. A random non-standard seed would also work; we derive it from a\n // fixed string so the choice is auditable and deterministic across rebuilds.\n let h2 = 0x050c5d1f;\n for (let i = 0; i < s.length; i++) { h2 ^= s.charCodeAt(i); h2 = (h2 * 0x01000193) >>> 0; }\n return h1.toString(36) + h2.toString(36);\n}\nfunction __isrCacheKey(pathname, suffix) {\n const normalized = pathname === \"/\" ? \"/\" : pathname.replace(/\\\\/$/, \"\");\n // __VINEXT_BUILD_ID is replaced at compile time by Vite's define plugin.\n const buildId = process.env.__VINEXT_BUILD_ID;\n const prefix = buildId ? \"app:\" + buildId : \"app\";\n const key = prefix + \":\" + normalized + \":\" + suffix;\n if (key.length <= 200) return key;\n // Pathname too long — hash it to keep under KV's 512-byte key limit.\n return prefix + \":__hash:\" + __isrFnv1a64(normalized) + \":\" + suffix;\n}\nfunction __isrHtmlKey(pathname) { return __isrCacheKey(pathname, \"html\"); }\nfunction __isrRscKey(pathname) { return __isrCacheKey(pathname, \"rsc\"); }\nfunction __isrRouteKey(pathname) { return __isrCacheKey(pathname, \"route\"); }\n// Verbose cache logging — opt in with NEXT_PRIVATE_DEBUG_CACHE=1.\n// Matches the env var Next.js uses for its own cache debug output so operators\n// have a single knob for all cache tracing.\nconst __isrDebug = process.env.NEXT_PRIVATE_DEBUG_CACHE\n ? console.debug.bind(console, \"[vinext] ISR:\")\n : undefined;\n\n// Normalize null-prototype objects from matchPattern() into thenable objects\n// that work both as Promises (for Next.js 15+ async params) and as plain\n// objects with synchronous property access (for pre-15 code like params.id).\n//\n// matchPattern() uses Object.create(null), producing objects without\n// Object.prototype. The RSC serializer rejects these. Spreading ({...obj})\n// restores a normal prototype. Object.assign onto the Promise preserves\n// synchronous property access (params.id, params.slug) that existing\n// components and test fixtures rely on.\nfunction makeThenableParams(obj) {\n const plain = { ...obj };\n return Object.assign(Promise.resolve(plain), plain);\n}\n\n// djb2 hash — matches Next.js's stringHash for digest generation.\n// Produces a stable numeric string from error message + stack.\nfunction __errorDigest(str) {\n let hash = 5381;\n for (let i = str.length - 1; i >= 0; i--) {\n hash = (hash * 33) ^ str.charCodeAt(i);\n }\n return (hash >>> 0).toString();\n}\n\n// Sanitize an error for client consumption. In production, replaces the error\n// with a generic Error that only carries a digest hash (matching Next.js\n// behavior). In development, returns the original error for debugging.\n// Navigation errors (redirect, notFound, etc.) are always passed through\n// unchanged since their digests are used for client-side routing.\nfunction __sanitizeErrorForClient(error) {\n // Navigation errors must pass through with their digest intact\n if (__resolveAppPageSpecialError(error)) {\n return error;\n }\n // In development, pass through the original error for debugging\n if (process.env.NODE_ENV !== \"production\") {\n return error;\n }\n // In production, create a sanitized error with only a digest hash\n const msg = error instanceof Error ? error.message : String(error);\n const stack = error instanceof Error ? (error.stack || \"\") : \"\";\n const sanitized = new Error(\n \"An error occurred in the Server Components render. \" +\n \"The specific message is omitted in production builds to avoid leaking sensitive details. \" +\n \"A digest property is included on this error instance which may provide additional details about the nature of the error.\"\n );\n sanitized.digest = __errorDigest(msg + stack);\n return sanitized;\n}\n\n// onError callback for renderToReadableStream — preserves the digest for\n// Next.js navigation errors (redirect, notFound, forbidden, unauthorized)\n// thrown during RSC streaming (e.g. inside Suspense boundaries).\n// For non-navigation errors in production, generates a digest hash so the\n// error can be correlated with server logs without leaking details.\nfunction rscOnError(error, requestInfo, errorContext) {\n if (error && typeof error === \"object\" && \"digest\" in error) {\n return String(error.digest);\n }\n\n // In dev, detect the \"Only plain objects\" RSC serialization error and emit\n // an actionable hint. This error occurs when a Server Component passes a\n // class instance, ES module namespace object, or null-prototype object as a\n // prop to a Client Component.\n //\n // Root cause: Vite bundles modules as true ESM (module namespace objects\n // have a null-like internal slot), while Next.js's webpack build produces\n // plain CJS-wrapped objects with __esModule:true. React's RSC serializer\n // accepts the latter as plain objects but rejects the former — which means\n // code that accidentally passes \"import * as X\" works in webpack/Next.js\n // but correctly fails in vinext.\n //\n // Common triggers:\n // - \"import * as utils from './utils'\" passed as a prop\n // - class instances (new Foo()) passed as props\n // - Date / Map / Set instances passed as props\n // - Objects with Object.create(null) (null prototype)\n if (\n process.env.NODE_ENV !== \"production\" &&\n error instanceof Error &&\n error.message.includes(\"Only plain objects, and a few built-ins, can be passed to Client Components\")\n ) {\n console.error(\n \"[vinext] RSC serialization error: a non-plain object was passed from a Server Component to a Client Component.\\\\n\" +\n \"\\\\n\" +\n \"Common causes:\\\\n\" +\n \" * Passing a module namespace (import * as X) directly as a prop.\\\\n\" +\n \" Unlike Next.js (webpack), Vite produces real ESM module namespace objects\\\\n\" +\n \" which are not serializable. Fix: pass individual values instead,\\\\n\" +\n \" e.g. <Comp value={module.value} />\\\\n\" +\n \" * Passing a class instance (new Foo()) as a prop.\\\\n\" +\n \" Fix: convert to a plain object, e.g. { id: foo.id, name: foo.name }\\\\n\" +\n \" * Passing a Date, Map, or Set. Use .toISOString(), [...map.entries()], etc.\\\\n\" +\n \" * Passing Object.create(null). Use { ...obj } to restore a prototype.\\\\n\" +\n \"\\\\n\" +\n \"Original error:\",\n error.message,\n );\n return undefined;\n }\n\n if (requestInfo && errorContext && error) {\n _reportRequestError(\n error instanceof Error ? error : new Error(String(error)),\n requestInfo,\n errorContext,\n );\n }\n\n // In production, generate a digest hash for non-navigation errors\n if (process.env.NODE_ENV === \"production\" && error) {\n const msg = error instanceof Error ? error.message : String(error);\n const stack = error instanceof Error ? (error.stack || \"\") : \"\";\n return __errorDigest(msg + stack);\n }\n return undefined;\n}\n\nfunction createRscOnErrorHandler(request, pathname, routePath) {\n const requestInfo = {\n path: pathname,\n method: request.method,\n headers: Object.fromEntries(request.headers.entries()),\n };\n const errorContext = {\n routerKind: \"App Router\",\n routePath: routePath || pathname,\n routeType: \"render\",\n };\n return function(error) {\n return rscOnError(error, requestInfo, errorContext);\n };\n}\n\n${imports.join(\"\\n\")}\n\n${\n instrumentationPath\n ? `// Run instrumentation register() exactly once, lazily on the first request.\n// Previously this was a top-level await, which blocked the entire module graph\n// from finishing initialization until register() resolved — adding that latency\n// to every cold start. Moving it here preserves the \"runs before any request is\n// handled\" guarantee while not blocking V8 isolate initialization.\n// On Cloudflare Workers, module evaluation happens synchronously in the isolate\n// startup phase; a top-level await extends that phase and increases cold-start\n// wall time for all requests, not just the first.\nlet __instrumentationInitialized = false;\nlet __instrumentationInitPromise = null;\nasync function __ensureInstrumentation() {\n if (process.env.VINEXT_PRERENDER === \"1\") return;\n if (__instrumentationInitialized) return;\n if (__instrumentationInitPromise) return __instrumentationInitPromise;\n __instrumentationInitPromise = (async () => {\n if (typeof _instrumentation.register === \"function\") {\n await _instrumentation.register();\n }\n // Store the onRequestError handler on globalThis so it is visible to\n // reportRequestError() (imported as _reportRequestError above) regardless\n // of which Vite environment module graph it is called from. With\n // @vitejs/plugin-rsc the RSC and SSR environments run in the same Node.js\n // process and share globalThis. With @cloudflare/vite-plugin everything\n // runs inside the Worker so globalThis is the Worker's global — also correct.\n if (typeof _instrumentation.onRequestError === \"function\") {\n globalThis.__VINEXT_onRequestErrorHandler__ = _instrumentation.onRequestError;\n }\n __instrumentationInitialized = true;\n })();\n return __instrumentationInitPromise;\n}`\n : \"\"\n}\n\nconst routes = [\n${routeEntries.join(\",\\n\")}\n];\nconst _routeTrie = _buildRouteTrie(routes);\n\nconst metadataRoutes = [\n${metaRouteEntries.join(\",\\n\")}\n];\n\nconst rootNotFoundModule = ${rootNotFoundVar ? rootNotFoundVar : \"null\"};\nconst rootForbiddenModule = ${rootForbiddenVar ? rootForbiddenVar : \"null\"};\nconst rootUnauthorizedModule = ${rootUnauthorizedVar ? rootUnauthorizedVar : \"null\"};\nconst rootLayouts = [${rootLayoutVars.join(\", \")}];\n\n/**\n * Render an HTTP access fallback page (not-found/forbidden/unauthorized) with layouts and noindex meta.\n * Returns null if no matching component is available.\n *\n * @param opts.boundaryComponent - Override the boundary component (for layout-level notFound)\n * @param opts.layouts - Override the layouts to wrap with (for layout-level notFound, excludes the throwing layout)\n */\nasync function renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, opts) {\n return __renderAppPageHttpAccessFallback({\n boundaryComponent: opts?.boundaryComponent ?? null,\n buildFontLinkHeader: __buildAppPageFontLinkHeader,\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n createRscOnErrorHandler(pathname, routePath) {\n return createRscOnErrorHandler(request, pathname, routePath);\n },\n getFontLinks: _getSSRFontLinks,\n getFontPreloads: _getSSRFontPreloads,\n getFontStyles: _getSSRFontStyles,\n getNavigationContext: _getNavigationContext,\n globalErrorModule: ${globalErrorVar ? globalErrorVar : \"null\"},\n isRscRequest,\n layoutModules: opts?.layouts ?? null,\n loadSsrHandler() {\n return import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n },\n makeThenableParams,\n matchedParams: opts?.matchedParams ?? route?.params ?? {},\n requestUrl: request.url,\n resolveChildSegments: __resolveAppPageChildSegments,\n rootForbiddenModule: rootForbiddenModule,\n rootLayouts: rootLayouts,\n rootNotFoundModule: rootNotFoundModule,\n rootUnauthorizedModule: rootUnauthorizedModule,\n route,\n renderToReadableStream,\n statusCode,\n });\n}\n\n/** Convenience: render a not-found page (404) */\nasync function renderNotFoundPage(route, isRscRequest, request, matchedParams) {\n return renderHTTPAccessFallbackPage(route, 404, isRscRequest, request, { matchedParams });\n}\n\n/**\n * Render an error.tsx boundary page when a server component or generateMetadata() throws.\n * Returns null if no error boundary component is available for this route.\n *\n * Next.js returns HTTP 200 when error.tsx catches an error (the error is \"handled\"\n * by the boundary). This matches that behavior intentionally.\n */\nasync function renderErrorBoundaryPage(route, error, isRscRequest, request, matchedParams) {\n return __renderAppPageErrorBoundary({\n buildFontLinkHeader: __buildAppPageFontLinkHeader,\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n createRscOnErrorHandler(pathname, routePath) {\n return createRscOnErrorHandler(request, pathname, routePath);\n },\n error,\n getFontLinks: _getSSRFontLinks,\n getFontPreloads: _getSSRFontPreloads,\n getFontStyles: _getSSRFontStyles,\n getNavigationContext: _getNavigationContext,\n globalErrorModule: ${globalErrorVar ? globalErrorVar : \"null\"},\n isRscRequest,\n loadSsrHandler() {\n return import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n },\n makeThenableParams,\n matchedParams: matchedParams ?? route?.params ?? {},\n requestUrl: request.url,\n resolveChildSegments: __resolveAppPageChildSegments,\n rootLayouts: rootLayouts,\n route,\n renderToReadableStream,\n sanitizeErrorForClient: __sanitizeErrorForClient,\n });\n}\n\nfunction matchRoute(url) {\n const pathname = url.split(\"?\")[0];\n let normalizedUrl = pathname === \"/\" ? \"/\" : pathname.replace(/\\\\/$/, \"\");\n // NOTE: Do NOT decodeURIComponent here. The caller is responsible for decoding\n // the pathname exactly once at the request entry point. Decoding again here\n // would cause inconsistent path matching between middleware and routing.\n const urlParts = normalizedUrl.split(\"/\").filter(Boolean);\n return _trieMatch(_routeTrie, urlParts);\n}\n\nfunction __createStaticFileSignal(pathname, _mwCtx) {\n const headers = new Headers({\n \"x-vinext-static-file\": encodeURIComponent(pathname),\n });\n if (_mwCtx.headers) {\n for (const [key, value] of _mwCtx.headers) {\n headers.append(key, value);\n }\n }\n return new Response(null, {\n status: _mwCtx.status ?? 200,\n headers,\n });\n}\n\n// matchPattern is kept for findIntercept (linear scan over small interceptLookup array).\nfunction matchPattern(urlParts, patternParts) {\n const params = Object.create(null);\n for (let i = 0; i < patternParts.length; i++) {\n const pp = patternParts[i];\n if (pp.endsWith(\"+\")) {\n if (i !== patternParts.length - 1) return null;\n const paramName = pp.slice(1, -1);\n const remaining = urlParts.slice(i);\n if (remaining.length === 0) return null;\n params[paramName] = remaining;\n return params;\n }\n if (pp.endsWith(\"*\")) {\n if (i !== patternParts.length - 1) return null;\n const paramName = pp.slice(1, -1);\n params[paramName] = urlParts.slice(i);\n return params;\n }\n if (pp.startsWith(\":\")) {\n if (i >= urlParts.length) return null;\n params[pp.slice(1)] = urlParts[i];\n continue;\n }\n if (i >= urlParts.length || urlParts[i] !== pp) return null;\n }\n if (urlParts.length !== patternParts.length) return null;\n return params;\n}\n\n// Build a global intercepting route lookup for RSC navigation.\n// Maps target URL patterns to { sourceRouteIndex, slotName, interceptPage, params }.\nconst interceptLookup = [];\nfor (let ri = 0; ri < routes.length; ri++) {\n const r = routes[ri];\n if (!r.slots) continue;\n for (const [slotName, slotMod] of Object.entries(r.slots)) {\n if (!slotMod.intercepts) continue;\n for (const intercept of slotMod.intercepts) {\n interceptLookup.push({\n sourceRouteIndex: ri,\n slotName,\n targetPattern: intercept.targetPattern,\n targetPatternParts: intercept.targetPattern.split(\"/\").filter(Boolean),\n page: intercept.page,\n params: intercept.params,\n });\n }\n }\n}\n\n/**\n * Check if a pathname matches any intercepting route.\n * Returns the match info or null.\n */\nfunction findIntercept(pathname) {\n const urlParts = pathname.split(\"/\").filter(Boolean);\n for (const entry of interceptLookup) {\n const params = matchPattern(urlParts, entry.targetPatternParts);\n if (params !== null) {\n return { ...entry, matchedParams: params };\n }\n }\n return null;\n}\n\nasync function buildPageElement(route, params, opts, searchParams) {\n const PageComponent = route.page?.default;\n if (!PageComponent) {\n return createElement(\"div\", null, \"Page has no default export\");\n }\n\n // Resolve metadata and viewport from layouts and page.\n //\n // generateMetadata() accepts a \"parent\" (Promise of ResolvedMetadata) as its\n // second argument (Next.js 13+). The parent resolves to the accumulated\n // merged metadata of all ancestor segments, enabling patterns like:\n //\n // const previousImages = (await parent).openGraph?.images ?? []\n // return { openGraph: { images: ['/new-image.jpg', ...previousImages] } }\n //\n // Next.js uses an eager-execution-with-serial-resolution approach:\n // all generateMetadata() calls are kicked off concurrently, but each\n // segment's \"parent\" promise resolves only after the preceding segment's\n // metadata is resolved and merged. This preserves concurrency for I/O-bound\n // work while guaranteeing that parent data is available when needed.\n //\n // We build a chain: layoutParentPromises[0] = Promise.resolve({}) (no parent\n // for root layout), layoutParentPromises[i+1] resolves to merge(layouts[0..i]),\n // and pageParentPromise resolves to merge(all layouts).\n //\n // IMPORTANT: Layout metadata errors are swallowed (.catch(() => null)) because\n // a layout's generateMetadata() failing should not crash the page.\n // Page metadata errors are NOT swallowed — if the page's generateMetadata()\n // throws, the error propagates out of buildPageElement() so the caller can\n // route it to the nearest error.tsx boundary (or global-error.tsx).\n const layoutMods = route.layouts.filter(Boolean);\n\n // Build the parent promise chain and kick off metadata resolution in one pass.\n // Each layout module is called exactly once. layoutMetaPromises[i] is the\n // promise for layout[i]'s own metadata result.\n //\n // All calls are kicked off immediately (concurrent I/O), but each layout's\n // \"parent\" promise only resolves after the preceding layout's metadata is done.\n const layoutMetaPromises = [];\n let accumulatedMetaPromise = Promise.resolve({});\n for (let i = 0; i < layoutMods.length; i++) {\n const parentForThisLayout = accumulatedMetaPromise;\n // Kick off this layout's metadata resolution now (concurrent with others).\n const metaPromise = resolveModuleMetadata(layoutMods[i], params, undefined, parentForThisLayout)\n .catch((err) => { console.error(\"[vinext] Layout generateMetadata() failed:\", err); return null; });\n layoutMetaPromises.push(metaPromise);\n // Advance accumulator: resolves to merged(layouts[0..i]) once layout[i] is done.\n accumulatedMetaPromise = metaPromise.then(async (result) =>\n result ? mergeMetadata([await parentForThisLayout, result]) : await parentForThisLayout\n );\n }\n // Page's parent is the fully-accumulated layout metadata.\n const pageParentPromise = accumulatedMetaPromise;\n\n // Convert URLSearchParams → plain object so we can pass it to\n // resolveModuleMetadata (which expects Record<string, string | string[]>).\n // This same object is reused for pageProps.searchParams below.\n const spObj = {};\n let hasSearchParams = false;\n if (searchParams && searchParams.forEach) {\n searchParams.forEach(function(v, k) {\n hasSearchParams = true;\n if (k in spObj) {\n spObj[k] = Array.isArray(spObj[k]) ? spObj[k].concat(v) : [spObj[k], v];\n } else {\n spObj[k] = v;\n }\n });\n }\n\n const [layoutMetaResults, layoutVpResults, pageMeta, pageVp] = await Promise.all([\n Promise.all(layoutMetaPromises),\n Promise.all(layoutMods.map((mod) => resolveModuleViewport(mod, params).catch((err) => { console.error(\"[vinext] Layout generateViewport() failed:\", err); return null; }))),\n route.page ? resolveModuleMetadata(route.page, params, spObj, pageParentPromise) : Promise.resolve(null),\n route.page ? resolveModuleViewport(route.page, params) : Promise.resolve(null),\n ]);\n\n const metadataList = [...layoutMetaResults.filter(Boolean), ...(pageMeta ? [pageMeta] : [])];\n const viewportList = [...layoutVpResults.filter(Boolean), ...(pageVp ? [pageVp] : [])];\n const resolvedMetadata = metadataList.length > 0 ? mergeMetadata(metadataList) : null;\n const resolvedViewport = mergeViewport(viewportList);\n\n // Build the route tree from the leaf page, then delegate the boundary/layout/\n // template/segment wiring to a typed runtime helper so the generated entry\n // stays thin and the wiring logic can be unit tested directly.\n const pageProps = { params: makeThenableParams(params) };\n if (searchParams) {\n // Always provide searchParams prop when the URL object is available, even\n // when the query string is empty -- pages that do \"await searchParams\" need\n // it to be a thenable rather than undefined.\n pageProps.searchParams = makeThenableParams(spObj);\n // If the URL has query parameters, mark the page as dynamic.\n // In Next.js, only accessing the searchParams prop signals dynamic usage,\n // but a Proxy-based approach doesn't work here because React's RSC debug\n // serializer accesses properties on all props (e.g. $$typeof check in\n // isClientReference), triggering the Proxy even when user code doesn't\n // read searchParams. Checking for non-empty query params is a safe\n // approximation: pages with query params in the URL are almost always\n // dynamic, and this avoids false positives from React internals.\n if (hasSearchParams) markDynamicUsage();\n }\n return __buildAppPageRouteElement({\n element: createElement(PageComponent, pageProps),\n globalErrorModule: ${globalErrorVar ? globalErrorVar : \"null\"},\n makeThenableParams,\n matchedParams: params,\n resolvedMetadata,\n resolvedViewport,\n rootNotFoundModule: ${rootNotFoundVar ? rootNotFoundVar : \"null\"},\n route,\n slotOverrides:\n opts && opts.interceptSlot && opts.interceptPage\n ? {\n [opts.interceptSlot]: {\n pageModule: opts.interceptPage,\n params: opts.interceptParams || params,\n },\n }\n : null,\n });\n}\n\n${middlewarePath ? generateMiddlewareMatcherCode(\"modern\") : \"\"}\n\nconst __basePath = ${JSON.stringify(bp)};\nconst __trailingSlash = ${JSON.stringify(ts)};\nconst __i18nConfig = ${JSON.stringify(i18nConfig)};\nconst __configRedirects = ${JSON.stringify(redirects)};\nconst __configRewrites = ${JSON.stringify(rewrites)};\nconst __configHeaders = ${JSON.stringify(headers)};\nconst __publicFiles = new Set(${JSON.stringify(publicFiles)});\nconst __allowedOrigins = ${JSON.stringify(allowedOrigins)};\n\n${generateDevOriginCheckCode(config?.allowedDevOrigins)}\n\n// ── ReDoS-safe regex compilation (still needed for middleware matching) ──\n${generateSafeRegExpCode(\"modern\")}\n\n// ── Path normalization ──────────────────────────────────────────────────\n${generateNormalizePathCode(\"modern\")}\n${generateRouteMatchNormalizationCode(\"modern\")}\n\n// ── Config pattern matching, redirects, rewrites, headers, CSRF validation,\n// external URL proxy, cookie parsing, and request context are imported from\n// config-matchers.ts and request-pipeline.ts (see import statements above).\n// This eliminates ~250 lines of duplicated inline code and ensures the\n// single-pass tokenizer in config-matchers.ts is used consistently\n// (fixing the chained .replace() divergence flagged by CodeQL).\n\n/**\n * Build a request context from the live ALS HeadersContext, which reflects\n * any x-middleware-request-* header mutations applied by middleware.\n * Used for afterFiles and fallback rewrite has/missing evaluation — these\n * run after middleware in the App Router execution order.\n */\nfunction __buildPostMwRequestContext(request) {\n const url = new URL(request.url);\n const ctx = getHeadersContext();\n if (!ctx) return requestContextFromRequest(request);\n // ctx.cookies is a Map<string, string> (HeadersContext), but RequestContext\n // requires a plain Record<string, string> for has/missing cookie evaluation\n // (config-matchers.ts uses obj[key] not Map.get()). Convert here.\n const cookiesRecord = Object.fromEntries(ctx.cookies);\n return {\n headers: ctx.headers,\n cookies: cookiesRecord,\n query: url.searchParams,\n host: normalizeHost(ctx.headers.get(\"host\"), url.hostname),\n };\n}\n\n/**\n * Maximum server-action request body size.\n * Configurable via experimental.serverActions.bodySizeLimit in next.config.\n * Defaults to 1MB, matching the Next.js default.\n * @see https://nextjs.org/docs/app/api-reference/config/next-config-js/serverActions#bodysizelimit\n * Prevents unbounded request body buffering.\n */\nvar __MAX_ACTION_BODY_SIZE = ${JSON.stringify(bodySizeLimit)};\n\n/**\n * Read a request body as text with a size limit.\n * Enforces the limit on the actual byte stream to prevent bypasses\n * via chunked transfer-encoding where Content-Length is absent or spoofed.\n */\nasync function __readBodyWithLimit(request, maxBytes) {\n if (!request.body) return \"\";\n var reader = request.body.getReader();\n var decoder = new TextDecoder();\n var chunks = [];\n var totalSize = 0;\n for (;;) {\n var result = await reader.read();\n if (result.done) break;\n totalSize += result.value.byteLength;\n if (totalSize > maxBytes) {\n reader.cancel();\n throw new Error(\"Request body too large\");\n }\n chunks.push(decoder.decode(result.value, { stream: true }));\n }\n chunks.push(decoder.decode());\n return chunks.join(\"\");\n}\n\n/**\n * Read a request body as FormData with a size limit.\n * Consumes the body stream with a byte counter and then parses the\n * collected bytes as multipart form data via the Response constructor.\n */\nasync function __readFormDataWithLimit(request, maxBytes) {\n if (!request.body) return new FormData();\n var reader = request.body.getReader();\n var chunks = [];\n var totalSize = 0;\n for (;;) {\n var result = await reader.read();\n if (result.done) break;\n totalSize += result.value.byteLength;\n if (totalSize > maxBytes) {\n reader.cancel();\n throw new Error(\"Request body too large\");\n }\n chunks.push(result.value);\n }\n // Reconstruct a Response with the original Content-Type so that\n // the FormData parser can handle multipart boundaries correctly.\n var combined = new Uint8Array(totalSize);\n var offset = 0;\n for (var chunk of chunks) {\n combined.set(chunk, offset);\n offset += chunk.byteLength;\n }\n var contentType = request.headers.get(\"content-type\") || \"\";\n return new Response(combined, { headers: { \"Content-Type\": contentType } }).formData();\n}\n\n// Map from route pattern to generateStaticParams function.\n// Used by the prerender phase to enumerate dynamic route URLs without\n// loading route modules via the dev server.\nexport const generateStaticParamsMap = {\n// TODO: layout-level generateStaticParams — this map only includes routes that\n// have a pagePath (leaf pages). Layout segments can also export generateStaticParams\n// to provide parent params for nested dynamic routes, but they don't have a pagePath\n// so they are excluded here. Supporting layout-level generateStaticParams requires\n// scanning layout.tsx files separately and including them in this map.\n${routes\n .filter((r) => r.isDynamic && r.pagePath)\n .map(\n (r) =>\n ` ${JSON.stringify(r.pattern)}: ${getImportVar(r.pagePath!)}?.generateStaticParams ?? null,`,\n )\n .join(\"\\n\")}\n};\n\nexport default async function handler(request, ctx) {\n ${\n instrumentationPath\n ? `// Ensure instrumentation.register() has run before handling the first request.\n // This is a no-op after the first call (guarded by __instrumentationInitialized).\n await __ensureInstrumentation();\n `\n : \"\"\n }\n // Wrap the entire request in a single unified ALS scope for per-request\n // isolation. All state modules (headers, navigation, cache, fetch-cache,\n // execution-context) read from this store via isInsideUnifiedScope().\n const headersCtx = headersContextFromRequest(request);\n const __uCtx = _createUnifiedCtx({\n headersContext: headersCtx,\n executionContext: ctx ?? _getRequestExecutionContext() ?? null,\n });\n return _runWithUnifiedCtx(__uCtx, async () => {\n _ensureFetchPatch();\n const __reqCtx = requestContextFromRequest(request);\n // Per-request container for middleware state. Passed into\n // _handleRequest which fills in .headers and .status;\n // avoids module-level variables that race on Workers.\n const _mwCtx = { headers: null, status: null };\n const response = await _handleRequest(request, __reqCtx, _mwCtx);\n // Apply custom headers from next.config.js to non-redirect responses.\n // Skip redirects (3xx) because Response.redirect() creates immutable headers,\n // and Next.js doesn't apply custom headers to redirects anyway.\n if (response && response.headers && !(response.status >= 300 && response.status < 400)) {\n if (__configHeaders.length) {\n const url = new URL(request.url);\n let pathname;\n try { pathname = __normalizePath(__normalizePathnameForRouteMatch(url.pathname)); } catch { pathname = url.pathname; }\n ${bp ? `if (pathname.startsWith(${JSON.stringify(bp)})) pathname = pathname.slice(${JSON.stringify(bp)}.length) || \"/\";` : \"\"}\n const extraHeaders = matchHeaders(pathname, __configHeaders, __reqCtx);\n for (const h of extraHeaders) {\n // Use append() for headers where multiple values must coexist\n // (Vary, Set-Cookie). Using set() on these would destroy\n // existing values like \"Vary: RSC, Accept\" which are critical\n // for correct CDN caching behavior.\n const lk = h.key.toLowerCase();\n if (lk === \"vary\" || lk === \"set-cookie\") {\n response.headers.append(h.key, h.value);\n } else if (!response.headers.has(lk)) {\n // Middleware headers take precedence: skip config keys already\n // set by middleware so middleware headers always win.\n response.headers.set(h.key, h.value);\n }\n }\n }\n }\n return response;\n });\n}\n\nasync function _handleRequest(request, __reqCtx, _mwCtx) {\n const __reqStart = process.env.NODE_ENV !== \"production\" ? performance.now() : 0;\n // __reqStart is included in the timing header so the Node logging middleware\n // can compute true compile time as: handlerStart - middlewareStart.\n // Format: \"handlerStart,compileMs,renderMs\" - all as integers (ms). Dev-only.\n const url = new URL(request.url);\n\n // ── Cross-origin request protection (dev only) ─────────────────────\n // Block requests from non-localhost origins to prevent data exfiltration.\n // Skipped in production — Vite replaces NODE_ENV at build time.\n if (process.env.NODE_ENV !== \"production\") {\n const __originBlock = __validateDevRequestOrigin(request);\n if (__originBlock) return __originBlock;\n }\n\n // Guard against protocol-relative URL open redirects (see request-pipeline.ts).\n const __protoGuard = guardProtocolRelativeUrl(url.pathname);\n if (__protoGuard) return __protoGuard;\n\n // Decode percent-encoding segment-wise and normalize pathname to canonical form.\n // This preserves encoded path delimiters like %2F within a single segment.\n // __normalizePath collapses //foo///bar → /foo/bar, resolves . and .. segments.\n let decodedUrlPathname;\n try { decodedUrlPathname = __normalizePathnameForRouteMatchStrict(url.pathname); } catch (e) {\n return new Response(\"Bad Request\", { status: 400 });\n }\n let pathname = __normalizePath(decodedUrlPathname);\n\n ${\n bp\n ? `\n if (!hasBasePath(pathname, __basePath) && !pathname.startsWith(\"/__vinext/\")) {\n return new Response(\"Not Found\", { status: 404 });\n }\n // Strip basePath prefix\n pathname = stripBasePath(pathname, __basePath);\n `\n : \"\"\n }\n\n // ── Prerender: static-params endpoint ────────────────────────────────\n // Internal endpoint used by prerenderApp() during build to fetch\n // generateStaticParams results via wrangler unstable_startWorker.\n // Gated on VINEXT_PRERENDER=1 to prevent exposure in normal deployments.\n // For Node builds, process.env.VINEXT_PRERENDER is set directly by the\n // prerender orchestrator. For CF Workers builds, wrangler unstable_startWorker\n // injects VINEXT_PRERENDER as a binding which Miniflare exposes via process.env\n // in bundled workers. The /__vinext/ prefix ensures no user route ever conflicts.\n if (pathname === \"/__vinext/prerender/static-params\") {\n if (process.env.VINEXT_PRERENDER !== \"1\") {\n return new Response(\"Not Found\", { status: 404 });\n }\n const pattern = url.searchParams.get(\"pattern\");\n if (!pattern) return new Response(\"missing pattern\", { status: 400 });\n const fn = generateStaticParamsMap[pattern];\n if (typeof fn !== \"function\") return new Response(\"null\", { status: 200, headers: { \"content-type\": \"application/json\" } });\n try {\n const parentParams = url.searchParams.get(\"parentParams\");\n const raw = parentParams ? JSON.parse(parentParams) : {};\n // Ensure params is a plain object — reject primitives, arrays, and null\n // so user-authored generateStaticParams always receives { params: {} }\n // rather than { params: 5 } or similar if input is malformed.\n const params = (typeof raw === \"object\" && raw !== null && !Array.isArray(raw)) ? raw : {};\n const result = await fn({ params });\n return new Response(JSON.stringify(result), { status: 200, headers: { \"content-type\": \"application/json\" } });\n } catch (e) {\n return new Response(JSON.stringify({ error: String(e) }), { status: 500, headers: { \"content-type\": \"application/json\" } });\n }\n }\n\n ${\n hasPagesDir\n ? `\n // ── Prerender: pages-static-paths endpoint ───────────────────────────\n // Internal endpoint used by prerenderPages() during a CF Workers hybrid\n // build to call getStaticPaths() for dynamic Pages Router routes via\n // wrangler unstable_startWorker. Returns JSON-serialised getStaticPaths result.\n // Gated on VINEXT_PRERENDER=1 to prevent exposure in normal deployments.\n // See static-params endpoint above for process.env vs CF vars notes.\n //\n // pageRoutes lives in the SSR environment (virtual:vinext-server-entry).\n // We load it lazily via import.meta.viteRsc.loadModule — the same pattern\n // used by handleSsr() elsewhere in this template. At build time, Vite's RSC\n // plugin transforms this call into a bundled cross-environment import, so it\n // works correctly in the CF Workers production bundle running in Miniflare.\n if (pathname === \"/__vinext/prerender/pages-static-paths\") {\n if (process.env.VINEXT_PRERENDER !== \"1\") {\n return new Response(\"Not Found\", { status: 404 });\n }\n const __gspPattern = url.searchParams.get(\"pattern\");\n if (!__gspPattern) return new Response(\"missing pattern\", { status: 400 });\n try {\n const __gspSsrEntry = await import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n const __pagesRoutes = __gspSsrEntry.pageRoutes;\n const __gspRoute = Array.isArray(__pagesRoutes)\n ? __pagesRoutes.find((r) => r.pattern === __gspPattern)\n : undefined;\n if (!__gspRoute || typeof __gspRoute.module?.getStaticPaths !== \"function\") {\n return new Response(\"null\", { status: 200, headers: { \"content-type\": \"application/json\" } });\n }\n const __localesParam = url.searchParams.get(\"locales\");\n const __locales = __localesParam ? JSON.parse(__localesParam) : [];\n const __defaultLocale = url.searchParams.get(\"defaultLocale\") ?? \"\";\n const __gspResult = await __gspRoute.module.getStaticPaths({ locales: __locales, defaultLocale: __defaultLocale });\n return new Response(JSON.stringify(__gspResult), { status: 200, headers: { \"content-type\": \"application/json\" } });\n } catch (e) {\n return new Response(JSON.stringify({ error: String(e) }), { status: 500, headers: { \"content-type\": \"application/json\" } });\n }\n }\n `\n : \"\"\n }\n\n // Trailing slash normalization (redirect to canonical form)\n const __tsRedirect = normalizeTrailingSlash(pathname, __basePath, __trailingSlash, url.search);\n if (__tsRedirect) return __tsRedirect;\n\n // ── Apply redirects from next.config.js ───────────────────────────────\n if (__configRedirects.length) {\n // Strip .rsc suffix before matching redirect rules - RSC (client-side nav) requests\n // arrive as /some/path.rsc but redirect patterns are defined without it (e.g.\n // /some/path). Without this, soft-nav fetches bypass all config redirects.\n const __redirPathname = pathname.endsWith(\".rsc\") ? pathname.slice(0, -4) : pathname;\n const __redir = matchRedirect(__redirPathname, __configRedirects, __reqCtx);\n if (__redir) {\n const __redirDest = sanitizeDestination(\n __basePath &&\n !isExternalUrl(__redir.destination) &&\n !hasBasePath(__redir.destination, __basePath)\n ? __basePath + __redir.destination\n : __redir.destination\n );\n return new Response(null, {\n status: __redir.permanent ? 308 : 307,\n headers: { Location: __redirDest },\n });\n }\n }\n\n const isRscRequest = pathname.endsWith(\".rsc\") || request.headers.get(\"accept\")?.includes(\"text/x-component\");\n let cleanPathname = pathname.replace(/\\\\.rsc$/, \"\");\n\n // Middleware response headers and custom rewrite status are stored in\n // _mwCtx (per-request container) so handler() can merge them into\n // every response path without module-level state that races on Workers.\n\n ${\n middlewarePath\n ? `\n // In hybrid app+pages dev mode the connect handler already ran middleware\n // and forwarded the results via x-vinext-mw-ctx. Reconstruct _mwCtx from\n // the forwarded data instead of re-running the middleware function.\n // Guarded by NODE_ENV because this header only exists in dev (the connect\n // handler sets it). In production there is no connect handler, so an\n // attacker-supplied header must not be trusted.\n let __mwCtxApplied = false;\n if (process.env.NODE_ENV !== \"production\") {\n const __mwCtxHeader = request.headers.get(\"x-vinext-mw-ctx\");\n if (__mwCtxHeader) {\n try {\n const __mwCtxData = JSON.parse(__mwCtxHeader);\n if (__mwCtxData.h && __mwCtxData.h.length > 0) {\n // Note: h may include x-middleware-request-* internal headers so\n // applyMiddlewareRequestHeaders() can unpack them below.\n // processMiddlewareHeaders() strips them before any response.\n _mwCtx.headers = new Headers();\n for (const [key, value] of __mwCtxData.h) {\n _mwCtx.headers.append(key, value);\n }\n }\n if (__mwCtxData.s != null) {\n _mwCtx.status = __mwCtxData.s;\n }\n // Apply forwarded middleware rewrite so routing uses the rewritten path.\n // The RSC plugin constructs its Request from the original HTTP request,\n // not from req.url, so the connect handler's req.url rewrite is invisible.\n if (__mwCtxData.r) {\n const __rewriteParsed = new URL(__mwCtxData.r, request.url);\n cleanPathname = __rewriteParsed.pathname;\n url.search = __rewriteParsed.search;\n }\n // Flag set after full context application — if any step fails (e.g. malformed\n // rewrite URL), we fall back to re-running middleware as a safety net.\n __mwCtxApplied = true;\n } catch (e) {\n console.error(\"[vinext] Failed to parse forwarded middleware context:\", e);\n }\n }\n }\n if (!__mwCtxApplied) {\n // Run proxy/middleware if present and path matches.\n // Validate exports match the file type (proxy.ts vs middleware.ts), matching Next.js behavior.\n // https://github.com/vercel/next.js/blob/canary/test/e2e/app-dir/proxy-missing-export/proxy-missing-export.test.ts\n const _isProxy = ${JSON.stringify(isProxyFile(middlewarePath))};\n const middlewareFn = _isProxy\n ? (middlewareModule.proxy ?? middlewareModule.default)\n : (middlewareModule.middleware ?? middlewareModule.default);\n if (typeof middlewareFn !== \"function\") {\n const _fileType = _isProxy ? \"Proxy\" : \"Middleware\";\n const _expectedExport = _isProxy ? \"proxy\" : \"middleware\";\n throw new Error(\"The \" + _fileType + \" file must export a function named \\`\" + _expectedExport + \"\\` or a \\`default\\` function.\");\n }\n const middlewareMatcher = middlewareModule.config?.matcher;\n if (matchesMiddleware(cleanPathname, middlewareMatcher, request, __i18nConfig)) {\n try {\n // Wrap in NextRequest so middleware gets .nextUrl, .cookies, .geo, .ip, etc.\n // Always construct a new Request with the fully decoded + normalized pathname\n // so middleware and the router see the same canonical path.\n const mwUrl = new URL(request.url);\n mwUrl.pathname = cleanPathname;\n const mwRequest = new Request(mwUrl, request);\n const __mwNextConfig = (__basePath || __i18nConfig) ? { basePath: __basePath, i18n: __i18nConfig ?? undefined } : undefined;\n const nextRequest = mwRequest instanceof NextRequest ? mwRequest : new NextRequest(mwRequest, __mwNextConfig ? { nextConfig: __mwNextConfig } : undefined);\n const mwFetchEvent = new NextFetchEvent({ page: cleanPathname });\n let mwResponse;\n try {\n mwResponse = await middlewareFn(nextRequest, mwFetchEvent);\n } finally {\n const _mwWaitUntil = mwFetchEvent.drainWaitUntil();\n const _mwExecCtx = _getRequestExecutionContext();\n if (_mwExecCtx && typeof _mwExecCtx.waitUntil === \"function\") { _mwExecCtx.waitUntil(_mwWaitUntil); }\n }\n if (mwResponse) {\n // Check for x-middleware-next (continue)\n if (mwResponse.headers.get(\"x-middleware-next\") === \"1\") {\n // Middleware wants to continue — collect all headers except the two\n // control headers we've already consumed. x-middleware-request-*\n // headers are kept so applyMiddlewareRequestHeaders() can unpack them;\n // the blanket strip loop after that call removes every remaining\n // x-middleware-* header before the set is merged into the response.\n _mwCtx.headers = new Headers();\n for (const [key, value] of mwResponse.headers) {\n if (key !== \"x-middleware-next\" && key !== \"x-middleware-rewrite\") {\n _mwCtx.headers.append(key, value);\n }\n }\n } else {\n // Check for redirect\n if (mwResponse.status >= 300 && mwResponse.status < 400) {\n return mwResponse;\n }\n // Check for rewrite\n const rewriteUrl = mwResponse.headers.get(\"x-middleware-rewrite\");\n if (rewriteUrl) {\n const rewriteParsed = new URL(rewriteUrl, request.url);\n cleanPathname = rewriteParsed.pathname;\n // Carry over query params from the rewrite URL so that\n // searchParams props, useSearchParams(), and navigation context\n // reflect the rewrite destination, not the original request.\n url.search = rewriteParsed.search;\n // Capture custom status code from rewrite (e.g. NextResponse.rewrite(url, { status: 403 }))\n if (mwResponse.status !== 200) {\n _mwCtx.status = mwResponse.status;\n }\n // Also save any other headers from the rewrite response\n _mwCtx.headers = new Headers();\n for (const [key, value] of mwResponse.headers) {\n if (key !== \"x-middleware-next\" && key !== \"x-middleware-rewrite\") {\n _mwCtx.headers.append(key, value);\n }\n }\n } else {\n // Middleware returned a custom response\n return mwResponse;\n }\n }\n }\n } catch (err) {\n console.error(\"[vinext] Middleware error:\", err);\n return new Response(\"Internal Server Error\", { status: 500 });\n }\n }\n } // end of if (!__mwCtxApplied)\n\n // Unpack x-middleware-request-* headers into the request context so that\n // headers() returns the middleware-modified headers instead of the original\n // request headers. Strip ALL x-middleware-* headers from the set that will\n // be merged into the outgoing HTTP response — this prefix is reserved for\n // internal routing signals and must never reach clients.\n if (_mwCtx.headers) {\n applyMiddlewareRequestHeaders(_mwCtx.headers);\n processMiddlewareHeaders(_mwCtx.headers);\n }\n `\n : \"\"\n }\n\n // Build post-middleware request context for afterFiles/fallback rewrites.\n // These run after middleware in the App Router execution order and should\n // evaluate has/missing conditions against middleware-modified headers.\n // When no middleware is present, this falls back to requestContextFromRequest.\n const __postMwReqCtx = __buildPostMwRequestContext(request);\n\n // ── Apply beforeFiles rewrites from next.config.js ────────────────────\n // In App Router execution order, beforeFiles runs after middleware so that\n // has/missing conditions can evaluate against middleware-modified headers.\n if (__configRewrites.beforeFiles && __configRewrites.beforeFiles.length) {\n const __rewritten = matchRewrite(cleanPathname, __configRewrites.beforeFiles, __postMwReqCtx);\n if (__rewritten) {\n if (isExternalUrl(__rewritten)) {\n setHeadersContext(null);\n setNavigationContext(null);\n return proxyExternalRequest(request, __rewritten);\n }\n cleanPathname = __rewritten;\n }\n }\n\n // ── Image optimization passthrough (dev mode — no transformation) ───────\n if (cleanPathname === \"/_vinext/image\") {\n const __imgResult = validateImageUrl(url.searchParams.get(\"url\"), request.url);\n if (__imgResult instanceof Response) return __imgResult;\n // In dev, redirect to the original asset URL so Vite's static serving handles it.\n return Response.redirect(new URL(__imgResult, url.origin).href, 302);\n }\n\n // Handle metadata routes (sitemap.xml, robots.txt, manifest.webmanifest, etc.)\n for (const metaRoute of metadataRoutes) {\n // generateSitemaps() support — paginated sitemaps at /{prefix}/sitemap/{id}.xml\n // When a sitemap module exports generateSitemaps, the base URL (e.g. /products/sitemap.xml)\n // is no longer served. Instead, individual sitemaps are served at /products/sitemap/{id}.xml.\n if (\n metaRoute.type === \"sitemap\" &&\n metaRoute.isDynamic &&\n typeof metaRoute.module.generateSitemaps === \"function\"\n ) {\n const sitemapPrefix = metaRoute.servedUrl.slice(0, -4); // strip \".xml\"\n // Match exactly /{prefix}/{id}.xml — one segment only (no slashes in id)\n if (cleanPathname.startsWith(sitemapPrefix + \"/\") && cleanPathname.endsWith(\".xml\")) {\n const rawId = cleanPathname.slice(sitemapPrefix.length + 1, -4);\n if (rawId.includes(\"/\")) continue; // multi-segment — not a paginated sitemap\n const sitemaps = await metaRoute.module.generateSitemaps();\n const matched = sitemaps.find(function(s) { return String(s.id) === rawId; });\n if (!matched) return new Response(\"Not Found\", { status: 404 });\n // Pass the original typed id from generateSitemaps() so numeric IDs stay numeric.\n // TODO: wrap with makeThenableParams-style Promise when upgrading to Next.js 16\n // full-Promise param semantics (id becomes Promise<string> in v16).\n const result = await metaRoute.module.default({ id: matched.id });\n if (result instanceof Response) return result;\n return new Response(sitemapToXml(result), {\n headers: { \"Content-Type\": metaRoute.contentType },\n });\n }\n // Skip — the base servedUrl is not served when generateSitemaps exists\n continue;\n }\n // Match metadata route — use pattern matching for dynamic segments,\n // strict equality for static paths.\n var _metaParams = null;\n if (metaRoute.patternParts) {\n var _metaUrlParts = cleanPathname.split(\"/\").filter(Boolean);\n _metaParams = matchPattern(_metaUrlParts, metaRoute.patternParts);\n if (!_metaParams) continue;\n } else if (cleanPathname !== metaRoute.servedUrl) {\n continue;\n }\n if (metaRoute.isDynamic) {\n // Dynamic metadata route — call the default export and serialize\n const metaFn = metaRoute.module.default;\n if (typeof metaFn === \"function\") {\n const result = await metaFn({ params: makeThenableParams(_metaParams || {}) });\n let body;\n // If it's already a Response (e.g., ImageResponse), return directly\n if (result instanceof Response) return result;\n // Serialize based on type\n if (metaRoute.type === \"sitemap\") body = sitemapToXml(result);\n else if (metaRoute.type === \"robots\") body = robotsToText(result);\n else if (metaRoute.type === \"manifest\") body = manifestToJson(result);\n else body = JSON.stringify(result);\n return new Response(body, {\n headers: { \"Content-Type\": metaRoute.contentType },\n });\n }\n } else {\n // Static metadata file — decode from embedded base64 data\n try {\n const binary = atob(metaRoute.fileDataBase64);\n const bytes = new Uint8Array(binary.length);\n for (let i = 0; i < binary.length; i++) bytes[i] = binary.charCodeAt(i);\n return new Response(bytes, {\n headers: {\n \"Content-Type\": metaRoute.contentType,\n \"Cache-Control\": \"public, max-age=0, must-revalidate\",\n },\n });\n } catch {\n return new Response(\"Not Found\", { status: 404 });\n }\n }\n }\n\n // Serve public/ files as filesystem routes after middleware and before\n // afterFiles/fallback rewrites, matching Next.js routing semantics.\n if (\n (request.method === \"GET\" || request.method === \"HEAD\") &&\n !pathname.endsWith(\".rsc\") &&\n __publicFiles.has(cleanPathname)\n ) {\n setHeadersContext(null);\n setNavigationContext(null);\n return __createStaticFileSignal(cleanPathname, _mwCtx);\n }\n\n // Set navigation context for Server Components.\n // Note: Headers context is already set by runWithRequestContext in the handler wrapper.\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: url.searchParams,\n params: {},\n });\n\n // Handle server action POST requests\n const actionId = request.headers.get(\"x-rsc-action\");\n if (request.method === \"POST\" && actionId) {\n // ── CSRF protection ─────────────────────────────────────────────────\n // Verify that the Origin header matches the Host header to prevent\n // cross-site request forgery, matching Next.js server action behavior.\n const csrfResponse = validateCsrfOrigin(request, __allowedOrigins);\n if (csrfResponse) return csrfResponse;\n\n // ── Body size limit ─────────────────────────────────────────────────\n // Reject payloads larger than the configured limit.\n // Check Content-Length as a fast path, then enforce on the actual\n // stream to prevent bypasses via chunked transfer-encoding.\n const contentLength = parseInt(request.headers.get(\"content-length\") || \"0\", 10);\n if (contentLength > __MAX_ACTION_BODY_SIZE) {\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Payload Too Large\", { status: 413 });\n }\n\n try {\n const contentType = request.headers.get(\"content-type\") || \"\";\n let body;\n try {\n body = contentType.startsWith(\"multipart/form-data\")\n ? await __readFormDataWithLimit(request, __MAX_ACTION_BODY_SIZE)\n : await __readBodyWithLimit(request, __MAX_ACTION_BODY_SIZE);\n } catch (sizeErr) {\n if (sizeErr && sizeErr.message === \"Request body too large\") {\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Payload Too Large\", { status: 413 });\n }\n throw sizeErr;\n }\n const temporaryReferences = createTemporaryReferenceSet();\n const args = await decodeReply(body, { temporaryReferences });\n const action = await loadServerAction(actionId);\n let returnValue;\n let actionRedirect = null;\n const previousHeadersPhase = setHeadersAccessPhase(\"action\");\n try {\n try {\n const data = await action.apply(null, args);\n returnValue = { ok: true, data };\n } catch (e) {\n // Detect redirect() / permanentRedirect() called inside the action.\n // These throw errors with digest \"NEXT_REDIRECT;<type>;<url>[;<status>]\".\n // The type field is empty when redirect() was called without an explicit\n // type argument. In Server Action context, Next.js defaults to \"push\" so\n // the Back button works after form submissions.\n // The URL is encodeURIComponent-encoded to prevent semicolons in the URL\n // from corrupting the delimiter-based digest format.\n if (e && typeof e === \"object\" && \"digest\" in e) {\n const digest = String(e.digest);\n if (digest.startsWith(\"NEXT_REDIRECT;\")) {\n const parts = digest.split(\";\");\n actionRedirect = {\n url: decodeURIComponent(parts[2]),\n type: parts[1] || \"push\", // Server Action → default \"push\"\n status: parts[3] ? parseInt(parts[3], 10) : 307,\n };\n returnValue = { ok: true, data: undefined };\n } else if (digest === \"NEXT_NOT_FOUND\" || digest.startsWith(\"NEXT_HTTP_ERROR_FALLBACK;\")) {\n // notFound() / forbidden() / unauthorized() in action — package as error\n returnValue = { ok: false, data: e };\n } else {\n // Non-navigation digest error — sanitize in production to avoid\n // leaking internal details (connection strings, paths, etc.)\n console.error(\"[vinext] Server action error:\", e);\n returnValue = { ok: false, data: __sanitizeErrorForClient(e) };\n }\n } else {\n // Unhandled error — sanitize in production to avoid leaking\n // internal details (database errors, file paths, stack traces, etc.)\n console.error(\"[vinext] Server action error:\", e);\n returnValue = { ok: false, data: __sanitizeErrorForClient(e) };\n }\n }\n } finally {\n setHeadersAccessPhase(previousHeadersPhase);\n }\n\n // If the action called redirect(), signal the client to navigate.\n // We can't use a real HTTP redirect (the fetch would follow it automatically\n // and receive a page HTML instead of RSC stream). Instead, we return a 200\n // with x-action-redirect header that the client entry detects and handles.\n if (actionRedirect) {\n const actionPendingCookies = getAndClearPendingCookies();\n const actionDraftCookie = getDraftModeCookieHeader();\n setHeadersContext(null);\n setNavigationContext(null);\n const redirectHeaders = new Headers({\n \"Content-Type\": \"text/x-component; charset=utf-8\",\n \"Vary\": \"RSC, Accept\",\n });\n // Merge middleware headers first so the framework's own redirect control\n // headers below are always authoritative and cannot be clobbered by\n // middleware that happens to set x-action-redirect* keys.\n __mergeMiddlewareResponseHeaders(redirectHeaders, _mwCtx.headers);\n redirectHeaders.set(\"x-action-redirect\", actionRedirect.url);\n redirectHeaders.set(\"x-action-redirect-type\", actionRedirect.type);\n redirectHeaders.set(\"x-action-redirect-status\", String(actionRedirect.status));\n for (const cookie of actionPendingCookies) {\n redirectHeaders.append(\"Set-Cookie\", cookie);\n }\n if (actionDraftCookie) redirectHeaders.append(\"Set-Cookie\", actionDraftCookie);\n // Send an empty RSC-like body (client will navigate instead of parsing)\n return new Response(\"\", { status: 200, headers: redirectHeaders });\n }\n\n // After the action, re-render the current page so the client\n // gets an updated React tree reflecting any mutations.\n const match = matchRoute(cleanPathname);\n let element;\n if (match) {\n const { route: actionRoute, params: actionParams } = match;\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: url.searchParams,\n params: actionParams,\n });\n element = await buildPageElement(actionRoute, actionParams, undefined, url.searchParams);\n } else {\n element = createElement(\"div\", null, \"Page not found\");\n }\n\n const onRenderError = createRscOnErrorHandler(\n request,\n cleanPathname,\n match ? match.route.pattern : cleanPathname,\n );\n const rscStream = renderToReadableStream(\n { root: element, returnValue },\n { temporaryReferences, onError: onRenderError },\n );\n\n // Collect cookies set during the action synchronously (before stream is consumed).\n // Do NOT clear headers/navigation context here — the RSC stream is consumed lazily\n // by the client, and async server components that run during consumption need the\n // context to still be live. The AsyncLocalStorage scope from runWithRequestContext\n // handles cleanup naturally when all async continuations complete.\n const actionPendingCookies = getAndClearPendingCookies();\n const actionDraftCookie = getDraftModeCookieHeader();\n\n const actionHeaders = new Headers({ \"Content-Type\": \"text/x-component; charset=utf-8\", \"Vary\": \"RSC, Accept\" });\n __mergeMiddlewareResponseHeaders(actionHeaders, _mwCtx.headers);\n if (actionPendingCookies.length > 0 || actionDraftCookie) {\n for (const cookie of actionPendingCookies) {\n actionHeaders.append(\"Set-Cookie\", cookie);\n }\n if (actionDraftCookie) actionHeaders.append(\"Set-Cookie\", actionDraftCookie);\n }\n return new Response(rscStream, { status: _mwCtx.status ?? 200, headers: actionHeaders });\n } catch (err) {\n getAndClearPendingCookies(); // Clear pending cookies on error\n console.error(\"[vinext] Server action error:\", err);\n _reportRequestError(\n err instanceof Error ? err : new Error(String(err)),\n { path: cleanPathname, method: request.method, headers: Object.fromEntries(request.headers.entries()) },\n { routerKind: \"App Router\", routePath: cleanPathname, routeType: \"action\" },\n );\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\n process.env.NODE_ENV === \"production\"\n ? \"Internal Server Error\"\n : \"Server action failed: \" + (err && err.message ? err.message : String(err)),\n { status: 500 },\n );\n }\n }\n\n // ── Apply afterFiles rewrites from next.config.js ──────────────────────\n if (__configRewrites.afterFiles && __configRewrites.afterFiles.length) {\n const __afterRewritten = matchRewrite(cleanPathname, __configRewrites.afterFiles, __postMwReqCtx);\n if (__afterRewritten) {\n if (isExternalUrl(__afterRewritten)) {\n setHeadersContext(null);\n setNavigationContext(null);\n return proxyExternalRequest(request, __afterRewritten);\n }\n cleanPathname = __afterRewritten;\n }\n }\n\n let match = matchRoute(cleanPathname);\n\n // ── Fallback rewrites from next.config.js (if no route matched) ───────\n if (!match && __configRewrites.fallback && __configRewrites.fallback.length) {\n const __fallbackRewritten = matchRewrite(cleanPathname, __configRewrites.fallback, __postMwReqCtx);\n if (__fallbackRewritten) {\n if (isExternalUrl(__fallbackRewritten)) {\n setHeadersContext(null);\n setNavigationContext(null);\n return proxyExternalRequest(request, __fallbackRewritten);\n }\n cleanPathname = __fallbackRewritten;\n match = matchRoute(cleanPathname);\n }\n }\n\n if (!match) {\n ${\n hasPagesDir\n ? `\n // ── Pages Router fallback ────────────────────────────────────────────\n // When a request doesn't match any App Router route, delegate to the\n // Pages Router handler (available in the SSR environment). This covers\n // both production request serving and prerender fetches from wrangler.\n // RSC requests (.rsc suffix or Accept: text/x-component) cannot be\n // handled by the Pages Router, so skip the delegation for those.\n if (!isRscRequest) {\n const __pagesEntry = await import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n if (typeof __pagesEntry.renderPage === \"function\") {\n // Use segment-wise decoding to preserve encoded path delimiters (%2F).\n // decodeURIComponent would turn /admin%2Fpanel into /admin/panel,\n // changing the path structure and bypassing middleware matchers.\n // Ported from Next.js: packages/next/src/server/lib/router-utils/decode-path-params.ts\n // https://github.com/vercel/next.js/blob/canary/packages/next/src/server/lib/router-utils/decode-path-params.ts\n const __pagesRes = await __pagesEntry.renderPage(request, __decodePathParams(url.pathname) + (url.search || \"\"), {});\n // Only return the Pages Router response if it matched a route\n // (non-404). A 404 means the path isn't a Pages route either,\n // so fall through to the App Router not-found page below.\n if (__pagesRes.status !== 404) {\n setHeadersContext(null);\n setNavigationContext(null);\n return __pagesRes;\n }\n }\n }\n `\n : \"\"\n }\n // Render custom not-found page if available, otherwise plain 404\n const notFoundResponse = await renderNotFoundPage(null, isRscRequest, request);\n if (notFoundResponse) return notFoundResponse;\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Not Found\", { status: 404 });\n }\n\n const { route, params } = match;\n\n // Update navigation context with matched params\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: url.searchParams,\n params,\n });\n\n // Handle route.ts API handlers\n if (route.routeHandler) {\n const handler = route.routeHandler;\n const method = request.method.toUpperCase();\n const revalidateSeconds = __getAppRouteHandlerRevalidateSeconds(handler);\n if (__hasAppRouteHandlerDefaultExport(handler) && process.env.NODE_ENV === \"development\") {\n console.error(\n \"[vinext] Detected default export in route handler \" + route.pattern + \". Export a named export for each HTTP method instead.\",\n );\n }\n\n const {\n allowHeaderForOptions,\n handlerFn,\n isAutoHead,\n shouldAutoRespondToOptions,\n } = __resolveAppRouteHandlerMethod(handler, method);\n\n if (shouldAutoRespondToOptions) {\n setHeadersContext(null);\n setNavigationContext(null);\n return __applyRouteHandlerMiddlewareContext(\n new Response(null, {\n status: 204,\n headers: { \"Allow\": allowHeaderForOptions },\n }),\n _mwCtx,\n );\n }\n\n // ISR cache read for route handlers (production only).\n // Only GET/HEAD (auto-HEAD) with finite revalidate > 0 are ISR-eligible.\n // Known-dynamic handlers skip the read entirely so stale cache entries\n // from earlier requests do not replay once the process has learned they\n // access request-specific data.\n if (\n __shouldReadAppRouteHandlerCache({\n dynamicConfig: handler.dynamic,\n handlerFn,\n isAutoHead,\n isKnownDynamic: __isKnownDynamicAppRoute(route.pattern),\n isProduction: process.env.NODE_ENV === \"production\",\n method,\n revalidateSeconds,\n })\n ) {\n const __cachedRouteResponse = await __readAppRouteHandlerCacheResponse({\n basePath: __basePath,\n buildPageCacheTags: __pageCacheTags,\n cleanPathname,\n clearRequestContext: function() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n consumeDynamicUsage,\n getCollectedFetchTags,\n handlerFn,\n i18n: __i18nConfig,\n isAutoHead,\n isrDebug: __isrDebug,\n isrGet: __isrGet,\n isrRouteKey: __isrRouteKey,\n isrSet: __isrSet,\n markDynamicUsage,\n middlewareContext: _mwCtx,\n params,\n requestUrl: request.url,\n revalidateSearchParams: url.searchParams,\n revalidateSeconds,\n routePattern: route.pattern,\n runInRevalidationContext: async function(renderFn) {\n const __revalHeadCtx = { headers: new Headers(), cookies: new Map() };\n const __revalUCtx = _createUnifiedCtx({\n headersContext: __revalHeadCtx,\n executionContext: _getRequestExecutionContext(),\n });\n await _runWithUnifiedCtx(__revalUCtx, async () => {\n _ensureFetchPatch();\n await renderFn();\n });\n },\n scheduleBackgroundRegeneration: __triggerBackgroundRegeneration,\n setNavigationContext,\n });\n if (__cachedRouteResponse) {\n return __cachedRouteResponse;\n }\n }\n\n if (typeof handlerFn === \"function\") {\n return __executeAppRouteHandler({\n basePath: __basePath,\n buildPageCacheTags: __pageCacheTags,\n cleanPathname,\n clearRequestContext: function() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n consumeDynamicUsage,\n executionContext: _getRequestExecutionContext(),\n getAndClearPendingCookies,\n getCollectedFetchTags,\n getDraftModeCookieHeader,\n handler,\n handlerFn,\n i18n: __i18nConfig,\n isAutoHead,\n isProduction: process.env.NODE_ENV === \"production\",\n isrDebug: __isrDebug,\n isrRouteKey: __isrRouteKey,\n isrSet: __isrSet,\n markDynamicUsage,\n method,\n middlewareContext: _mwCtx,\n params: makeThenableParams(params),\n reportRequestError: _reportRequestError,\n request,\n revalidateSeconds,\n routePattern: route.pattern,\n setHeadersAccessPhase,\n });\n }\n setHeadersContext(null);\n setNavigationContext(null);\n return __applyRouteHandlerMiddlewareContext(\n new Response(null, {\n status: 405,\n }),\n _mwCtx,\n );\n }\n\n // Build the component tree: layouts wrapping the page\n const PageComponent = route.page?.default;\n if (!PageComponent) {\n setHeadersContext(null);\n setNavigationContext(null);\n return new Response(\"Page has no default export\", { status: 500 });\n }\n\n // Read route segment config from page module exports\n let revalidateSeconds = typeof route.page?.revalidate === \"number\" ? route.page.revalidate : null;\n const dynamicConfig = route.page?.dynamic; // 'auto' | 'force-dynamic' | 'force-static' | 'error'\n const dynamicParamsConfig = route.page?.dynamicParams; // true (default) | false\n const isForceStatic = dynamicConfig === \"force-static\";\n const isDynamicError = dynamicConfig === \"error\";\n\n // force-static: replace headers/cookies context with empty values and\n // clear searchParams so dynamic APIs return defaults instead of real data\n if (isForceStatic) {\n setHeadersContext({ headers: new Headers(), cookies: new Map() });\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: new URLSearchParams(),\n params,\n });\n }\n\n // dynamic = 'error': install an access error so request APIs fail with the\n // static-generation message even for legacy sync property access.\n if (isDynamicError) {\n const errorMsg = 'Page with \\`dynamic = \"error\"\\` used a dynamic API. ' +\n 'This page was expected to be fully static, but headers(), cookies(), ' +\n 'or searchParams was accessed. Remove the dynamic API usage or change ' +\n 'the dynamic config to \"auto\" or \"force-dynamic\".';\n setHeadersContext({\n headers: new Headers(),\n cookies: new Map(),\n accessError: new Error(errorMsg),\n });\n setNavigationContext({\n pathname: cleanPathname,\n searchParams: new URLSearchParams(),\n params,\n });\n }\n\n // force-dynamic: set no-store Cache-Control\n const isForceDynamic = dynamicConfig === \"force-dynamic\";\n\n // ── ISR cache read (production only) ─────────────────────────────────────\n // Read from cache BEFORE generateStaticParams and all rendering work.\n // This is the critical performance optimization: on a cache hit we skip\n // ALL expensive work (generateStaticParams, buildPageElement, layout probe,\n // page probe, renderToReadableStream, SSR). Both HTML and RSC requests\n // (client-side navigation / prefetch) are served from cache.\n //\n // HTML and RSC are stored under separate keys (matching Next.js's .html/.rsc\n // file layout) so each request type reads and writes independently — no races,\n // no partial-entry sentinels, no read-before-write hacks needed.\n //\n // force-static and dynamic='error' are compatible with ISR — they control\n // how dynamic APIs behave during rendering, not whether results are cached.\n // Only force-dynamic truly bypasses the ISR cache.\n if (\n process.env.NODE_ENV === \"production\" &&\n !isForceDynamic &&\n revalidateSeconds !== null && revalidateSeconds > 0 && revalidateSeconds !== Infinity\n ) {\n const __cachedPageResponse = await __readAppPageCacheResponse({\n cleanPathname,\n clearRequestContext: function() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n isRscRequest,\n isrDebug: __isrDebug,\n isrGet: __isrGet,\n isrHtmlKey: __isrHtmlKey,\n isrRscKey: __isrRscKey,\n isrSet: __isrSet,\n revalidateSeconds,\n renderFreshPageForCache: async function() {\n // Re-render the page to produce fresh HTML + RSC data for the cache\n // Use an empty headers context for background regeneration — not the original\n // user request — to prevent user-specific cookies/auth headers from leaking\n // into content that is cached and served to all subsequent users.\n const __revalHeadCtx = { headers: new Headers(), cookies: new Map() };\n const __revalUCtx = _createUnifiedCtx({\n headersContext: __revalHeadCtx,\n executionContext: _getRequestExecutionContext(),\n });\n return _runWithUnifiedCtx(__revalUCtx, async () => {\n _ensureFetchPatch();\n setNavigationContext({ pathname: cleanPathname, searchParams: new URLSearchParams(), params });\n const __revalElement = await buildPageElement(route, params, undefined, new URLSearchParams());\n const __revalOnError = createRscOnErrorHandler(request, cleanPathname, route.pattern);\n const __revalRscStream = renderToReadableStream(__revalElement, { onError: __revalOnError });\n const __revalRscCapture = __teeAppPageRscStreamForCapture(__revalRscStream, true);\n const __revalFontData = { links: _getSSRFontLinks(), styles: _getSSRFontStyles(), preloads: _getSSRFontPreloads() };\n const __revalSsrEntry = await import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n const __revalHtmlStream = await __revalSsrEntry.handleSsr(\n __revalRscCapture.responseStream,\n _getNavigationContext(),\n __revalFontData,\n );\n setHeadersContext(null);\n setNavigationContext(null);\n const __freshHtml = await __readAppPageTextStream(__revalHtmlStream);\n const __freshRscData = await __revalRscCapture.capturedRscDataPromise;\n const __pageTags = __pageCacheTags(cleanPathname, getCollectedFetchTags());\n return { html: __freshHtml, rscData: __freshRscData, tags: __pageTags };\n });\n },\n scheduleBackgroundRegeneration: __triggerBackgroundRegeneration,\n });\n if (__cachedPageResponse) {\n return __cachedPageResponse;\n }\n }\n\n // dynamicParams = false: only params from generateStaticParams are allowed.\n // This runs AFTER the ISR cache read so that a cache hit skips this work entirely.\n const __dynamicParamsResponse = await __validateAppPageDynamicParams({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n enforceStaticParamsOnly: dynamicParamsConfig === false,\n generateStaticParams: route.page?.generateStaticParams,\n isDynamicRoute: route.isDynamic,\n logGenerateStaticParamsError(err) {\n console.error(\"[vinext] generateStaticParams error:\", err);\n },\n params,\n });\n if (__dynamicParamsResponse) {\n return __dynamicParamsResponse;\n }\n\n // Check for intercepting routes on RSC requests (client-side navigation).\n // If the target URL matches an intercepting route in a parallel slot,\n // render the source route with the intercepting page in the slot.\n const __interceptResult = await __resolveAppPageIntercept({\n buildPageElement,\n cleanPathname,\n currentRoute: route,\n findIntercept,\n getRoutePattern(sourceRoute) {\n return sourceRoute.pattern;\n },\n getSourceRoute(sourceRouteIndex) {\n return routes[sourceRouteIndex];\n },\n isRscRequest,\n matchSourceRouteParams(pattern) {\n // Extract actual URL param values by prefix-matching the request pathname\n // against the source route's pattern. This handles all interception conventions:\n // (.) same-level, (..) one-level-up, and (...) root — the source pattern's\n // dynamic segments that align with the URL get their real values extracted.\n // We must NOT use matchRoute(pattern) here: the trie would match the literal\n // \":param\" strings as dynamic segment values, returning e.g. {id: \":id\"}.\n const patternParts = pattern.split(\"/\").filter(Boolean);\n const urlParts = cleanPathname.split(\"/\").filter(Boolean);\n const params = Object.create(null);\n for (let i = 0; i < patternParts.length; i++) {\n const pp = patternParts[i];\n if (pp.endsWith(\"+\") || pp.endsWith(\"*\")) {\n // urlParts.slice(i) safely returns [] when i >= urlParts.length,\n // which is the correct value for optional catch-all with zero segments.\n params[pp.slice(1, -1)] = urlParts.slice(i);\n break;\n }\n if (i >= urlParts.length) break;\n if (pp.startsWith(\":\")) {\n params[pp.slice(1)] = urlParts[i];\n } else if (pp !== urlParts[i]) {\n break;\n }\n }\n return params;\n },\n renderInterceptResponse(sourceRoute, interceptElement) {\n const interceptOnError = createRscOnErrorHandler(\n request,\n cleanPathname,\n sourceRoute.pattern,\n );\n const interceptStream = renderToReadableStream(interceptElement, {\n onError: interceptOnError,\n });\n // Do NOT clear headers/navigation context here — the RSC stream is consumed lazily\n // by the client, and async server components that run during consumption need the\n // context to still be live. The AsyncLocalStorage scope from runWithRequestContext\n // handles cleanup naturally when all async continuations complete.\n const interceptHeaders = new Headers({ \"Content-Type\": \"text/x-component; charset=utf-8\", \"Vary\": \"RSC, Accept\" });\n __mergeMiddlewareResponseHeaders(interceptHeaders, _mwCtx.headers);\n return new Response(interceptStream, {\n status: _mwCtx.status ?? 200,\n headers: interceptHeaders,\n });\n },\n searchParams: url.searchParams,\n setNavigationContext,\n toInterceptOpts(intercept) {\n return {\n interceptSlot: intercept.slotName,\n interceptPage: intercept.page,\n interceptParams: intercept.matchedParams,\n };\n },\n });\n if (__interceptResult.response) {\n return __interceptResult.response;\n }\n const interceptOpts = __interceptResult.interceptOpts;\n\n const __pageBuildResult = await __buildAppPageElement({\n buildPageElement() {\n return buildPageElement(route, params, interceptOpts, url.searchParams);\n },\n renderErrorBoundaryPage(buildErr) {\n return renderErrorBoundaryPage(route, buildErr, isRscRequest, request, params);\n },\n renderSpecialError(__buildSpecialError) {\n return __buildAppPageSpecialErrorResponse({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n renderFallbackPage(statusCode) {\n return renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, {\n matchedParams: params,\n });\n },\n requestUrl: request.url,\n specialError: __buildSpecialError,\n });\n },\n resolveSpecialError: __resolveAppPageSpecialError,\n });\n if (__pageBuildResult.response) {\n return __pageBuildResult.response;\n }\n const element = __pageBuildResult.element;\n\n // Note: CSS is automatically injected by @vitejs/plugin-rsc's\n // rscCssTransform — no manual loadCss() call needed.\n const _hasLoadingBoundary = !!(route.loading && route.loading.default);\n const _asyncLayoutParams = makeThenableParams(params);\n // Convert URLSearchParams to a plain object then wrap in makeThenableParams()\n // so probePage() passes the same shape that buildPageElement() gives to the\n // real render. Without this, pages that destructure await-ed searchParams\n // throw TypeError during probe.\n const _probeSearchObj = {};\n url.searchParams.forEach(function(v, k) {\n if (k in _probeSearchObj) {\n _probeSearchObj[k] = Array.isArray(_probeSearchObj[k]) ? _probeSearchObj[k].concat(v) : [_probeSearchObj[k], v];\n } else {\n _probeSearchObj[k] = v;\n }\n });\n const _asyncSearchParams = makeThenableParams(_probeSearchObj);\n return __renderAppPageLifecycle({\n cleanPathname,\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n consumeDynamicUsage,\n createRscOnErrorHandler(pathname, routePath) {\n return createRscOnErrorHandler(request, pathname, routePath);\n },\n element,\n getDraftModeCookieHeader,\n getFontLinks: _getSSRFontLinks,\n getFontPreloads: _getSSRFontPreloads,\n getFontStyles: _getSSRFontStyles,\n getNavigationContext: _getNavigationContext,\n getPageTags() {\n return __pageCacheTags(cleanPathname, getCollectedFetchTags());\n },\n getRequestCacheLife() {\n return _consumeRequestScopedCacheLife();\n },\n handlerStart: __reqStart,\n hasLoadingBoundary: _hasLoadingBoundary,\n isDynamicError,\n isForceDynamic,\n isForceStatic,\n isProduction: process.env.NODE_ENV === \"production\",\n isRscRequest,\n isrDebug: __isrDebug,\n isrHtmlKey: __isrHtmlKey,\n isrRscKey: __isrRscKey,\n isrSet: __isrSet,\n layoutCount: route.layouts?.length ?? 0,\n loadSsrHandler() {\n return import.meta.viteRsc.loadModule(\"ssr\", \"index\");\n },\n middlewareContext: _mwCtx,\n params,\n probeLayoutAt(li) {\n const LayoutComp = route.layouts[li]?.default;\n if (!LayoutComp) return null;\n return LayoutComp({ params: _asyncLayoutParams, children: null });\n },\n probePage() {\n return PageComponent({ params: _asyncLayoutParams, searchParams: _asyncSearchParams });\n },\n revalidateSeconds,\n renderErrorBoundaryResponse(renderErr) {\n return renderErrorBoundaryPage(route, renderErr, isRscRequest, request, params);\n },\n async renderLayoutSpecialError(__layoutSpecialError, li) {\n return __buildAppPageSpecialErrorResponse({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n renderFallbackPage(statusCode) {\n // Find the not-found component from the parent level (the boundary that\n // would catch this in Next.js). Walk up from the throwing layout to find\n // the nearest not-found at a parent layout's directory.\n let parentNotFound = null;\n if (route.notFounds) {\n for (let pi = li - 1; pi >= 0; pi--) {\n if (route.notFounds[pi]?.default) {\n parentNotFound = route.notFounds[pi].default;\n break;\n }\n }\n }\n if (!parentNotFound) parentNotFound = ${rootNotFoundVar ? `${rootNotFoundVar}?.default` : \"null\"};\n const parentLayouts = route.layouts.slice(0, li);\n return renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, {\n boundaryComponent: parentNotFound,\n layouts: parentLayouts,\n matchedParams: params,\n });\n },\n requestUrl: request.url,\n specialError: __layoutSpecialError,\n });\n },\n async renderPageSpecialError(specialError) {\n return __buildAppPageSpecialErrorResponse({\n clearRequestContext() {\n setHeadersContext(null);\n setNavigationContext(null);\n },\n renderFallbackPage(statusCode) {\n return renderHTTPAccessFallbackPage(route, statusCode, isRscRequest, request, {\n matchedParams: params,\n });\n },\n requestUrl: request.url,\n specialError,\n });\n },\n renderToReadableStream,\n routeHasLocalBoundary: !!(route?.error?.default) || !!(route?.errors && route.errors.some(function(e) { return e?.default; })),\n routePattern: route.pattern,\n runWithSuppressedHookWarning(probe) {\n // Run inside ALS context so the module-level console.error patch suppresses\n // \"Invalid hook call\" only for this request's probe — concurrent requests\n // each have their own ALS store and are unaffected.\n return _suppressHookWarningAls.run(true, probe);\n },\n waitUntil(__cachePromise) {\n _getRequestExecutionContext()?.waitUntil(__cachePromise);\n },\n });\n}\n\nif (import.meta.hot) {\n import.meta.hot.accept();\n}\n`;\n}\n"],"mappings":"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"}