@wular/pnext 0.1.6 → 0.1.8

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 (337) hide show
  1. package/bin/pnext +9 -2
  2. package/dist/server/_chunks/aliases-pycbtjt1.js +46 -0
  3. package/dist/server/_chunks/analyze-4d9e00g9.js +449 -0
  4. package/dist/server/_chunks/boot-bhemypxz.js +38 -0
  5. package/dist/server/_chunks/build-c991dv65.js +86 -0
  6. package/dist/server/_chunks/build-kh5e3x48.js +3341 -0
  7. package/dist/server/_chunks/build-tier-0a96kmx3.js +2456 -0
  8. package/dist/server/_chunks/compile-040r79gj.js +22 -0
  9. package/dist/server/_chunks/config-0tvz03a6.js +24 -0
  10. package/dist/server/_chunks/config-27rj7830.js +36 -0
  11. package/dist/server/_chunks/create-9rvwshsp.js +135 -0
  12. package/dist/server/_chunks/dev-ex9exynt.js +220 -0
  13. package/dist/server/_chunks/esbuild-yyktfrtt.js +15 -0
  14. package/dist/server/_chunks/generate-myw9hef7.js +22 -0
  15. package/dist/server/_chunks/index-0r5eqfc7.js +279 -0
  16. package/dist/server/_chunks/index-0yjv5v47.js +105 -0
  17. package/dist/server/_chunks/index-11xpbfej.js +17 -0
  18. package/dist/server/_chunks/index-141vcwk6.js +109 -0
  19. package/dist/server/_chunks/index-1pzm1hdy.js +4130 -0
  20. package/dist/server/_chunks/index-29pq0kax.js +590 -0
  21. package/dist/server/_chunks/index-2vz0wzdn.js +59 -0
  22. package/dist/server/_chunks/index-2wfv4kvx.js +182 -0
  23. package/dist/server/_chunks/index-38xpdxwd.js +194 -0
  24. package/dist/server/_chunks/index-3e075kny.js +128 -0
  25. package/dist/server/_chunks/index-3ycf5ckv.js +472 -0
  26. package/dist/server/_chunks/index-4399bvd2.js +18 -0
  27. package/dist/server/_chunks/index-4da76t62.js +297 -0
  28. package/dist/server/_chunks/index-4t92hdxd.js +172 -0
  29. package/dist/server/_chunks/index-4zzebszd.js +10 -0
  30. package/dist/server/_chunks/index-52k54ykj.js +95 -0
  31. package/dist/server/_chunks/index-5hr4062s.js +70 -0
  32. package/dist/server/_chunks/index-68m3mwbd.js +84 -0
  33. package/dist/server/_chunks/index-6b009mt0.js +56 -0
  34. package/dist/server/_chunks/index-6gex3pfa.js +15 -0
  35. package/dist/server/_chunks/index-6kp9r0d9.js +11 -0
  36. package/dist/server/_chunks/index-6q7zvrap.js +134 -0
  37. package/dist/server/_chunks/index-71885zaq.js +284 -0
  38. package/dist/server/_chunks/index-73z4esab.js +38 -0
  39. package/dist/server/_chunks/index-79ngvam8.js +60 -0
  40. package/dist/server/_chunks/index-7wc9n8be.js +25 -0
  41. package/dist/server/_chunks/index-8ct7rqy3.js +198 -0
  42. package/dist/server/_chunks/index-8kcxdfya.js +206 -0
  43. package/dist/server/_chunks/index-9ch50vtq.js +18 -0
  44. package/dist/server/_chunks/index-9f49w76j.js +213 -0
  45. package/dist/server/_chunks/index-9hz3s0m8.js +851 -0
  46. package/dist/server/_chunks/index-akkrvjn6.js +535 -0
  47. package/dist/server/_chunks/index-b6wtkdp4.js +24 -0
  48. package/dist/server/_chunks/index-b7j671dj.js +207 -0
  49. package/dist/server/_chunks/index-bcws5eh2.js +35 -0
  50. package/dist/server/_chunks/index-bzd2ef7t.js +10 -0
  51. package/dist/server/_chunks/index-cjgqs13g.js +65 -0
  52. package/dist/server/_chunks/index-ckkdpht5.js +41 -0
  53. package/dist/server/_chunks/index-cn86z041.js +296 -0
  54. package/dist/server/_chunks/index-cvr4z22m.js +92 -0
  55. package/dist/server/_chunks/index-cyfednwb.js +87 -0
  56. package/dist/server/_chunks/index-d158y67j.js +152 -0
  57. package/dist/server/_chunks/index-d1jsmhhk.js +955 -0
  58. package/dist/server/_chunks/index-dg0f05zs.js +199 -0
  59. package/dist/server/_chunks/index-dgr390q7.js +9438 -0
  60. package/dist/server/_chunks/index-drwv61cc.js +185 -0
  61. package/dist/server/_chunks/index-e3a6yx84.js +18 -0
  62. package/dist/server/_chunks/index-e88tyv35.js +45 -0
  63. package/dist/server/_chunks/index-en7n9f7m.js +22 -0
  64. package/dist/server/_chunks/index-entm8bmz.js +28 -0
  65. package/dist/server/_chunks/index-evhd413j.js +57 -0
  66. package/dist/server/_chunks/index-ezgj0tr1.js +88 -0
  67. package/dist/server/_chunks/index-fjv96re1.js +5295 -0
  68. package/dist/server/_chunks/index-fn1chkkd.js +214 -0
  69. package/dist/server/_chunks/index-fp8r0sqs.js +64 -0
  70. package/dist/server/_chunks/index-gcmj16xy.js +92 -0
  71. package/dist/server/_chunks/index-gkndxkxf.js +736 -0
  72. package/dist/server/_chunks/index-grta8ap3.js +238 -0
  73. package/dist/server/_chunks/index-h2a70tg4.js +7 -0
  74. package/dist/server/_chunks/index-h4xy648y.js +51 -0
  75. package/dist/server/_chunks/index-hdbwtdv2.js +352 -0
  76. package/dist/server/_chunks/index-he6n2bvp.js +1270 -0
  77. package/dist/server/_chunks/index-j0m1jxqa.js +1253 -0
  78. package/dist/server/_chunks/index-j2zrcp1k.js +66 -0
  79. package/dist/server/_chunks/index-j681c48a.js +2530 -0
  80. package/dist/server/_chunks/index-jbj7ehef.js +50 -0
  81. package/dist/server/_chunks/index-jcsjq3d1.js +20 -0
  82. package/dist/server/_chunks/index-jks0x0a1.js +14 -0
  83. package/dist/server/_chunks/index-jn9rbhrx.js +1599 -0
  84. package/dist/server/_chunks/index-jt8e1pje.js +12 -0
  85. package/dist/server/_chunks/index-kdhxpwyq.js +483 -0
  86. package/dist/server/_chunks/index-knp0s912.js +7 -0
  87. package/dist/server/_chunks/index-kqyy1d4f.js +50 -0
  88. package/dist/server/_chunks/index-kresp2n8.js +445 -0
  89. package/dist/server/_chunks/index-m63czgq5.js +590 -0
  90. package/dist/server/_chunks/index-ms9v9tnx.js +31 -0
  91. package/dist/server/_chunks/index-n4hxpng2.js +11 -0
  92. package/dist/server/_chunks/index-n629dy38.js +1071 -0
  93. package/dist/server/_chunks/index-nf3df4jy.js +266 -0
  94. package/dist/server/_chunks/index-nqh3xhdc.js +57 -0
  95. package/dist/server/_chunks/index-pym1cezq.js +39 -0
  96. package/dist/server/_chunks/index-q3r9z8mq.js +213 -0
  97. package/dist/server/_chunks/index-q738kkhj.js +100 -0
  98. package/dist/server/_chunks/index-qcrvt6er.js +112 -0
  99. package/dist/server/_chunks/index-qjj6gddn.js +54 -0
  100. package/dist/server/_chunks/index-qpwsgt3a.js +158 -0
  101. package/dist/server/_chunks/index-r97ptz1q.js +97 -0
  102. package/dist/server/_chunks/index-ras0sdab.js +26 -0
  103. package/dist/server/_chunks/index-rcs322t1.js +19 -0
  104. package/dist/server/_chunks/index-rgj5mx84.js +101 -0
  105. package/dist/server/_chunks/index-rjegyfx4.js +1435 -0
  106. package/dist/server/_chunks/index-rt9qq1va.js +4 -0
  107. package/dist/server/_chunks/index-rthrsed5.js +356 -0
  108. package/dist/server/_chunks/index-sq3kvz3g.js +200 -0
  109. package/dist/server/_chunks/index-stbk3jhn.js +31 -0
  110. package/dist/server/_chunks/index-tf4j19ge.js +130 -0
  111. package/dist/server/_chunks/index-tgcakdxc.js +125 -0
  112. package/dist/server/_chunks/index-tgsfjmep.js +74 -0
  113. package/dist/server/_chunks/index-tq1f96v7.js +51 -0
  114. package/dist/server/_chunks/index-tq3b39a5.js +107 -0
  115. package/dist/server/_chunks/index-typcbcsv.js +819 -0
  116. package/dist/server/_chunks/index-v1ags1na.js +132 -0
  117. package/dist/server/_chunks/index-vmr35jjw.js +170 -0
  118. package/dist/server/_chunks/index-vvq7rqtn.js +329 -0
  119. package/dist/server/_chunks/index-vz0km5qk.js +33 -0
  120. package/dist/server/_chunks/index-w6h8m6vp.js +138 -0
  121. package/dist/server/_chunks/index-web361b8.js +138 -0
  122. package/dist/server/_chunks/index-wm36rj4v.js +311 -0
  123. package/dist/server/_chunks/index-x0y005nh.js +283 -0
  124. package/dist/server/_chunks/index-x2m17v9c.js +6166 -0
  125. package/dist/server/_chunks/index-x3yn4ywm.js +22 -0
  126. package/dist/server/_chunks/index-x9c55pzy.js +871 -0
  127. package/dist/server/_chunks/index-xh1nbk46.js +1299 -0
  128. package/dist/server/_chunks/index-xvj80c3a.js +30 -0
  129. package/dist/server/_chunks/index-xywjg2vc.js +100 -0
  130. package/dist/server/_chunks/index-y4d02znn.js +66 -0
  131. package/dist/server/_chunks/index-y7mzvq2q.js +110 -0
  132. package/dist/server/_chunks/index-ye9hmsvf.js +47 -0
  133. package/dist/server/_chunks/index-yhxkxghe.js +56 -0
  134. package/dist/server/_chunks/index-yrjkqtfj.js +86 -0
  135. package/dist/server/_chunks/index-z88qv16t.js +11 -0
  136. package/dist/server/_chunks/index-zfrwq472.js +154 -0
  137. package/dist/server/_chunks/index-zqpqyg8p.js +666 -0
  138. package/dist/server/_chunks/loader-5en7wpt5.js +80 -0
  139. package/dist/server/_chunks/modules-t92favpj.js +76 -0
  140. package/dist/server/_chunks/pipeline-4t9q43ht.js +836 -0
  141. package/dist/server/_chunks/production-385bw8df.js +55 -0
  142. package/dist/server/_chunks/proxy-config-60gprphe.js +23 -0
  143. package/dist/server/_chunks/proxy-gfhmktbk.js +35 -0
  144. package/dist/server/_chunks/router-xnrva921.js +501 -0
  145. package/dist/server/_chunks/routes-ht868pdc.js +66 -0
  146. package/dist/server/_chunks/run-d40d63ag.js +697 -0
  147. package/dist/server/_chunks/server-2p8fgqq2.js +1839 -0
  148. package/dist/server/_chunks/tsconfig-defaults-bcn34eqb.js +21 -0
  149. package/dist/server/_chunks/typegen-dvtcjtaw.js +37 -0
  150. package/dist/server/api/client-cache.js +14 -0
  151. package/dist/server/cli/index.js +375 -0
  152. package/dist/server/cli/start.js +158 -0
  153. package/dist/server/client/reference.js +16 -0
  154. package/dist/server/compat/next/cache.js +56 -0
  155. package/dist/server/compat/next/canonical-url.js +13 -0
  156. package/dist/server/compat/next/client-cache.js +57 -0
  157. package/dist/server/compat/next/client-navigation.js +232 -0
  158. package/dist/server/compat/next/client-only.js +1 -0
  159. package/dist/server/compat/next/client-script.js +178 -0
  160. package/dist/server/compat/next/client-server.js +34 -0
  161. package/dist/server/compat/next/config-headers.js +34 -0
  162. package/dist/server/compat/next/config-loader.js +25 -0
  163. package/dist/server/compat/next/config.js +10 -0
  164. package/dist/server/compat/next/constants.js +18 -0
  165. package/dist/server/compat/next/custom-server.js +10 -0
  166. package/dist/server/compat/next/dist/client/components/app-router-headers.js +48 -0
  167. package/dist/server/compat/next/dist/server/web/spec-extension/revalidate.js +27 -0
  168. package/dist/server/compat/next/dist/server/web/spec-extension/unstable-cache.js +25 -0
  169. package/dist/server/compat/next/dist/server/web/spec-extension/unstable-no-store.js +25 -0
  170. package/dist/server/compat/next/dynamic.js +21 -0
  171. package/dist/server/compat/next/error.js +112 -0
  172. package/dist/server/compat/next/font/cache.js +16 -0
  173. package/dist/server/compat/next/font/google.js +3 -0
  174. package/dist/server/compat/next/font/index.js +1 -0
  175. package/dist/server/compat/next/font/local.js +24 -0
  176. package/dist/server/compat/next/font/runtime-client.js +33 -0
  177. package/dist/server/compat/next/font/runtime.js +43 -0
  178. package/dist/server/compat/next/font/shared.js +22 -0
  179. package/dist/server/compat/next/form.js +129 -0
  180. package/dist/server/compat/next/head.js +10 -0
  181. package/dist/server/compat/next/headers.js +30 -0
  182. package/dist/server/compat/next/image/client.js +11 -0
  183. package/dist/server/compat/next/image/config.js +18 -0
  184. package/dist/server/compat/next/image/optimizer.js +25 -0
  185. package/dist/server/compat/next/image/patterns.js +12 -0
  186. package/dist/server/compat/next/image/props.js +16 -0
  187. package/dist/server/compat/next/image/shared.js +86 -0
  188. package/dist/server/compat/next/image/static-metadata.js +32 -0
  189. package/dist/server/compat/next/image/validate.js +8 -0
  190. package/dist/server/compat/next/image.js +59 -0
  191. package/dist/server/compat/next/index.js +1 -0
  192. package/dist/server/compat/next/legacy-image.js +78 -0
  193. package/dist/server/compat/next/legacy-request-apis.js +24 -0
  194. package/dist/server/compat/next/link-transform.js +15 -0
  195. package/dist/server/compat/next/link.js +14 -0
  196. package/dist/server/compat/next/navigation.js +191 -0
  197. package/dist/server/compat/next/offline.js +45 -0
  198. package/dist/server/compat/next/og.js +8 -0
  199. package/dist/server/compat/next/preferred-region.js +8 -0
  200. package/dist/server/compat/next/redirects.js +32 -0
  201. package/dist/server/compat/next/resource-hints.js +30 -0
  202. package/dist/server/compat/next/rewrites.js +43 -0
  203. package/dist/server/compat/next/root-params.js +121 -0
  204. package/dist/server/compat/next/route-state.js +23 -0
  205. package/dist/server/compat/next/router.js +103 -0
  206. package/dist/server/compat/next/script.js +37 -0
  207. package/dist/server/compat/next/server-only.js +1 -0
  208. package/dist/server/compat/next/server.js +131 -0
  209. package/dist/server/compat/next/svgr.js +14 -0
  210. package/dist/server/compat/next/telemetry.js +10 -0
  211. package/dist/server/compat/next/usage.js +13 -0
  212. package/dist/server/compat/next/user-agent.js +12 -0
  213. package/dist/server/compat/next/web-vitals.js +35 -0
  214. package/dist/server/compat/react/action-state.js +11 -0
  215. package/dist/server/compat/react/client-lite.js +83 -0
  216. package/dist/server/compat/react/client.js +131 -0
  217. package/dist/server/compat/react/compiler-runtime.js +42 -0
  218. package/dist/server/compat/react/dom-client.js +106 -0
  219. package/dist/server/compat/react/dom-react-server.js +37 -0
  220. package/dist/server/compat/react/dom-server.js +40 -0
  221. package/dist/server/compat/react/dom.js +52 -0
  222. package/dist/server/compat/react/hooks-extra.js +12 -0
  223. package/dist/server/compat/react/internals.js +14 -0
  224. package/dist/server/compat/react/parity.js +11 -0
  225. package/dist/server/compat/react/preact.js +113 -0
  226. package/dist/server/compat/react/react-server.js +133 -0
  227. package/dist/server/compat/react/router-shim.js +8 -0
  228. package/dist/server/compat/react/server-component-use.js +14 -0
  229. package/dist/server/compat/react/server-inserted-html.js +14 -0
  230. package/dist/server/compat/react/server.js +194 -0
  231. package/dist/server/compat/react/style-values.js +10 -0
  232. package/dist/server/compat/react/use.js +10 -0
  233. package/dist/server/compat/react/view-transition.js +12 -0
  234. package/dist/server/generation.json +1 -0
  235. package/package.json +4 -1
  236. package/reference/compat.md +1 -1
  237. package/reference/config.md +2 -2
  238. package/reference/dev.md +1 -1
  239. package/reference/getting-started.md +1 -1
  240. package/reference/rendering.md +4 -4
  241. package/src/api/dynamic.tsx +86 -4
  242. package/src/api/server.ts +24 -6
  243. package/src/cli/adapters/vercel-warm.ts +327 -62
  244. package/src/cli/adapters/vercel.ts +164 -1054
  245. package/src/cli/analyze.ts +3 -2
  246. package/src/cli/build/cache.ts +6 -6
  247. package/src/cli/build.ts +78 -45
  248. package/src/cli/index.ts +21 -3
  249. package/src/cli/serve/immutable.ts +31 -0
  250. package/src/cli/serve/pipeline.ts +97 -93
  251. package/src/cli/serve/standalone-worker.ts +8 -0
  252. package/src/cli/serve/standalone.ts +703 -0
  253. package/src/cli/start.ts +31 -8
  254. package/src/client/build.ts +1 -1
  255. package/src/client/chunk-fold.ts +19 -6
  256. package/src/client/react-tier.ts +3 -2
  257. package/src/client/reference-stub.ts +23 -36
  258. package/src/compat/actions/client-plugin.ts +4 -2
  259. package/src/compat/actions/config.ts +6 -5
  260. package/src/compat/actions/extensions.ts +5 -5
  261. package/src/compat/aliases.ts +8 -1
  262. package/src/compat/bundler/config.ts +88 -0
  263. package/src/compat/bundler/optimize-package-imports.ts +86 -26
  264. package/src/compat/bundler/relay-transform.ts +15 -3
  265. package/src/compat/bundler/require-context.ts +2 -1
  266. package/src/compat/bundler/webpack-loaders.ts +3 -2
  267. package/src/compat/bundler/worker.ts +2 -2
  268. package/src/compat/cache-control.ts +16 -8
  269. package/src/compat/css/inline-css.ts +1 -1
  270. package/src/compat/css/modules.ts +18 -5
  271. package/src/compat/export/build-complete.ts +1 -1
  272. package/src/compat/export/emit.ts +4 -4
  273. package/src/compat/export/standalone.ts +30 -65
  274. package/src/compat/image-optimizer/optimize.ts +1 -1
  275. package/src/compat/lifecycle/error-funnel.ts +1 -1
  276. package/src/compat/lifecycle/instrumentation-client.ts +4 -3
  277. package/src/compat/lifecycle/instrumentation.ts +117 -24
  278. package/src/compat/lifecycle/testmode.ts +3 -2
  279. package/src/compat/metadata-artifacts.ts +1 -1
  280. package/src/compat/next/config-loader.ts +140 -13
  281. package/src/compat/next/dynamic.tsx +10 -23
  282. package/src/compat/next/font/cache.ts +2 -1
  283. package/src/compat/next/font/runtime.ts +23 -3
  284. package/src/compat/next/og.ts +3 -3
  285. package/src/compat/next/usage.ts +3 -2
  286. package/src/compat/pages/api.ts +83 -14
  287. package/src/compat/pages/router.ts +30 -14
  288. package/src/compat/register/bundler.ts +3 -1
  289. package/src/compat/register/image.ts +1 -1
  290. package/src/compat/register/middleware.ts +1 -1
  291. package/src/compat/register/otel.ts +5 -9
  292. package/src/compat/register/render.ts +3 -1
  293. package/src/compat/register/use-cache.ts +3 -1
  294. package/src/compat/release.ts +46 -0
  295. package/src/compat/segment/serve.ts +1 -1
  296. package/src/compat/typecheck/check.ts +6 -4
  297. package/src/compat/validation/validate.ts +10 -7
  298. package/src/config.ts +76 -9
  299. package/src/css/assets.ts +213 -0
  300. package/src/css/build.ts +190 -247
  301. package/src/dev/client-chunk-store.ts +2 -1
  302. package/src/dev/restart/client-key.ts +2 -1
  303. package/src/dev/restart/global-css.ts +2 -1
  304. package/src/dev/restart/route-bundle-key.ts +2 -1
  305. package/src/dev/restart/route-facts.ts +2 -1
  306. package/src/dev/server.ts +34 -14
  307. package/src/extensions.ts +4 -0
  308. package/src/out-paths.ts +10 -0
  309. package/src/render/hooks.ts +13 -0
  310. package/src/render/renderer.ts +53 -33
  311. package/src/request/context.ts +9 -0
  312. package/src/resolve/dynamic.ts +7 -1
  313. package/src/resolve/engine.ts +2 -12
  314. package/src/resolve/imports.ts +12 -52
  315. package/src/resolve/package-json.ts +56 -0
  316. package/src/resolve/scan-facts.ts +250 -1
  317. package/src/routing/href.ts +10 -3
  318. package/src/routing/match.ts +287 -0
  319. package/src/routing/metadata-files.ts +20 -6
  320. package/src/routing/proxy-config.ts +137 -0
  321. package/src/routing/proxy.ts +35 -134
  322. package/src/routing/routes.ts +22 -281
  323. package/src/runtime/fingerprint.ts +23 -8
  324. package/src/runtime/load.ts +170 -0
  325. package/src/runtime/loader.ts +218 -44
  326. package/src/runtime/module-cache.ts +15 -1
  327. package/src/runtime/modules.ts +405 -82
  328. package/src/runtime/prebundle.ts +101 -0
  329. package/src/runtime/production.ts +456 -0
  330. package/src/runtime/release-graph.ts +342 -0
  331. package/src/runtime/vendor-build.ts +750 -17
  332. package/src/runtime/vendor.ts +16 -3
  333. package/src/types.ts +4 -3
  334. package/src/utils/directive.ts +40 -0
  335. package/src/utils/fs.ts +95 -4
  336. package/src/utils/resource-query.ts +12 -0
  337. package/src/cli/serve/entry.ts +0 -45
