@wular/pnext 0.0.1

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 (371) hide show
  1. package/README.md +153 -0
  2. package/bin/pnext +67 -0
  3. package/config/lint/base.js +48 -0
  4. package/config/ts/base.json +26 -0
  5. package/config/ts/react.json +13 -0
  6. package/package.json +70 -0
  7. package/reference/compat.md +63 -0
  8. package/reference/config.md +120 -0
  9. package/reference/css.md +58 -0
  10. package/reference/dev.md +69 -0
  11. package/reference/env.md +40 -0
  12. package/reference/metadata.md +86 -0
  13. package/reference/navigation.md +149 -0
  14. package/reference/overview.md +35 -0
  15. package/reference/performance.md +97 -0
  16. package/reference/rendering.md +127 -0
  17. package/reference/routing.md +167 -0
  18. package/reference/typegen.md +64 -0
  19. package/src/api/cache.ts +80 -0
  20. package/src/api/client-cache.ts +9 -0
  21. package/src/api/client-navigation.ts +279 -0
  22. package/src/api/dynamic.tsx +102 -0
  23. package/src/api/link.tsx +119 -0
  24. package/src/api/navigation.ts +198 -0
  25. package/src/api/router/events.ts +53 -0
  26. package/src/api/router/history.ts +70 -0
  27. package/src/api/router/hub.ts +194 -0
  28. package/src/api/router/policies.ts +107 -0
  29. package/src/api/router/runtime.ts +5238 -0
  30. package/src/api/router/types.ts +299 -0
  31. package/src/api/router.ts +167 -0
  32. package/src/api/server.ts +323 -0
  33. package/src/api/suspense.ts +16 -0
  34. package/src/cache/context.ts +61 -0
  35. package/src/cli/adapters/vercel-warm.ts +375 -0
  36. package/src/cli/adapters/vercel.ts +1310 -0
  37. package/src/cli/analyze-print.ts +181 -0
  38. package/src/cli/analyze.ts +328 -0
  39. package/src/cli/boot-trace.ts +29 -0
  40. package/src/cli/build.ts +3114 -0
  41. package/src/cli/dev.ts +276 -0
  42. package/src/cli/index.ts +196 -0
  43. package/src/cli/named-bin.ts +119 -0
  44. package/src/cli/serve-ui.ts +160 -0
  45. package/src/cli/start.ts +1425 -0
  46. package/src/client/build.ts +2136 -0
  47. package/src/client/chunk-fold.ts +526 -0
  48. package/src/client/entry.ts +1525 -0
  49. package/src/client/paths.ts +22 -0
  50. package/src/client/prebuilt.ts +621 -0
  51. package/src/client/profile.ts +75 -0
  52. package/src/client/react-compiler.ts +94 -0
  53. package/src/client/reference-stub.ts +145 -0
  54. package/src/client/reference.ts +47 -0
  55. package/src/compat/actions/action-client.ts +531 -0
  56. package/src/compat/actions/action-dispatch.ts +676 -0
  57. package/src/compat/actions/action-router.ts +40 -0
  58. package/src/compat/actions/action-shared.ts +95 -0
  59. package/src/compat/actions/client-plugin.ts +135 -0
  60. package/src/compat/actions/client-stub.ts +65 -0
  61. package/src/compat/actions/config.ts +164 -0
  62. package/src/compat/actions/detect.ts +208 -0
  63. package/src/compat/actions/discovery.ts +244 -0
  64. package/src/compat/actions/early-submit.ts +40 -0
  65. package/src/compat/actions/endpoint.ts +602 -0
  66. package/src/compat/actions/flight.ts +52 -0
  67. package/src/compat/actions/form-state.ts +73 -0
  68. package/src/compat/actions/hoist.ts +485 -0
  69. package/src/compat/actions/ids.ts +39 -0
  70. package/src/compat/actions/index.ts +41 -0
  71. package/src/compat/actions/instances.ts +144 -0
  72. package/src/compat/actions/origin.ts +109 -0
  73. package/src/compat/actions/protocol.ts +125 -0
  74. package/src/compat/actions/registry.ts +74 -0
  75. package/src/compat/actions/rewrite.ts +282 -0
  76. package/src/compat/actions/serve.ts +414 -0
  77. package/src/compat/actions/server-tag.ts +21 -0
  78. package/src/compat/actions/unrecognized-error.ts +30 -0
  79. package/src/compat/adapter/build-complete.ts +257 -0
  80. package/src/compat/bundler/bun-externals.ts +53 -0
  81. package/src/compat/bundler/cjs-exports.ts +542 -0
  82. package/src/compat/bundler/config.ts +363 -0
  83. package/src/compat/bundler/externals.ts +34 -0
  84. package/src/compat/bundler/import-meta-url.ts +60 -0
  85. package/src/compat/bundler/modularize-imports.ts +119 -0
  86. package/src/compat/bundler/new-url-asset.ts +87 -0
  87. package/src/compat/bundler/optimize-package-imports.ts +273 -0
  88. package/src/compat/bundler/polyfill.ts +88 -0
  89. package/src/compat/bundler/react-compiler.ts +61 -0
  90. package/src/compat/bundler/react-profiler.tsx +25 -0
  91. package/src/compat/bundler/relay-transform.ts +116 -0
  92. package/src/compat/bundler/require-context.ts +281 -0
  93. package/src/compat/bundler/resolve-extensions.ts +75 -0
  94. package/src/compat/bundler/source-cache.ts +61 -0
  95. package/src/compat/bundler/static-imports.ts +25 -0
  96. package/src/compat/bundler/symlink-imports.ts +119 -0
  97. package/src/compat/bundler/tsconfig-paths.ts +50 -0
  98. package/src/compat/bundler/wasm.ts +153 -0
  99. package/src/compat/bundler/webpack-loaders.ts +685 -0
  100. package/src/compat/bundler/worker.ts +278 -0
  101. package/src/compat/cache/build-flags.ts +81 -0
  102. package/src/compat/cache/build-prerender-errors.ts +163 -0
  103. package/src/compat/cache/custom-handler.ts +159 -0
  104. package/src/compat/cache/fetch-patch.ts +745 -0
  105. package/src/compat/cache/handler.ts +100 -0
  106. package/src/compat/cache/modern-handler.ts +275 -0
  107. package/src/compat/cache/resume-data-cache.ts +143 -0
  108. package/src/compat/cache/revalidate.ts +759 -0
  109. package/src/compat/cache/runtime-error.ts +124 -0
  110. package/src/compat/cache/use-cache-transform.ts +961 -0
  111. package/src/compat/cache/use-cache.ts +1695 -0
  112. package/src/compat/cache-control.ts +269 -0
  113. package/src/compat/client/base-path.ts +64 -0
  114. package/src/compat/client/css-order.ts +36 -0
  115. package/src/compat/client/errors/control-flow.ts +92 -0
  116. package/src/compat/client/errors/error-boundary.ts +222 -0
  117. package/src/compat/client/errors/global-error.ts +238 -0
  118. package/src/compat/client/errors/install.ts +217 -0
  119. package/src/compat/client/errors/lazy.ts +53 -0
  120. package/src/compat/client/errors/primitive-throw.ts +126 -0
  121. package/src/compat/client/errors/soft-refresh.ts +14 -0
  122. package/src/compat/client/link-status.ts +86 -0
  123. package/src/compat/client/nav-compat-runtime.ts +57 -0
  124. package/src/compat/client/nav-compat.ts +42 -0
  125. package/src/compat/client/navigation-scroll.ts +154 -0
  126. package/src/compat/client/optimistic-routing.ts +206 -0
  127. package/src/compat/client/prefetch-cache.ts +111 -0
  128. package/src/compat/client/route-announcer.ts +72 -0
  129. package/src/compat/client/segment-cache-policy.ts +159 -0
  130. package/src/compat/client/segment-cache.ts +1077 -0
  131. package/src/compat/client/segment-prefetch.ts +375 -0
  132. package/src/compat/client/trailing-slash.ts +24 -0
  133. package/src/compat/css/chunking.ts +254 -0
  134. package/src/compat/css/inline-css.ts +73 -0
  135. package/src/compat/css/lightningcss.ts +90 -0
  136. package/src/compat/css/modules.ts +373 -0
  137. package/src/compat/css/nonce.ts +30 -0
  138. package/src/compat/css/sass-plugin.ts +65 -0
  139. package/src/compat/css/sass.ts +392 -0
  140. package/src/compat/css/styled-jsx-runtime.ts +80 -0
  141. package/src/compat/css/styled-jsx.ts +49 -0
  142. package/src/compat/edge-runtime.ts +71 -0
  143. package/src/compat/export/client.ts +112 -0
  144. package/src/compat/export/index.ts +272 -0
  145. package/src/compat/export/standalone.ts +207 -0
  146. package/src/compat/image-optimizer/cache.ts +119 -0
  147. package/src/compat/image-optimizer/detect.ts +143 -0
  148. package/src/compat/image-optimizer/index.ts +601 -0
  149. package/src/compat/image-optimizer/source.ts +243 -0
  150. package/src/compat/index.ts +458 -0
  151. package/src/compat/lifecycle/after-scope.ts +86 -0
  152. package/src/compat/lifecycle/after.ts +173 -0
  153. package/src/compat/lifecycle/error-funnel.ts +306 -0
  154. package/src/compat/lifecycle/error-serialize.ts +87 -0
  155. package/src/compat/lifecycle/error-ui.ts +167 -0
  156. package/src/compat/lifecycle/instrumentation-client.ts +138 -0
  157. package/src/compat/lifecycle/instrumentation.ts +277 -0
  158. package/src/compat/lifecycle/node-console.ts +19 -0
  159. package/src/compat/lifecycle/testmode.ts +263 -0
  160. package/src/compat/mdx/compile.ts +219 -0
  161. package/src/compat/mdx/next-mdx-stub.ts +46 -0
  162. package/src/compat/mdx/plugin.ts +37 -0
  163. package/src/compat/metadata-route-artifacts.ts +458 -0
  164. package/src/compat/metadata.ts +295 -0
  165. package/src/compat/middleware/manifest.ts +210 -0
  166. package/src/compat/misc/action-return.ts +173 -0
  167. package/src/compat/next/cache.ts +211 -0
  168. package/src/compat/next/canonical-url.ts +35 -0
  169. package/src/compat/next/client-cache.ts +57 -0
  170. package/src/compat/next/client-navigation.ts +313 -0
  171. package/src/compat/next/client-only.ts +3 -0
  172. package/src/compat/next/client-script.tsx +215 -0
  173. package/src/compat/next/client-server.ts +39 -0
  174. package/src/compat/next/config-loader.ts +569 -0
  175. package/src/compat/next/config.ts +29 -0
  176. package/src/compat/next/constants.cjs +6 -0
  177. package/src/compat/next/constants.ts +6 -0
  178. package/src/compat/next/custom-server.ts +236 -0
  179. package/src/compat/next/dist/client/components/app-router-headers.ts +32 -0
  180. package/src/compat/next/dist/server/app-render/work-unit-async-storage.external.cjs +38 -0
  181. package/src/compat/next/dist/server/web/spec-extension/revalidate.ts +1 -0
  182. package/src/compat/next/dist/server/web/spec-extension/unstable-cache.ts +1 -0
  183. package/src/compat/next/dist/server/web/spec-extension/unstable-no-store.ts +1 -0
  184. package/src/compat/next/dynamic.tsx +46 -0
  185. package/src/compat/next/error.tsx +148 -0
  186. package/src/compat/next/font/cache.ts +171 -0
  187. package/src/compat/next/font/google.ts +2 -0
  188. package/src/compat/next/font/index.ts +8 -0
  189. package/src/compat/next/font/local.ts +5 -0
  190. package/src/compat/next/font/runtime-client.ts +71 -0
  191. package/src/compat/next/font/runtime.ts +974 -0
  192. package/src/compat/next/font/shared.ts +281 -0
  193. package/src/compat/next/form.tsx +156 -0
  194. package/src/compat/next/head.tsx +10 -0
  195. package/src/compat/next/headers.ts +247 -0
  196. package/src/compat/next/image/config.ts +196 -0
  197. package/src/compat/next/image/optimizer.ts +96 -0
  198. package/src/compat/next/image/patterns.ts +103 -0
  199. package/src/compat/next/image/shared.ts +141 -0
  200. package/src/compat/next/image/static-metadata.ts +283 -0
  201. package/src/compat/next/image/validate.ts +269 -0
  202. package/src/compat/next/image-client.tsx +215 -0
  203. package/src/compat/next/image-props.ts +575 -0
  204. package/src/compat/next/image-usage.ts +102 -0
  205. package/src/compat/next/image.tsx +56 -0
  206. package/src/compat/next/index.ts +1 -0
  207. package/src/compat/next/legacy-image.tsx +97 -0
  208. package/src/compat/next/link-usage.ts +29 -0
  209. package/src/compat/next/link-validation-transform.ts +200 -0
  210. package/src/compat/next/link.tsx +466 -0
  211. package/src/compat/next/navigation.cjs +21 -0
  212. package/src/compat/next/navigation.ts +188 -0
  213. package/src/compat/next/offline.ts +51 -0
  214. package/src/compat/next/og.ts +324 -0
  215. package/src/compat/next/optimistic-route-state.ts +188 -0
  216. package/src/compat/next/preferred-region.ts +39 -0
  217. package/src/compat/next/redirects.ts +131 -0
  218. package/src/compat/next/resource-hints.ts +136 -0
  219. package/src/compat/next/rewrites.ts +350 -0
  220. package/src/compat/next/root-params.ts +142 -0
  221. package/src/compat/next/router.cjs +49 -0
  222. package/src/compat/next/router.ts +143 -0
  223. package/src/compat/next/script.tsx +355 -0
  224. package/src/compat/next/server-only.ts +3 -0
  225. package/src/compat/next/server.ts +28 -0
  226. package/src/compat/next/svgr.ts +58 -0
  227. package/src/compat/next/telemetry.ts +77 -0
  228. package/src/compat/next/user-agent.ts +100 -0
  229. package/src/compat/next/web-vitals.ts +56 -0
  230. package/src/compat/otel/api.ts +95 -0
  231. package/src/compat/otel/client-trace-metadata.ts +71 -0
  232. package/src/compat/otel/fetch-span.ts +77 -0
  233. package/src/compat/otel/tracer.ts +944 -0
  234. package/src/compat/pages/client-plugin.ts +108 -0
  235. package/src/compat/pages/index.ts +527 -0
  236. package/src/compat/pages/router-state.ts +94 -0
  237. package/src/compat/ppr/io.ts +38 -0
  238. package/src/compat/ppr/missing-root-params.ts +105 -0
  239. package/src/compat/ppr/root-params-scan.ts +164 -0
  240. package/src/compat/ppr/root-params-transform.ts +75 -0
  241. package/src/compat/ppr/root-params.ts +129 -0
  242. package/src/compat/ppr/segment-config-incompat.ts +34 -0
  243. package/src/compat/protocol.ts +202 -0
  244. package/src/compat/react/client.ts +59 -0
  245. package/src/compat/react/compiler-runtime.ts +60 -0
  246. package/src/compat/react/dom-client.ts +115 -0
  247. package/src/compat/react/dom-react-server.ts +20 -0
  248. package/src/compat/react/dom-server.ts +40 -0
  249. package/src/compat/react/dom.ts +154 -0
  250. package/src/compat/react/preact.ts +522 -0
  251. package/src/compat/react/react-server.ts +84 -0
  252. package/src/compat/react/router-shim.ts +26 -0
  253. package/src/compat/react/server-component-use.ts +48 -0
  254. package/src/compat/react/server-inserted-html.ts +87 -0
  255. package/src/compat/react/server.ts +156 -0
  256. package/src/compat/react/view-transition.ts +60 -0
  257. package/src/compat/register/actions.ts +875 -0
  258. package/src/compat/register/boot.ts +141 -0
  259. package/src/compat/register/build-tier.ts +11 -0
  260. package/src/compat/register/build.ts +182 -0
  261. package/src/compat/register/bundler.ts +587 -0
  262. package/src/compat/register/cache.ts +85 -0
  263. package/src/compat/register/client-errors.ts +18 -0
  264. package/src/compat/register/config.ts +17 -0
  265. package/src/compat/register/css-extras.ts +120 -0
  266. package/src/compat/register/edge-runtime.ts +6 -0
  267. package/src/compat/register/errors.ts +46 -0
  268. package/src/compat/register/export.ts +23 -0
  269. package/src/compat/register/font.ts +36 -0
  270. package/src/compat/register/hooks.ts +34 -0
  271. package/src/compat/register/image.ts +133 -0
  272. package/src/compat/register/index.ts +111 -0
  273. package/src/compat/register/instrumentation-client.ts +35 -0
  274. package/src/compat/register/lifecycle.ts +86 -0
  275. package/src/compat/register/mdx.ts +48 -0
  276. package/src/compat/register/middleware.ts +36 -0
  277. package/src/compat/register/misc.ts +44 -0
  278. package/src/compat/register/otel.ts +288 -0
  279. package/src/compat/register/pages-api.ts +473 -0
  280. package/src/compat/register/ppr.ts +56 -0
  281. package/src/compat/register/protocol.ts +57 -0
  282. package/src/compat/register/proxy.ts +127 -0
  283. package/src/compat/register/render.ts +268 -0
  284. package/src/compat/register/routing.ts +410 -0
  285. package/src/compat/register/segment.ts +1903 -0
  286. package/src/compat/register/static-image.ts +21 -0
  287. package/src/compat/register/typed-routes.ts +35 -0
  288. package/src/compat/register/usecache.ts +131 -0
  289. package/src/compat/register/validation.ts +56 -0
  290. package/src/compat/segment/loading-boundary.ts +113 -0
  291. package/src/compat/segment/page-slot.ts +200 -0
  292. package/src/compat/segment/tree.ts +481 -0
  293. package/src/compat/segment/vary-key.ts +102 -0
  294. package/src/compat/segment/vary-params.ts +551 -0
  295. package/src/compat/static-params.ts +33 -0
  296. package/src/compat/tsconfig-defaults.ts +301 -0
  297. package/src/compat/typecheck/index.ts +1481 -0
  298. package/src/compat/typecheck/worker.ts +26 -0
  299. package/src/compat/typed-routes/index.ts +92 -0
  300. package/src/compat/typed-routes/manifest.ts +356 -0
  301. package/src/compat/typed-routes/typegen.ts +566 -0
  302. package/src/compat/validation/errors.ts +159 -0
  303. package/src/compat/validation/index.ts +1770 -0
  304. package/src/compat/validation/prerender-diagnostics.ts +1508 -0
  305. package/src/compat-bootstrap.ts +67 -0
  306. package/src/config.ts +218 -0
  307. package/src/css/build.ts +697 -0
  308. package/src/css/index.ts +2 -0
  309. package/src/css/postcss.ts +236 -0
  310. package/src/css/worker.ts +34 -0
  311. package/src/dev/client-actions.ts +35 -0
  312. package/src/dev/client-chunk-store.ts +92 -0
  313. package/src/dev/client-key-cache.ts +178 -0
  314. package/src/dev/global-css-cache.ts +212 -0
  315. package/src/dev/imports.ts +2430 -0
  316. package/src/dev/module-cache.ts +721 -0
  317. package/src/dev/module-generations.ts +38 -0
  318. package/src/dev/module-transform.ts +188 -0
  319. package/src/dev/node-module-bundle-cache.ts +63 -0
  320. package/src/dev/restart-cache.ts +10 -0
  321. package/src/dev/route-bundle-key-cache.ts +154 -0
  322. package/src/dev/route-facts-cache.ts +223 -0
  323. package/src/dev/server.ts +1710 -0
  324. package/src/dynamic/source.ts +307 -0
  325. package/src/dynamic/tree-shake.ts +262 -0
  326. package/src/env.ts +92 -0
  327. package/src/extensions.ts +1898 -0
  328. package/src/index.ts +34 -0
  329. package/src/internal.ts +43 -0
  330. package/src/islands/boundary-error.ts +8 -0
  331. package/src/islands/static-children.ts +37 -0
  332. package/src/islands/static-slots.ts +106 -0
  333. package/src/ppr-postpone.ts +24 -0
  334. package/src/ppr.ts +784 -0
  335. package/src/proxy.ts +752 -0
  336. package/src/render/hooks.ts +384 -0
  337. package/src/render/index.ts +1 -0
  338. package/src/render/island-context.ts +47 -0
  339. package/src/render/metadata.ts +857 -0
  340. package/src/render/renderer.ts +7391 -0
  341. package/src/render/resource-hints.ts +44 -0
  342. package/src/render/slots.tsx +679 -0
  343. package/src/request/context.ts +396 -0
  344. package/src/resolve/engine.ts +219 -0
  345. package/src/resolve/imports.ts +1104 -0
  346. package/src/resolve/scan-facts.ts +474 -0
  347. package/src/resolve/source-text.ts +86 -0
  348. package/src/routing/forwarded.ts +41 -0
  349. package/src/routing/handler.ts +271 -0
  350. package/src/routing/href.ts +203 -0
  351. package/src/routing/metadata.ts +1018 -0
  352. package/src/routing/request-runtime.ts +43 -0
  353. package/src/routing/routes.ts +2560 -0
  354. package/src/routing/slots.ts +432 -0
  355. package/src/runtime/server.ts +3453 -0
  356. package/src/runtime/vendor.ts +1160 -0
  357. package/src/style-modules.d.ts +9 -0
  358. package/src/typegen.ts +151 -0
  359. package/src/types.ts +725 -0
  360. package/src/utils/ansi.ts +9 -0
  361. package/src/utils/content-type.ts +31 -0
  362. package/src/utils/decode.ts +7 -0
  363. package/src/utils/dev-profile.ts +31 -0
  364. package/src/utils/error-log.ts +29 -0
  365. package/src/utils/fs-cache.ts +31 -0
  366. package/src/utils/fs.ts +119 -0
  367. package/src/utils/html.ts +46 -0
  368. package/src/utils/serialize.ts +378 -0
  369. package/src/utils/source.ts +35 -0
  370. package/src/utils/verbose.ts +39 -0
  371. package/tsconfig.json +10 -0