@@ -8,6 +8,7 @@ import { matchRoute } from '../routing/routes'
8
8
  import { bold, cyan, dim } from '../utils/ansi'
9
9
  import { listFiles } from '../utils/fs'
10
10
  import type { BuildManifest, RouteManifestEntry } from '../types'
11
+ import { buildManifestFile } from '../runtime/production'
11
12
 
12
13
  export interface AnalyzeResult {
13
14
  root: string
@@ -109,7 +110,7 @@ async function analyzeRouteBundles(
109
110
  files: AnalyzeFile[],
110
111
  routeFilter?: string,
111
112
  ) {
112
- const manifestPath = path.join(outPath, 'manifest.json')
113
+ const manifestPath = buildManifestFile(outPath)
113
114
  if (!existsSync(manifestPath)) return []
114
115
 
115
116
  const manifest = JSON.parse(await readFile(manifestPath, 'utf8')) as BuildManifest
@@ -374,7 +375,7 @@ function prerenderedPathname(route: RouteManifestEntry) {
374
375
  function analyzeTarget(outPath: string) {
375
376
  // PPR shells live in `.pnext/ppr`, outside `public`: they are resumed
376
377
  // server-side and never downloaded, so they are not shipped weight.
377
- const publicPath = path.join(outPath, 'public')
378
+ const publicPath = path.join(outPath, 'static')
378
379
  return existsSync(publicPath) ? { root: publicPath } : null
379
380
  }
380
381
 
@@ -7,9 +7,11 @@ import type { ResolvedConfig } from '../../config'
7
7
  import { frameworkFingerprint } from '../../runtime/fingerprint'
8
8
  import type { BuildManifest } from '../../types'
9
9
  import { writeFileAtomic } from '../../utils/fs'
10
+ import { buildManifestFile } from '../../runtime/production'
11
+ import { outCachePath } from '../../out-paths'
10
12
 
11
13
  const CACHE_VERSION = 2
12
- const CACHE_SEGMENTS = ['cache', 'build'] as const
14
+ const CACHE_SEGMENTS = ['build'] as const
13
15
  const SKIP_INPUT_DIRS = new Set([
14
16
  '.claude',
15
17
  '.git',
@@ -75,9 +77,7 @@ export async function lookupBuildCache(
75
77
  }
76
78
  try {
77
79
  const manifest = resolveManifest(
78
- JSON.parse(
79
- await readFile(path.join(config.outPath, 'manifest.json'), 'utf8'),
80
- ) as BuildManifest,
80
+ JSON.parse(await readFile(buildManifestFile(config.outPath), 'utf8')) as BuildManifest,
81
81
  config.outPath,
82
82
  config.root,
83
83
  )
@@ -121,7 +121,7 @@ function cacheEnabled(options: BuildCacheOptions) {
121
121
  }
122
122
 
123
123
  function cacheDir(outPath: string) {
124
- return path.join(outPath, ...CACHE_SEGMENTS)
124
+ return path.join(outCachePath(outPath), ...CACHE_SEGMENTS)
125
125
  }
126
126
 
127
127
  function recordFile(outPath: string) {
@@ -220,7 +220,7 @@ async function collectModuleGraphInputs(config: ResolvedConfig, files: Map<strin
220
220
  let parsed: ModuleGraphIndex
221
221
  try {
222
222
  parsed = JSON.parse(
223
- await readFile(path.join(config.outPath, 'cache', 'server', 'graph.json'), 'utf8'),
223
+ await readFile(path.join(outCachePath(config.outPath), 'server', 'graph.json'), 'utf8'),
224
224
  ) as ModuleGraphIndex
225
225
  } catch {
226
226
  return
package/src/cli/build.ts CHANGED
@@ -25,13 +25,15 @@ import { beginSourceScope, endSourceScope, sourceCacheStats } from '../resolve/s
25
25
  import { flushDevModuleCaches } from '../runtime/module-cache'
26
26
  import { scanFactsStats } from '../resolve/scan-facts'
27
27
  import { clientEntryName } from '../client/chunk-name'
28
+ import { compiledClientReferenceFiles } from '../client/reference'
29
+ import { buildIndexFile, buildManifestFile } from '../runtime/production'
28
30
  import { registerServerRuntime, serverBundleTargetForRuntime } from '../runtime/loader'
29
31
  import {
30
- buildClientReferenceCss,
31
32
  buildGlobalCss,
32
33
  buildNotFoundCss,
33
- buildRouteCss,
34
+ buildRouteStylesheets,
34
35
  emittedAssetNames,
36
+ globalCssSources,
35
37
  prepareRouteCssChunks,
36
38
  registerCssRuntime,
37
39
  warmCssPipeline,
@@ -72,6 +74,7 @@ import {
72
74
  devServerModuleHref,
73
75
  resetModuleGraphFailure,
74
76
  setEmitCompiledSpecifiersManifest,
77
+ setReleaseCompile,
75
78
  throwIfModuleGraphFailed,
76
79
  } from '../runtime/modules'
77
80
  import {
@@ -91,7 +94,8 @@ import {
91
94
  import { interceptionMarkerLevels } from '../routing/slots'
92
95
  import { writeTypegen } from './typegen'
93
96
  import { lookupBuildCache, writeBuildCache } from './build/cache'
94
- import { emitServerEntry } from './serve/entry'
97
+ import { startStandalone, writeStandalone } from './serve/standalone'
98
+ import { immutableAssetPath } from './serve/immutable'
95
99
  import { createVerboseLogger, type VerboseLogger } from '../utils/verbose'
96
100
  import { bold, cyan, dim, green } from '../utils/ansi'
97
101
  import type {
@@ -165,6 +169,7 @@ export async function buildProject(root?: string, options: BuildOptions = {}) {
165
169
  // Only the vercel adapter's trace step reads the per-artifact specifier
166
170
  // sidecars; every other build path pays nothing for them.
167
171
  const restoreSpecifiersManifest = setEmitCompiledSpecifiersManifest(options.adapter === 'vercel')
172
+ const restoreReleaseCompile = setReleaseCompile(true)
168
173
  const lifecycle: { warm?: WarmChild } = {}
169
174
  try {
170
175
  return await runBuild(root, options, lifecycle)
@@ -177,6 +182,7 @@ export async function buildProject(root?: string, options: BuildOptions = {}) {
177
182
  lifecycle.warm?.kill()
178
183
  endSourceScope()
179
184
  restoreSpecifiersManifest()
185
+ restoreReleaseCompile()
180
186
  flushDevModuleCaches()
181
187
  }
182
188
  }
@@ -225,11 +231,14 @@ async function runBuild(
225
231
  const warmMode = options.adapter === 'vercel' ? 'full' : 'compile'
226
232
  const warm = startWarmChild(config, warmMode)
227
233
  lifecycle.warm = warm
228
- await log.step('prepare output directory', async () => {
234
+ // The framework's half of the standalone trace needs no build output; it overlaps the bundling.
235
+ const standalone = startStandalone(config)
236
+ const publicFiles = await log.step('prepare output directory', async () => {
229
237
  // Build-owned outputs only: `<outRoot>/dev` belongs to a possibly-running
230
238
  // dev server and must survive.
231
- await ensureEmptyDir(config.outPath, [devOutSegment])
232
- await copyPublicDir(config.publicPath, path.join(config.outPath, 'public'))
239
+ // Materialized pages sources too: this build's config already resolved into them.
240
+ await ensureEmptyDir(config.outRootPath, [devOutSegment, 'pnext-pages-compat'])
241
+ return copyPublicDir(config.publicPath, path.join(config.outPath, 'static'))
233
242
  })
234
243
  // The document-level stylesheets run their postcss/Tailwind pass on the CSS
235
244
  // worker, so they overlap with the route scan below instead of serializing
@@ -305,6 +314,14 @@ async function runBuild(
305
314
  // - those are awaited just before the first route stylesheet is emitted, which lets a Tailwind
306
315
  // pass run under the build steps and the client bundles instead of ahead of them.
307
316
  prepareRouteCssChunks(routes)
317
+ // Route stylesheets bundle all at once under the client stage; the loop below publishes each
318
+ // route's names right before its prerender, after the document ones.
319
+ const routeStylesheets = buildRouteStylesheets(
320
+ config,
321
+ routes.filter(route => route.kind !== 'handler' && !route.dynamicErrorApi),
322
+ documentCss,
323
+ { verbose },
324
+ )
308
325
  // output:'export' with trailingSlash:false lays prerendered pages out flat
309
326
  // (`/a.html` rather than `/a/index.html`). Only meaningful under compat (the
310
327
  // Next config carries `output`); pure-core apps always use the dir layout.
@@ -353,9 +370,11 @@ async function runBuild(
353
370
  )
354
371
  : undefined
355
372
  metadataWarnings?.catch(() => undefined)
356
- const staticModuleMetadata = await log.step('core module metadata', () =>
373
+ // Imports the route modules; the client stage needs none of it, so both run at once.
374
+ const moduleMetadata = log.step('core module metadata', () =>
357
375
  collectStaticModuleMetadata(config, routes),
358
376
  )
377
+ moduleMetadata.catch(() => undefined)
359
378
 
360
379
  const actionSources = buildState.actionSources ?? buildState.actions.map(a => a.sourceKey)
361
380
  // realpath, not resolve: a hybrid app's routes are scanned through the pages-compat mirror, whose
@@ -366,13 +385,18 @@ async function runBuild(
366
385
  // A node_modules action module never lands in route.sourceFiles itself (that walk stops at the
367
386
  // package boundary), so a route reaching one only through a first-party importer is matched here.
368
387
  const actionImporters = new Set((buildState.actionImporters ?? []).map(realFilePath))
388
+ // Routes share most of their files; resolve each once.
389
+ const realFiles = new Map<string, string>()
390
+ const reachesAction = (file: string) => {
391
+ let real = realFiles.get(file)
392
+ if (real === undefined) realFiles.set(file, (real = realFilePath(file)))
393
+ return actionFiles.has(real) || actionImporters.has(real)
394
+ }
369
395
  for (const route of routes) {
370
396
  if (
371
397
  route.kind === 'page' &&
372
- route.sourceFiles.some(file => {
373
- const real = realFilePath(file)
374
- return actionFiles.has(real) || actionImporters.has(real)
375
- })
398
+ (actionFiles.size > 0 || actionImporters.size > 0) &&
399
+ route.sourceFiles.some(reachesAction)
376
400
  ) {
377
401
  addClientEntryReason(route, 'actions')
378
402
  }
@@ -389,7 +413,7 @@ async function runBuild(
389
413
  buildClientEntries({
390
414
  config,
391
415
  routes: clientRoutes,
392
- outDir: path.join(config.outPath, 'public', 'assets'),
416
+ outDir: path.join(config.outPath, 'static', 'assets'),
393
417
  verbose,
394
418
  hasServerActions: actionSources.length > 0,
395
419
  pipeline: clientSources,
@@ -400,14 +424,14 @@ async function runBuild(
400
424
  // other document does, and those names are only final once the client stage has
401
425
  // fingerprinted them — so this render follows the bundle rather than racing it.
402
426
  // Result is consumed after the prerender pass, where it always was.
403
- const notFoundDocuments = clientBundles.then(() =>
427
+ const notFoundDocuments = clientBundles.then(async () =>
404
428
  renderNotFoundDocuments({
405
429
  config,
406
430
  log,
407
431
  skip: options.buildMode === 'compile',
408
432
  documentCss,
409
433
  staticMetadataFiles,
410
- staticModuleMetadata,
434
+ staticModuleMetadata: await moduleMetadata,
411
435
  }),
412
436
  )
413
437
  notFoundDocuments.catch(() => undefined)
@@ -420,13 +444,14 @@ async function runBuild(
420
444
  ).then(() => log.step('typegen', () => writeTypegen(config, routes)))
421
445
  remainingSteps.catch(() => undefined)
422
446
  await remainingSteps
447
+ const staticModuleMetadata = await moduleMetadata
423
448
  await clientBundles
424
449
  const proxyModule = await proxyBuild
425
450
  await partytownLib
426
451
  // Standalone static chunks (compat: the no-module polyfills chunk) live
427
452
  // outside the esbuild entry graph, so emit them regardless of whether any
428
453
  // route produced a client bundle.
429
- await emitStaticClientChunks(config, path.join(config.outPath, 'public', 'assets'))
454
+ await emitStaticClientChunks(config, path.join(config.outPath, 'static', 'assets'))
430
455
  // All three source consumers have run by here; the split says how much of the
431
456
  // app was read once and shared rather than read per consumer.
432
457
  if (verbose) {
@@ -472,8 +497,7 @@ async function runBuild(
472
497
  const generateFailures: { route: string; omitErrorLine: boolean }[] = []
473
498
  if (isGenerate) console.log(' Collecting page data ...')
474
499
 
475
- // Route stylesheets build strictly after the document ones; this is the first
476
- // point that needs them, so everything above ran alongside the CSS worker.
500
+ // The first point that needs the stylesheets, so everything above ran alongside them.
477
501
  await documentCss
478
502
 
479
503
  for (const route of routes) {
@@ -515,10 +539,7 @@ async function runBuild(
515
539
  continue
516
540
  }
517
541
 
518
- await buildRouteCss(config, route, { verbose })
519
- for (const reference of route.clientReferences) {
520
- await buildClientReferenceCss(config, reference, { verbose })
521
- }
542
+ await routeStylesheets.get(route)?.()
522
543
 
523
544
  // Compile mode bundles only — every prerender/export step is generate's.
524
545
  if (isCompile) continue
@@ -768,7 +789,7 @@ async function runBuild(
768
789
  html: rendered.value.html,
769
790
  status: rendered.value.status,
770
791
  })
771
- const relative = toPosixPath(path.relative(path.join(config.outPath, 'public'), file))
792
+ const relative = toPosixPath(path.relative(path.join(config.outPath, 'static'), file))
772
793
  const revalidateSeconds = combineRevalidate(
773
794
  segmentConfig?.revalidate,
774
795
  rendered.revalidateSeconds,
@@ -906,6 +927,7 @@ async function runBuild(
906
927
  // carries its entries, so this is where it has to have landed.
907
928
  await deferredSteps
908
929
  const actions = buildState.actions
930
+ const publicAssets = publicFiles.filter(relative => immutableAssetPath(relative))
909
931
  const manifest: BuildManifest = {
910
932
  version: 0,
911
933
  root: config.root,
@@ -916,6 +938,7 @@ async function runBuild(
916
938
  // The serving process re-publishes these so a render resolves the same
917
939
  // content-hashed names the build emitted.
918
940
  assetNames: emittedAssetNames(config.outPath),
941
+ ...(publicAssets.length > 0 ? { publicAssets } : {}),
919
942
  staticMetadataFiles,
920
943
  ...(Object.keys(staticModuleMetadata).length > 0 ? { staticModuleMetadata } : {}),
921
944
  ...(!config.compat?.next
@@ -930,18 +953,25 @@ async function runBuild(
930
953
  }
931
954
  await writeBuildManifest(config.outPath, manifest)
932
955
  log.log(`wrote manifest.json (${routes.length} route${routes.length === 1 ? '' : 's'})`)
933
- await log.step('server entry', () => emitServerEntry(config.outPath))
934
956
  for (const hook of getBuildExtensions().completeHooks) {
935
957
  await hook({ config, manifest, log })
936
958
  }
937
- if (options.adapter === 'vercel')
938
- await log.step('vercel adapter output', () =>
939
- writeVercelOutput(config, manifest, { verbose, warm }),
940
- )
941
- // Plain build: the adapter owns the child in the branch above. Compiling the
942
- // rest of the app's modules is build work, so it counts toward the build's own
959
+ // Compiling the rest of the app's modules is build work, so it counts toward the build's own
943
960
  // duration rather than hiding after it.
944
- else await log.step('warm module cache', () => warm.finish(log))
961
+ await log.step('warm module cache', () =>
962
+ warm.finish(log, undefined, {
963
+ globalCss: globalCssSources(config),
964
+ clientReferences: [...compiledClientReferenceFiles()],
965
+ }),
966
+ )
967
+ // The release names every module production imports; a server compile that did not finish
968
+ // fails the build here rather than a request later.
969
+ if (!existsSync(buildIndexFile(config.outPath))) {
970
+ throw new Error('pnext build: the server compile did not complete (see the error above).')
971
+ }
972
+ await log.step('standalone output', () => writeStandalone(config, standalone))
973
+ if (options.adapter === 'vercel')
974
+ await log.step('vercel adapter output', () => writeVercelOutput(config, manifest, { verbose }))
945
975
 
946
976
  // Also cover module loads performed by completion hooks or the warm pass.
947
977
  throwIfModuleGraphFailed()
@@ -1046,8 +1076,9 @@ function interceptionDisplayRoute(route: RouteManifestEntry, filled?: string): s
1046
1076
 
1047
1077
  async function writeBuildManifest(outPath: string, manifest: BuildManifest) {
1048
1078
  assertManifestServerArtifacts(outPath, manifest)
1049
- const file = path.join(outPath, 'manifest.json')
1050
- const temporary = path.join(outPath, `.manifest-${process.pid}.tmp`)
1079
+ const file = buildManifestFile(outPath)
1080
+ const temporary = `${file}.${process.pid}.tmp`
1081
+ await mkdir(path.dirname(file), { recursive: true })
1051
1082
  await writeFile(temporary, serializeBuildManifest(manifest))
1052
1083
  await rename(temporary, file)
1053
1084
  }
@@ -1057,9 +1088,11 @@ function assertManifestServerArtifacts(outPath: string, manifest: BuildManifest)
1057
1088
  ...(manifest.proxyModule ? [manifest.proxyModule] : []),
1058
1089
  ...(manifest.actions?.map(action => action.modulePath) ?? []),
1059
1090
  ]
1091
+ // Compiled artifacts still sit in the build cache beside the release until writeStandalone moves them.
1092
+ const outRoot = path.dirname(outPath)
1060
1093
  for (const artifact of artifacts) {
1061
1094
  const file = path.resolve(outPath, artifact)
1062
- if (file !== outPath && !file.startsWith(`${outPath}${path.sep}`)) {
1095
+ if (!file.startsWith(`${outRoot}${path.sep}`)) {
1063
1096
  throw new Error(`Build manifest server artifact escapes output directory: ${artifact}`)
1064
1097
  }
1065
1098
  if (!existsSync(file)) {
@@ -2223,7 +2256,7 @@ async function renderNotFoundDocuments({
2223
2256
 
2224
2257
  if (await shouldBuildGlobalNotFound(config)) {
2225
2258
  await log.step('global not-found', async () =>
2226
- writeText(path.join(config.outPath, 'public', '404.html'), await render()),
2259
+ writeText(path.join(config.outPath, 'static', '404.html'), await render()),
2227
2260
  )
2228
2261
  }
2229
2262
  // Next always prerenders the built-in `/_not-found` document for a compat
@@ -2231,7 +2264,7 @@ async function renderNotFoundDocuments({
2231
2264
  // `.next/server/app/_not-found.html`). When public/404.html was written, the
2232
2265
  // .next artifacts are copied from it; otherwise they need a document here.
2233
2266
  if (!config.compat?.next) return undefined
2234
- if (existsSync(path.join(config.outPath, 'public', '404.html'))) return undefined
2267
+ if (existsSync(path.join(config.outPath, 'static', '404.html'))) return undefined
2235
2268
  // Nothing prerenderable to render into the document: either the app authored no not-found.* at
2236
2269
  // all, or it authored one and declared it force-dynamic, in which case Next leaves `/_not-found`
2237
2270
  // dynamic and prerenders no custom 404 either. Emit the standalone default rather than boot the
@@ -2289,7 +2322,7 @@ async function emitNextNotFoundArtifacts(
2289
2322
  fallback404?: string,
2290
2323
  ) {
2291
2324
  if (!config.compat?.next) return
2292
- const source = path.join(config.outPath, 'public', '404.html')
2325
+ const source = path.join(config.outPath, 'static', '404.html')
2293
2326
  const html = existsSync(source) ? readFileSync(source, 'utf8') : fallback404
2294
2327
  if (html === undefined) return
2295
2328
 
@@ -2506,7 +2539,7 @@ async function buildStaticRouteHandler(
2506
2539
  if (rendered.noStore && !staticRouteHandlerExplicitlyCached(route)) continue
2507
2540
  const body = await settleBeforeNextTask(response.clone().arrayBuffer())
2508
2541
  if (!body) continue
2509
- const relative = toPosixPath(path.relative(path.join(config.outPath, 'public'), file))
2542
+ const relative = toPosixPath(path.relative(path.join(config.outPath, 'static'), file))
2510
2543
  // Descendant handlers record their manifest entry (so the synthesized
2511
2544
  // prerender-manifest lists them) but skip the on-disk copy that would
2512
2545
  // collide with the ancestor's file; they serve dynamically at runtime.
@@ -2825,7 +2858,7 @@ async function copyStaticMetadataFiles(
2825
2858
  }
2826
2859
 
2827
2860
  export function staticHtmlPath(outPath: string, routePath: string, flatLayout = false) {
2828
- if (routePath === '/') return path.join(outPath, 'public', 'index.html')
2861
+ if (routePath === '/') return path.join(outPath, 'static', 'index.html')
2829
2862
  const normalized = routePath.replace(/^\/|\/$/g, '')
2830
2863
  // output:'export' with trailingSlash:false lays pages out flat (`/a.html`);
2831
2864
  // otherwise (and always for trailingSlash:true) each page gets its own dir
@@ -2924,7 +2957,7 @@ function staticRouteHandlerPath(outPath: string, routePath: string) {
2924
2957
  * route serves dynamically (start's static lookup only matches real files, then falls through).
2925
2958
  */
2926
2959
  function staticOutputCollision(outPath: string, file: string): string | null {
2927
- const publicPath = path.join(outPath, 'public')
2960
+ const publicPath = path.join(outPath, 'static')
2928
2961
  if (existsSync(file) && statSync(file).isDirectory()) {
2929
2962
  return `${toPosixPath(path.relative(publicPath, file))} already exists as a directory`
2930
2963
  }
@@ -3144,7 +3177,7 @@ function realFilePath(file: string): string {
3144
3177
  }
3145
3178
 
3146
3179
  function safePublicPath(outPath: string, ...segments: string[]) {
3147
- const publicPath = path.join(outPath, 'public')
3180
+ const publicPath = path.join(outPath, 'static')
3148
3181
  const file = path.join(publicPath, ...segments)
3149
3182
  const relative = path.relative(publicPath, file)
3150
3183
  if (relative.startsWith('..') || path.isAbsolute(relative)) {
@@ -3171,7 +3204,7 @@ async function copyPartytownLib(config: Awaited<ReturnType<typeof loadConfig>>)
3171
3204
  )
3172
3205
  return
3173
3206
  }
3174
- const target = path.join(config.outPath, 'public', '_next', 'static', '~partytown')
3207
+ const target = path.join(config.outPath, 'static', '_next', 'static', '~partytown')
3175
3208
  await mkdir(target, { recursive: true })
3176
3209
  await copyPublicDir(libDir, target)
3177
3210
  }
@@ -3194,11 +3227,11 @@ function resolvePartytownLibDir(root: string): string | null {
3194
3227
  }
3195
3228
 
3196
3229
  async function copyPublicDir(from: string, to: string) {
3197
- const files = await listFiles(from)
3198
- for (const file of files) {
3199
- const relative = toPosixPath(path.relative(from, file))
3230
+ const files = (await listFiles(from)).map(file => toPosixPath(path.relative(from, file)))
3231
+ for (const relative of files) {
3200
3232
  const target = path.join(to, relative)
3201
3233
  await mkdir(path.dirname(target), { recursive: true })
3202
- await copyFile(file, target)
3234
+ await copyFile(path.join(from, relative), target)
3203
3235
  }
3236
+ return files
3204
3237
  }
package/src/cli/index.ts CHANGED
@@ -50,8 +50,8 @@ markBoot('cli:entry')
50
50
  namedBunBinary(commandBinaryName(command))
51
51
 
52
52
  // Before any command lazily imports esbuild, which captures the binary path on
53
- // module load.
54
- nameEsbuildProcess()
53
+ // module load. `start` serves a finished build and never loads it.
54
+ if (command !== 'start') nameEsbuildProcess()
55
55
  markBoot('cli:naming')
56
56
 
57
57
  try {
@@ -90,7 +90,10 @@ try {
90
90
  } else if (command === 'start') {
91
91
  warnUnknownFlags(command, args)
92
92
  const root = positionalRoot(args)
93
- const { start } = await import('./start')
93
+ // A build of other source than this prebundle's is served from that source.
94
+ const { start } = (await prebundleServes(root))
95
+ ? await import('./start')
96
+ : ((await import(new URL('./start.ts', import.meta.url).href)) as typeof import('./start'))
94
97
  await start({
95
98
  root,
96
99
  port: optionNumber(args, '--port'),
@@ -160,6 +163,21 @@ function formatCliError(error: unknown) {
160
163
  }
161
164
  }
162
165
 
166
+ declare const PNEXT_PREBUNDLE: { version: string; fingerprint: string } | undefined
167
+
168
+ /** Whether this process's prebundle may serve `root`'s build: one made from its source and version. */
169
+ async function prebundleServes(root = process.cwd()) {
170
+ if (typeof PNEXT_PREBUNDLE !== 'object') return true
171
+ const [{ DEFAULT_OUT_DIR, standaloneOutSegment }, { buildIndexFile, readBuildIndex }] =
172
+ await Promise.all([import('../config'), import('../runtime/production')])
173
+ const outPath = path.resolve(root, DEFAULT_OUT_DIR, standaloneOutSegment)
174
+ return (
175
+ !existsSync(buildIndexFile(outPath)) ||
176
+ (readBuildIndex(outPath).framework === PNEXT_PREBUNDLE.fingerprint &&
177
+ VERSION === PNEXT_PREBUNDLE.version)
178
+ )
179
+ }
180
+
163
181
  function positionalRoot(args: string[]) {
164
182
  return positionals(args)[0]
165
183
  }
@@ -0,0 +1,31 @@
1
+ import { getAssetExtensions } from '../../extensions'
2
+
3
+ export const immutableCacheControl = 'public, max-age=31536000, immutable'
4
+
5
+ /**
6
+ * Everything the build emits under `assets/` (served at `/_next/static/*` in
7
+ * compat) is immutable, which is the promise Next makes for that whole
8
+ * namespace. It holds because every one of those names carries a content hash:
9
+ * esbuild's for chunks and fonts, assetContentHash for the route entries and the
10
+ * stylesheets (see fingerprintClientEntries / fingerprintAsset), and a build id
11
+ * for `_next/static/<id>/_*Manifest.js`. An UNHASHED name must never reach here —
12
+ * the same URL would answer different bytes after a deploy, and every browser
13
+ * that saw the old ones would keep them for a year.
14
+ *
15
+ * Route outputs (prerendered html, handler bodies) live outside both prefixes
16
+ * and stay revalidating; so do the app's own public/ files (manifest.publicAssets).
17
+ */
18
+ export function immutableAssetPath(relativePath: string) {
19
+ return immutableAssetPrefixes().some(prefix => relativePath.startsWith(prefix))
20
+ }
21
+
22
+ /** The public-relative prefixes `immutableAssetPath` covers. */
23
+ export function immutableAssetPrefixes() {
24
+ return [
25
+ 'assets/',
26
+ '_next/static/',
27
+ ...getAssetExtensions()
28
+ .staticAssetPublicPrefixes()
29
+ .map(prefix => prefix.replace(/^\/+/, '')),
30
+ ]
31
+ }