@@ -0,0 +1,127 @@
1
+ import path from 'node:path';
2
+ import { type ResolvedConfig } from '../../config';
3
+ import { setProxyExtensions, setProxyResponseProtocol } from '../../extensions';
4
+ import { findProxyFiles, setProxyRewriteObserver } from '../../proxy';
5
+ import { moduleExportNames } from '../../resolve/scan-facts';
6
+ import { readText, toPosixPath } from '../../utils/fs';
7
+ import { recordRewrite } from '../protocol';
8
+ import { recordCanonicalUrl } from '../next/canonical-url';
9
+ import { getNextConfig } from '../next/config-loader';
10
+ import { activateTestProxy } from '../lifecycle/testmode';
11
+
12
+ export function registerProxyExtensions(_config: ResolvedConfig): void {
13
+ setProxyResponseProtocol({
14
+ nextHeader: 'x-middleware-next',
15
+ rewriteHeader: 'x-middleware-rewrite',
16
+ });
17
+ setProxyExtensions({
18
+ names: ['proxy', 'middleware'],
19
+ validateFiles: validateNextProxyFiles,
20
+ handlerExport: module => module.proxy ?? module.default ?? module.middleware,
21
+ skipUrlNormalize: () => getNextConfig().skipProxyUrlNormalize === true,
22
+ locale: proxyLocale,
23
+ onExternalRewrite: request => activateTestProxy(request.headers),
24
+ clientMaxBodySize: proxyClientMaxBodySize,
25
+ });
26
+ // A same-origin middleware rewrite feeds the Next rewrite-tracking channel so
27
+ // RSC responses carry x-nextjs-rewritten-path/query (identical to next.config
28
+ // rewrites; the RSC-only emission gate lives in compat/protocol.ts). The
29
+ // ORIGINAL url is stashed too so usePathname/useSearchParams stay canonical.
30
+ setProxyRewriteObserver((from, to) => {
31
+ recordCanonicalUrl(from);
32
+ recordRewrite(from, to);
33
+ });
34
+ }
35
+
36
+ const DEFAULT_PROXY_CLIENT_MAX_BODY_SIZE = 10 * 1024 * 1024;
37
+
38
+ // experimental.proxyClientMaxBodySize accepts bytes (2097152) or a size string
39
+ // ('5mb'); experimental.middlewareClientMaxBodySize is the deprecated alias.
40
+ function proxyClientMaxBodySize(): number {
41
+ const experimental = (getNextConfig().experimental ?? {}) as Record<string, unknown>;
42
+ const raw = experimental.proxyClientMaxBodySize ?? experimental.middlewareClientMaxBodySize;
43
+ if (typeof raw === 'number' && raw > 0) return raw;
44
+ if (typeof raw === 'string') {
45
+ const match = /^(\d+(?:\.\d+)?)\s*(b|kb|mb|gb)?$/i.exec(raw.trim());
46
+ if (match?.[1]) {
47
+ const unit = (match[2] ?? 'b').toLowerCase();
48
+ const multiplier =
49
+ unit === 'gb' ? 1024 ** 3 : unit === 'mb' ? 1024 ** 2 : unit === 'kb' ? 1024 : 1;
50
+ const bytes = Math.floor(Number(match[1]) * multiplier);
51
+ if (bytes > 0) return bytes;
52
+ }
53
+ }
54
+ return DEFAULT_PROXY_CLIENT_MAX_BODY_SIZE;
55
+ }
56
+
57
+ function proxyLocale(url: URL): string {
58
+ const i18n = getNextConfig().i18n as { locales?: unknown } | undefined;
59
+ if (!Array.isArray(i18n?.locales)) return '';
60
+ const locales = i18n.locales.filter((locale): locale is string => typeof locale === 'string');
61
+ const dataLocale = /^\/_next\/data\/[^/]+\/([^/]+)(?:\/|$)/.exec(url.pathname)?.[1];
62
+ const candidate = dataLocale ?? url.pathname.split('/')[1];
63
+ return locales.find(locale => locale.toLowerCase() === candidate?.toLowerCase()) ?? '';
64
+ }
65
+
66
+ async function validateNextProxyFiles(config: ResolvedConfig) {
67
+ const files = findProxyFiles(config, ['proxy', 'middleware']);
68
+ const middleware = files.find(file => path.basename(file).startsWith('middleware.'));
69
+ const proxy = files.find(file => path.basename(file).startsWith('proxy.'));
70
+ if (middleware && proxy) {
71
+ throw new Error(
72
+ `Both middleware file "${relativeProxyPath(config, middleware)}" and proxy file "${relativeProxyPath(config, proxy)}" are detected. Please use "${relativeProxyPath(config, proxy)}" only.`,
73
+ );
74
+ }
75
+ if (middleware && !proxy) {
76
+ console.warn(
77
+ 'The "middleware" file convention is deprecated. Please use "proxy" instead.',
78
+ );
79
+ }
80
+ await Promise.all(files.map(file => validateNextProxyFile(config, file)));
81
+ }
82
+
83
+ async function validateNextProxyFile(config: ResolvedConfig, file: string) {
84
+ const source = await readText(file);
85
+ const name = path.basename(file).split('.')[0];
86
+ const exports = moduleExportNames(source, file);
87
+ const validExport =
88
+ exports.includes('default') ||
89
+ (name === 'proxy' ? exports.includes('proxy') : exports.includes('middleware'));
90
+ if (!validExport) {
91
+ throw new Error(proxyMissingExportError(config, file));
92
+ }
93
+ if (name === 'proxy' && hasRuntimeConfig(source)) {
94
+ throw new Error(
95
+ `Route segment config is not allowed in Proxy file at "${relativeProxyPath(config, file)}". Proxy always runs on Node.js runtime. Learn more: https://nextjs.org/docs/messages/middleware-to-proxy`,
96
+ );
97
+ }
98
+ }
99
+
100
+ function proxyMissingExportError(config: ResolvedConfig, file: string) {
101
+ const name = path.basename(file).split('.')[0] === 'middleware' ? 'middleware' : 'proxy';
102
+ const migrationReason =
103
+ name === 'proxy'
104
+ ? "- You are migrating from `middleware` to `proxy`, but haven't updated the exported function.\n"
105
+ : '';
106
+ const target = name === 'proxy' ? 'proxy (previously called middleware)' : 'middleware';
107
+ return `The file "${relativeProxyPath(config, file)}" must export a function, either as a default export or as a named "${name}" export.
108
+ This function is what Next.js runs for every request handled by this ${target}.
109
+
110
+ Why this happens:
111
+ ${migrationReason}- The file exists but doesn't export a function.
112
+ - The export is not a function (e.g., an object or constant).
113
+ - There's a syntax error preventing the export from being recognized.
114
+
115
+ To fix it:
116
+ - Ensure this file has either a default or "${name}" function export.
117
+
118
+ Learn more: https://nextjs.org/docs/messages/middleware-to-proxy`;
119
+ }
120
+
121
+ function hasRuntimeConfig(source: string) {
122
+ return /\bexport\s+const\s+config\s*=/.test(source) && /\bruntime\s*:/.test(source);
123
+ }
124
+
125
+ function relativeProxyPath(config: ResolvedConfig, file: string) {
126
+ return `./${toPosixPath(path.relative(config.root, file))}`;
127
+ }
@@ -0,0 +1,268 @@
1
+ // Render extension registration (COMPAT - may import core freely).
2
+ //
3
+ // Wires the react/next render behaviors into the core render registries at the gated bootstrap seam. Two
4
+ // homes:
5
+ //
6
+ // src/extensions.ts (shared render registry):
7
+ // - wrapServerComponentInvoke <- invokeServerComponentWithUse (use()-thenable replay for synchronous
8
+ // server components).
9
+ // - onRenderInit <- optional compat one-time render init.
10
+ //
11
+ // src/render/hooks.ts (render-only companion registry):
12
+ // - fontExtensions <- runWithFontScope + fontAssets (next/font CSS + preloads). Next-compat only.
13
+ // - suspenseExtensions <- the preact/compat Suspense identity the streaming walker treats as a
14
+ // boundary. React-compat, loaded lazily.
15
+ //
16
+ // serializeServerActionProp, collectRenderMeta and the server-action module tagging hooks are populated
17
+ // by the actions and cache sub-registrars; this file owns the react and font/suspense hooks.
18
+
19
+ import type { ResolvedConfig } from '../../config';
20
+ import { onExtensionHostReset, setRenderExtensions } from '../../extensions';
21
+ import { setReactCompatActive } from '../react/preact';
22
+
23
+ // preact's global vnode hook cannot be uninstalled, so it follows the host.
24
+ onExtensionHostReset(() => setReactCompatActive(false));
25
+ import {
26
+ nextCompatEnabled,
27
+ reactCompatEnabled,
28
+ setDocumentScriptExtensions,
29
+ setFontExtensions,
30
+ setMetadataExtensions,
31
+ setStaticParamsExtensions,
32
+ setStreamRouteExtensions,
33
+ setSuspenseExtensions,
34
+ } from '../../render/hooks';
35
+ import { withAssetPrefix } from '../../css';
36
+ import { polyfillsChunkPath } from '../bundler/polyfill';
37
+ import { nextRouterShimScript } from '../react/router-shim';
38
+ import { renderPartytownHeadScripts } from '../next/script';
39
+ import { ensureCompatSuspense, compatSuspenseType } from '../../compat';
40
+ import { invokeServerComponentWithUse } from '../react/server-component-use';
41
+ import { fontAssets, fontPreloadDomScript, prewarmFonts, runWithFontScope } from '../next/font/runtime';
42
+ import {
43
+ hasRuntimeMetadata,
44
+ readNextModuleMetadata,
45
+ readNextModuleViewport,
46
+ shouldRenderMetadataInBody,
47
+ } from '../metadata';
48
+ import { aliasGenerateStaticParams } from '../static-params';
49
+ import { getNextConfig } from '../next/config-loader';
50
+ import {
51
+ renderServerInsertedHTML,
52
+ setServerInsertedHTMLScope,
53
+ } from '../react/server-inserted-html';
54
+ import { nextClientRouteState } from '../next/optimistic-route-state';
55
+ import { earlySubmitCaptureScript } from '../actions/early-submit';
56
+ import { getWorkUnit } from '../../request/context';
57
+ import {
58
+ createVaryParamsAccumulator,
59
+ createVaryingParams,
60
+ createVaryingSearchParams,
61
+ normalizeOptionalCatchAllParams,
62
+ } from '../segment/vary-params';
63
+ import type { VaryParamsTrackingContext } from '../../extensions';
64
+
65
+ export function registerRenderExtensions(config: ResolvedConfig): void {
66
+ // The react layer only matters when react/next compat is on. A next-only
67
+ // predicate would miss react-compat-only apps (which still render server
68
+ // components with use() and need the compat Suspense identity for streaming).
69
+ if (!reactCompatEnabled(config)) return;
70
+
71
+ setReactCompatActive(true);
72
+
73
+ setServerInsertedHTMLScope(() => {
74
+ const workUnit = getWorkUnit();
75
+ if (!workUnit) return undefined;
76
+ return (workUnit.compat ??= {});
77
+ });
78
+
79
+ setRenderExtensions({
80
+ wrapServerComponentInvoke: invokeServerComponentWithUse,
81
+ genericErrorTitle: ({ dev }) => (dev ? undefined : 'This page couldn\u2019t load'),
82
+ });
83
+
84
+ setSuspenseExtensions({ ensureCompatSuspense, compatSuspenseType });
85
+
86
+ // next/font is a next-compat feature; a react-only app renders no fonts.
87
+ if (nextCompatEnabled(config)) {
88
+ setStreamRouteExtensions({
89
+ canStreamRoute: canStreamNextRoute,
90
+ inlineSuspenseStream: needsInlineSuspenseStream,
91
+ });
92
+ setMetadataExtensions({
93
+ enabled: nextCompatEnabled,
94
+ hasRuntimeMetadata,
95
+ readModuleMetadata: readNextModuleMetadata,
96
+ readModuleViewport: readNextModuleViewport,
97
+ shouldRenderMetadataInBody,
98
+ });
99
+ setStaticParamsExtensions({ normalizeModule: aliasGenerateStaticParams });
100
+ setRenderExtensions({
101
+ clientRouteState: nextClientRouteState,
102
+ trackVaryParams: trackRenderVaryParams,
103
+ // Next asserts structural selectors (`body > p`) against the live DOM, so
104
+ // island hosts and the page slot travel as comment pairs and the inline
105
+ // bootstrap materializes them. Core ships the elements as final.
106
+ islandCommentWireFormat: () => true,
107
+ });
108
+ setDocumentScriptExtensions({
109
+ stylesheetPrecedence: cfg => (nextCompatEnabled(cfg) ? 'next' : undefined),
110
+ });
111
+ setFontExtensions({ runWithFontScope, collectFontAssets: fontAssets, prewarmFontAssets: prewarmFonts });
112
+ setDocumentScriptExtensions({
113
+ documentBodyScripts: cfg =>
114
+ `${flightDataBootstrapScript()}${renderPartytownHeadScripts()}${basePathScript(cfg.basePath)}${trailingSlashScript(cfg.trailingSlash)}${skipTrailingSlashScript(cfg.skipTrailingSlashRedirect)}${staleTimesScript()}${segmentSchedulerScript()}${appShellsScript()}${optimisticRoutingScript()}${nextRouterShimScript()}<script>${earlySubmitCaptureScript()}</script>${fontPreloadDomScript()}`,
115
+ documentHeadTags: () => `${polyfillsScript(config)}${renderServerInsertedHTML()}`,
116
+ streamInsertedHTML: renderServerInsertedHTML,
117
+ });
118
+ }
119
+ }
120
+
121
+ /**
122
+ * Hand a render's `params`/`searchParams` back wrapped in a tracking view when a vary-params scope is
123
+ * open (a segment-prefetch render). Each call allocates its OWN body-segment accumulator, tagged with the
124
+ * caller's segment kind so the response publishes the layout and page vary sets side by side instead of
125
+ * one union. Outside a scope the accumulator is null and the original object passes through untouched, so
126
+ * ordinary document renders pay nothing.
127
+ */
128
+ function trackRenderVaryParams<T extends Record<string, unknown>>(
129
+ value: T,
130
+ context: VaryParamsTrackingContext,
131
+ ): T {
132
+ const accumulator = createVaryParamsAccumulator(context.segment ?? 'page');
133
+ if (!accumulator) {
134
+ // Segment-M2 deliverable 5: Next's params shape (an EMPTY optional catch-all
135
+ // carries no key) applies to every render, not just tracked ones.
136
+ return context.kind === 'searchParams'
137
+ ? value
138
+ : normalizeOptionalCatchAllParams(value, context.optionalCatchAllParam ?? null);
139
+ }
140
+ return context.kind === 'searchParams'
141
+ ? createVaryingSearchParams(accumulator, value)
142
+ : createVaryingParams(accumulator, value, context.optionalCatchAllParam ?? null);
143
+ }
144
+
145
+ /**
146
+ * Next's flight transport inlines its RSC payload as `self.__next_f.push(...)` chunks, and app code (plus
147
+ * Next's own e2e assertions) treats the presence of that global as "this document carries inlined server
148
+ * data". pnext streams its payload through a different global, so nothing here reads `__next_f` - this
149
+ * declares the array and pushes an empty marker so the documented global exists with Next's shape. Inert
150
+ * by construction.
151
+ */
152
+ function flightDataBootstrapScript(): string {
153
+ return `<script>(self.__next_f=self.__next_f||[]).push([0])</script>`;
154
+ }
155
+
156
+ // Next emits a `<script noModule>` tag referencing the polyfills chunk in the
157
+ // document head. It never executes in module-capable browsers; it exists so the
158
+ // served HTML carries the same polyfills tag Next does (the emitted chunk is
159
+ // written by the client build's static-chunk seam). assetPrefix is applied so a
160
+ // CDN-hosted asset base still resolves.
161
+ function polyfillsScript(config: ResolvedConfig): string {
162
+ return `<script src="${withAssetPrefix(config, polyfillsChunkPath())}" noModule=""></script>`;
163
+ }
164
+
165
+ function canStreamNextRoute(input: {
166
+ config: ResolvedConfig;
167
+ route: { client?: boolean; stream?: unknown };
168
+ }) {
169
+ if (!nextCompatEnabled(input.config)) return true;
170
+ // Whole-page client routes stream through a single Preact render, preserving
171
+ // ancestor provider context across their Suspense boundaries.
172
+ if (input.route.client) return true;
173
+ const stream = input.route.stream as
174
+ | { hasLoadingBoundary?: boolean; ancestorClientReferences?: string[] }
175
+ | undefined;
176
+ // No stream metadata means a non-page route (handlers never reach the page
177
+ // renderer) — nothing to stream.
178
+ if (!stream) return false;
179
+ // Out-of-order streaming isolates each Suspense boundary and drops client-provider context inherited
180
+ // from ancestor layouts/templates. When no ancestor ships a client reference there is nothing to lose;
181
+ // when one does, the route still streams through the single-render inline-suspense path, which keeps the
182
+ // whole tree in one preact render so ancestor providers stay in scope.
183
+ return true;
184
+ }
185
+
186
+ // A route whose ancestor layouts/templates ship client references streams in
187
+ // place (one preact render that suspends at each boundary) instead of flushing
188
+ // replacement chunks rendered from a fresh root, which would drop the ancestor
189
+ // islands' provider context around the boundary's content.
190
+ function needsInlineSuspenseStream(input: {
191
+ config: ResolvedConfig;
192
+ route: { client?: boolean; stream?: unknown };
193
+ }) {
194
+ if (!nextCompatEnabled(input.config) || input.route.client) return false;
195
+ const stream = input.route.stream as { ancestorClientReferences?: string[] } | undefined;
196
+ return (stream?.ancestorClientReferences?.length ?? 0) > 0;
197
+ }
198
+
199
+ // Inline script exposing experimental.staleTimes so the client prefetch cache
200
+ // honors config overrides (defaults 30s dynamic / 300s static apply otherwise).
201
+ function staleTimesScript(): string {
202
+ const experimental = getNextConfig().experimental as
203
+ | { staleTimes?: { dynamic?: number; static?: number } }
204
+ | undefined;
205
+ const staleTimes = experimental?.staleTimes;
206
+ if (!staleTimes) return '';
207
+ return `<script>window.__PNEXT_STALE_TIMES__=${JSON.stringify(staleTimes)};</script>`;
208
+ }
209
+
210
+ // The client prefetch bandwidth scheduler (concurrency limits + hover-reserved lanes) reproduces Next's
211
+ // SEGMENT-CACHE scheduler, which only exists under cacheComponents. A classic prefetch app must fire all
212
+ // visible prefetches without throttling - the app-client-cache full-prefetch tests clear their request
213
+ // listener between two staggered prefetches and would see the delayed one land as an unexpected request.
214
+ function segmentSchedulerScript(): string {
215
+ const config = getNextConfig() as { cacheComponents?: unknown };
216
+ return config.cacheComponents === true
217
+ ? `<script>window.__PNEXT_SEGMENT_SCHEDULER__=true;</script>`
218
+ : '';
219
+ }
220
+
221
+ // `experimental.appShells`: the client fires a SECOND, param-stripped prefetch
222
+ // per params-reading route to prime that route's shared App Shell (compat/
223
+ // client/segment-prefetch.ts). Strictly opt-in — without the flag the extra
224
+ // request would break the request-count contracts of every other suite.
225
+ function appShellsScript(): string {
226
+ const experimental = getNextConfig().experimental as { appShells?: unknown } | undefined;
227
+ return experimental?.appShells === true
228
+ ? `<script>window.__PNEXT_APP_SHELLS__=true;</script>`
229
+ : '';
230
+ }
231
+
232
+ // `experimental.optimisticRouting` defaults ON, so this is an OPT-OUT marker:
233
+ // only an app that explicitly disabled it stamps the document, and the client
234
+ // segment cache then stops letting one URL's entry satisfy another URL's
235
+ // PREFETCH (compat/client/segment-cache.ts). Navigation reuse is unaffected.
236
+ function optimisticRoutingScript(): string {
237
+ const experimental = getNextConfig().experimental as
238
+ | { optimisticRouting?: unknown }
239
+ | undefined;
240
+ return experimental?.optimisticRouting === false
241
+ ? `<script>window.__PNEXT_NO_OPTIMISTIC_ROUTING__=true;</script>`
242
+ : '';
243
+ }
244
+
245
+ /**
246
+ * Inline script exposing the configured basePath to the client. `next/form` and other compat client code
247
+ * read `window.__PNEXT_BASE_PATH__` to prefix soft-nav targets. Emitted only when a basePath is set - a
248
+ * bare app keeps the global undefined, treated as ''.
249
+ */
250
+ function basePathScript(basePath: string): string {
251
+ if (!basePath) return '';
252
+ return `<script>window.__PNEXT_BASE_PATH__=${JSON.stringify(basePath)};</script>`;
253
+ }
254
+
255
+ /**
256
+ * Inline script exposing skipTrailingSlashRedirect to the client so Link hrefs and client navigation
257
+ * preserve the author's exact trailing slash. Emitted only when the flag is set - a normal app keeps the
258
+ * global undefined, treated as false.
259
+ */
260
+ function skipTrailingSlashScript(skip: boolean | undefined): string {
261
+ if (!skip) return '';
262
+ return `<script>window.__PNEXT_SKIP_TRAILING_SLASH__=true;</script>`;
263
+ }
264
+
265
+ function trailingSlashScript(trailingSlash: boolean | undefined): string {
266
+ if (trailingSlash !== true) return '';
267
+ return `<script>window.__PNEXT_TRAILING_SLASH__=true;</script>`;
268
+ }