@wular/pnext 0.0.4 → 0.0.6

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 (392) hide show
  1. package/README.md +11 -11
  2. package/bin/pnext +1 -1
  3. package/config/lint/base.js +7 -7
  4. package/config/ts/base.json +2 -4
  5. package/config/ts/react.json +2 -6
  6. package/package.json +23 -2
  7. package/reference/compat.md +1 -1
  8. package/reference/config.md +2 -2
  9. package/reference/css.md +13 -9
  10. package/reference/dev.md +1 -1
  11. package/reference/metadata.md +7 -7
  12. package/reference/navigation.md +35 -28
  13. package/reference/performance.md +70 -70
  14. package/reference/rendering.md +17 -17
  15. package/reference/routing.md +17 -17
  16. package/reference/typegen.md +12 -8
  17. package/src/api/cache.ts +36 -37
  18. package/src/api/client-cache.ts +2 -2
  19. package/src/api/client-navigation.ts +113 -109
  20. package/src/api/dynamic.tsx +58 -55
  21. package/src/api/link.tsx +49 -52
  22. package/src/api/navigation.ts +59 -58
  23. package/src/api/server.ts +152 -144
  24. package/src/api/suspense.ts +4 -4
  25. package/src/cli/adapters/vercel-warm.ts +126 -121
  26. package/src/cli/adapters/vercel.ts +437 -443
  27. package/src/cli/analyze.ts +333 -144
  28. package/src/cli/{named-bin.ts → boot/named-bin.ts} +37 -37
  29. package/src/cli/{boot-trace.ts → boot/trace.ts} +10 -10
  30. package/src/cli/build.ts +976 -978
  31. package/src/cli/create.ts +71 -63
  32. package/src/cli/dev.ts +116 -116
  33. package/src/cli/index.ts +88 -85
  34. package/src/cli/migrate/package-json.ts +73 -71
  35. package/src/cli/migrate/report.ts +32 -33
  36. package/src/cli/migrate/{index.ts → run.ts} +48 -49
  37. package/src/cli/migrate/scan.ts +46 -46
  38. package/src/cli/migrate/spinner.ts +9 -9
  39. package/src/cli/migrate/tsconfig.ts +35 -35
  40. package/src/cli/{server-entry.ts → serve/entry.ts} +57 -57
  41. package/src/cli/{request-pipeline.ts → serve/pipeline.ts} +386 -394
  42. package/src/cli/{serve-ui.ts → serve/ui.ts} +47 -47
  43. package/src/cli/start.ts +65 -66
  44. package/src/{typegen.ts → cli/typegen.ts} +59 -59
  45. package/src/client/build.ts +794 -768
  46. package/src/client/chunk-fold.ts +245 -240
  47. package/src/client/{paths.ts → chunk-name.ts} +6 -6
  48. package/src/client/entry.ts +162 -147
  49. package/src/client/prebuilt.ts +231 -223
  50. package/src/client/profile.ts +29 -29
  51. package/src/client/react-compiler.ts +20 -15
  52. package/src/client/{compat-surface.ts → react-tier.ts} +64 -64
  53. package/src/client/reference-stub.ts +51 -51
  54. package/src/client/reference.ts +19 -19
  55. package/src/{api → client}/router/events.ts +17 -17
  56. package/src/{api → client}/router/history.ts +16 -16
  57. package/src/{api → client}/router/hub.ts +52 -53
  58. package/src/{api/router.ts → client/router/index.ts} +61 -60
  59. package/src/{api → client}/router/policies.ts +24 -24
  60. package/src/{api → client}/router/runtime.ts +1988 -1992
  61. package/src/{api → client}/router/types.ts +93 -98
  62. package/src/compat/actions/client-plugin.ts +42 -43
  63. package/src/compat/actions/client-stub.ts +14 -14
  64. package/src/compat/actions/{action-client.ts → client.ts} +194 -193
  65. package/src/compat/actions/config.ts +63 -64
  66. package/src/compat/actions/detect.ts +68 -68
  67. package/src/compat/actions/discovery.ts +105 -105
  68. package/src/compat/actions/{action-dispatch.ts → dispatch.ts} +277 -274
  69. package/src/compat/actions/early-submit.ts +1 -1
  70. package/src/compat/actions/endpoint.ts +198 -198
  71. package/src/compat/actions/extensions.ts +811 -0
  72. package/src/compat/actions/flight.ts +23 -23
  73. package/src/compat/actions/form-state.ts +34 -34
  74. package/src/compat/actions/hoist.ts +382 -236
  75. package/src/compat/actions/ids.ts +7 -12
  76. package/src/compat/actions/index.ts +8 -8
  77. package/src/compat/actions/instances.ts +46 -46
  78. package/src/compat/actions/origin.ts +47 -48
  79. package/src/compat/actions/protocol.ts +22 -22
  80. package/src/compat/actions/registry.ts +19 -19
  81. package/src/compat/{misc/action-return.ts → actions/return.ts} +60 -57
  82. package/src/compat/actions/rewrite.ts +125 -125
  83. package/src/compat/actions/{action-router.ts → router.ts} +10 -10
  84. package/src/compat/actions/serve.ts +132 -136
  85. package/src/compat/actions/server-tag.ts +4 -4
  86. package/src/compat/actions/{action-shared.ts → shared.ts} +34 -34
  87. package/src/compat/actions/unrecognized-error.ts +4 -4
  88. package/src/compat/{index.ts → aliases.ts} +112 -109
  89. package/src/compat/bundler/bun-externals.ts +18 -18
  90. package/src/compat/bundler/cjs-exports.ts +271 -223
  91. package/src/compat/bundler/config.ts +116 -111
  92. package/src/compat/bundler/externals.ts +12 -12
  93. package/src/compat/bundler/import-meta-url.ts +19 -19
  94. package/src/compat/bundler/modularize-imports.ts +36 -33
  95. package/src/compat/bundler/new-url-asset.ts +22 -24
  96. package/src/compat/bundler/optimize-package-imports.ts +111 -107
  97. package/src/compat/bundler/polyfill.ts +28 -28
  98. package/src/compat/bundler/react-compiler.ts +35 -29
  99. package/src/compat/bundler/react-profiler.tsx +11 -11
  100. package/src/compat/bundler/relay-transform.ts +48 -47
  101. package/src/compat/bundler/require-context.ts +119 -113
  102. package/src/compat/bundler/resolve-extensions.ts +19 -19
  103. package/src/compat/bundler/source-cache.ts +25 -25
  104. package/src/compat/bundler/static-imports.ts +7 -7
  105. package/src/compat/bundler/symlink-imports.ts +46 -46
  106. package/src/compat/bundler/tsconfig-paths.ts +13 -15
  107. package/src/compat/bundler/wasm.ts +58 -60
  108. package/src/compat/bundler/webpack-loaders.ts +254 -241
  109. package/src/compat/bundler/worker.ts +101 -104
  110. package/src/compat/cache/build-flags.ts +29 -29
  111. package/src/compat/cache/build-prerender-errors.ts +40 -44
  112. package/src/compat/cache/custom-handler.ts +60 -53
  113. package/src/compat/cache/fetch-patch.ts +240 -240
  114. package/src/compat/cache/handler.ts +27 -31
  115. package/src/compat/cache/modern-handler.ts +148 -126
  116. package/src/compat/cache/resume-data-cache.ts +47 -45
  117. package/src/compat/cache/revalidate.ts +233 -232
  118. package/src/compat/cache/runtime-error.ts +35 -35
  119. package/src/compat/cache/use-cache-transform.ts +442 -417
  120. package/src/compat/cache/use-cache.ts +650 -614
  121. package/src/compat/cache-control.ts +140 -142
  122. package/src/compat/client/base-path.ts +21 -20
  123. package/src/compat/client/css-order.ts +18 -18
  124. package/src/compat/client/errors/bare-boundary.ts +11 -11
  125. package/src/compat/client/errors/control-flow.ts +23 -23
  126. package/src/compat/client/errors/error-boundary.ts +61 -61
  127. package/src/compat/client/errors/global-error.ts +101 -91
  128. package/src/compat/client/errors/install.ts +71 -72
  129. package/src/compat/client/errors/lazy.ts +23 -23
  130. package/src/compat/client/errors/primitive-throw.ts +47 -45
  131. package/src/compat/client/errors/soft-refresh.ts +4 -4
  132. package/src/compat/client/link-status.ts +33 -33
  133. package/src/compat/client/{nav-compat-runtime.ts → nav-runtime.ts} +20 -20
  134. package/src/compat/client/{nav-compat.ts → nav.ts} +12 -13
  135. package/src/compat/client/navigation-scroll.ts +63 -63
  136. package/src/compat/client/optimistic-routing.ts +93 -88
  137. package/src/compat/client/prefetch-cache.ts +23 -24
  138. package/src/compat/client/route-announcer.ts +35 -35
  139. package/src/compat/client/segment-cache-policy.ts +20 -20
  140. package/src/compat/client/segment-cache.ts +309 -315
  141. package/src/compat/client/segment-prefetch.ts +127 -132
  142. package/src/compat/client/trailing-slash.ts +5 -4
  143. package/src/compat/css/chunking.ts +113 -116
  144. package/src/compat/css/inline-css.ts +21 -21
  145. package/src/compat/css/lightningcss.ts +37 -38
  146. package/src/compat/css/modules.ts +161 -175
  147. package/src/compat/css/nonce.ts +7 -7
  148. package/src/compat/css/sass-plugin.ts +18 -21
  149. package/src/compat/css/sass.ts +150 -152
  150. package/src/compat/css/styled-jsx-runtime.ts +27 -27
  151. package/src/compat/css/styled-jsx.ts +21 -21
  152. package/src/compat/edge-runtime.ts +27 -27
  153. package/src/compat/{adapter → export}/build-complete.ts +72 -75
  154. package/src/compat/export/client.ts +29 -31
  155. package/src/compat/export/{index.ts → emit.ts} +111 -110
  156. package/src/compat/export/standalone.ts +62 -54
  157. package/src/compat/image-optimizer/cache.ts +51 -49
  158. package/src/compat/image-optimizer/detect.ts +52 -52
  159. package/src/compat/image-optimizer/{index.ts → optimize.ts} +189 -194
  160. package/src/compat/image-optimizer/source.ts +77 -80
  161. package/src/compat/lifecycle/after-scope.ts +26 -26
  162. package/src/compat/lifecycle/after.ts +48 -45
  163. package/src/compat/lifecycle/error-funnel.ts +98 -102
  164. package/src/compat/lifecycle/error-serialize.ts +30 -26
  165. package/src/compat/lifecycle/error-ui.ts +67 -32
  166. package/src/compat/lifecycle/instrumentation-client.ts +36 -38
  167. package/src/compat/lifecycle/instrumentation.ts +85 -85
  168. package/src/compat/lifecycle/node-console.ts +11 -11
  169. package/src/compat/lifecycle/testmode.ts +160 -132
  170. package/src/compat/mdx/compile.ts +60 -57
  171. package/src/compat/mdx/plugin.ts +11 -11
  172. package/src/compat/mdx/{next-mdx-stub.ts → stub.ts} +5 -5
  173. package/src/compat/{metadata-route-artifacts.ts → metadata-artifacts.ts} +195 -191
  174. package/src/compat/metadata.ts +75 -81
  175. package/src/compat/next/cache.ts +68 -69
  176. package/src/compat/next/canonical-url.ts +9 -9
  177. package/src/compat/next/client-cache.ts +19 -19
  178. package/src/compat/next/client-navigation.ts +112 -116
  179. package/src/compat/next/client-only.ts +1 -1
  180. package/src/compat/next/client-script.tsx +99 -93
  181. package/src/compat/next/client-server.ts +10 -10
  182. package/src/compat/next/config-loader.ts +176 -173
  183. package/src/compat/next/config.ts +7 -7
  184. package/src/compat/next/constants.cjs +6 -6
  185. package/src/compat/next/constants.ts +6 -6
  186. package/src/compat/next/custom-server.ts +26 -24
  187. package/src/compat/next/dist/client/components/app-router-headers.ts +21 -21
  188. package/src/compat/next/dist/server/app-render/work-unit-async-storage.external.cjs +3 -4
  189. package/src/compat/next/dist/server/web/spec-extension/revalidate.ts +1 -1
  190. package/src/compat/next/dist/server/web/spec-extension/unstable-cache.ts +1 -1
  191. package/src/compat/next/dist/server/web/spec-extension/unstable-no-store.ts +1 -1
  192. package/src/compat/next/dynamic.tsx +21 -18
  193. package/src/compat/next/error.tsx +52 -52
  194. package/src/compat/next/font/cache.ts +74 -74
  195. package/src/compat/next/font/google.ts +2 -2
  196. package/src/compat/next/font/index.ts +1 -1
  197. package/src/compat/next/font/local.ts +3 -3
  198. package/src/compat/next/font/runtime-client.ts +17 -15
  199. package/src/compat/next/font/runtime.ts +443 -408
  200. package/src/compat/next/font/shared.ts +120 -108
  201. package/src/compat/next/form.tsx +63 -63
  202. package/src/compat/next/head.tsx +2 -2
  203. package/src/compat/next/headers.ts +103 -95
  204. package/src/compat/next/image/client.tsx +220 -0
  205. package/src/compat/next/image/config.ts +56 -58
  206. package/src/compat/next/image/optimizer.ts +40 -36
  207. package/src/compat/next/image/patterns.ts +37 -40
  208. package/src/compat/next/{image-props.ts → image/props.ts} +208 -202
  209. package/src/compat/next/image/shared.ts +65 -57
  210. package/src/compat/next/image/static-metadata.ts +98 -107
  211. package/src/compat/next/image/validate.ts +79 -88
  212. package/src/compat/next/image.tsx +19 -23
  213. package/src/compat/next/index.ts +1 -1
  214. package/src/compat/next/legacy-image.tsx +59 -60
  215. package/src/compat/next/{link-validation-transform.ts → link-transform.ts} +95 -96
  216. package/src/compat/next/link.tsx +158 -158
  217. package/src/compat/next/navigation.cjs +12 -3
  218. package/src/compat/next/navigation.ts +48 -50
  219. package/src/compat/next/offline.ts +27 -27
  220. package/src/compat/next/og.ts +121 -124
  221. package/src/compat/next/preferred-region.ts +13 -14
  222. package/src/compat/next/redirects.ts +58 -56
  223. package/src/compat/next/resource-hints.ts +73 -76
  224. package/src/compat/next/rewrites.ts +130 -133
  225. package/src/compat/next/root-params.ts +45 -45
  226. package/src/compat/next/{optimistic-route-state.ts → route-state.ts} +52 -52
  227. package/src/compat/next/router.cjs +4 -2
  228. package/src/compat/next/router.ts +58 -61
  229. package/src/compat/next/script.tsx +108 -108
  230. package/src/compat/next/server-only.ts +1 -1
  231. package/src/compat/next/server.ts +19 -19
  232. package/src/compat/next/svgr.ts +18 -17
  233. package/src/compat/next/telemetry.ts +24 -24
  234. package/src/compat/next/{image-usage.ts → usage.ts} +70 -39
  235. package/src/compat/next/user-agent.ts +53 -49
  236. package/src/compat/next/web-vitals.ts +22 -24
  237. package/src/compat/otel/api.ts +41 -41
  238. package/src/compat/otel/client-trace-metadata.ts +25 -27
  239. package/src/compat/otel/fetch-span.ts +29 -29
  240. package/src/compat/otel/tracer.ts +331 -331
  241. package/src/compat/pages/api.ts +456 -0
  242. package/src/compat/pages/client-plugin.ts +36 -36
  243. package/src/compat/pages/router-state.ts +34 -34
  244. package/src/compat/pages/{index.ts → router.ts} +130 -135
  245. package/src/compat/ppr/io.ts +12 -12
  246. package/src/compat/ppr/missing-root-params.ts +34 -38
  247. package/src/compat/ppr/root-params-scan.ts +66 -66
  248. package/src/compat/ppr/root-params-transform.ts +24 -26
  249. package/src/compat/ppr/root-params.ts +30 -30
  250. package/src/compat/ppr/segment-config-incompat.ts +6 -7
  251. package/src/compat/protocol.ts +71 -70
  252. package/src/compat/react/action-state.ts +47 -48
  253. package/src/compat/react/client-lite.ts +15 -15
  254. package/src/compat/react/client.ts +4 -4
  255. package/src/compat/react/compiler-runtime.ts +11 -11
  256. package/src/compat/react/dom-client.ts +44 -44
  257. package/src/compat/react/dom-react-server.ts +10 -16
  258. package/src/compat/react/dom-server.ts +10 -10
  259. package/src/compat/react/dom.ts +52 -52
  260. package/src/compat/react/hooks-extra.ts +34 -35
  261. package/src/compat/react/parity.ts +64 -61
  262. package/src/compat/react/preact.ts +81 -82
  263. package/src/compat/react/react-server.ts +28 -28
  264. package/src/compat/react/router-shim.ts +1 -1
  265. package/src/compat/react/server-component-use.ts +8 -8
  266. package/src/compat/react/server-inserted-html.ts +30 -31
  267. package/src/compat/react/server.ts +53 -55
  268. package/src/compat/react/use.ts +32 -32
  269. package/src/compat/react/view-transition.ts +20 -20
  270. package/src/compat/register/actions.ts +35 -824
  271. package/src/compat/register/boot.ts +41 -41
  272. package/src/compat/register/build-tier.ts +5 -5
  273. package/src/compat/register/build.ts +74 -70
  274. package/src/compat/register/bundler.ts +161 -156
  275. package/src/compat/register/cache.ts +20 -20
  276. package/src/compat/register/client-errors.ts +3 -3
  277. package/src/compat/register/config.ts +6 -6
  278. package/src/compat/register/css-extras.ts +30 -34
  279. package/src/compat/register/edge-runtime.ts +3 -3
  280. package/src/compat/register/errors.ts +10 -12
  281. package/src/compat/register/export.ts +16 -16
  282. package/src/compat/register/font.ts +11 -11
  283. package/src/compat/register/hooks.ts +2 -2
  284. package/src/compat/register/image.ts +40 -40
  285. package/src/compat/register/index.ts +59 -62
  286. package/src/compat/register/instrumentation-client.ts +10 -10
  287. package/src/compat/register/lifecycle.ts +25 -28
  288. package/src/compat/register/mdx.ts +10 -10
  289. package/src/compat/register/middleware.ts +226 -16
  290. package/src/compat/register/otel.ts +80 -88
  291. package/src/compat/register/pages-api.ts +10 -463
  292. package/src/compat/register/ppr.ts +16 -16
  293. package/src/compat/register/protocol.ts +17 -18
  294. package/src/compat/register/proxy.ts +49 -51
  295. package/src/compat/register/render.ts +79 -76
  296. package/src/compat/register/routing.ts +162 -159
  297. package/src/compat/register/segment.ts +24 -1897
  298. package/src/compat/register/static-image.ts +3 -3
  299. package/src/compat/register/{misc.ts → taint.ts} +9 -9
  300. package/src/compat/register/typed-routes.ts +14 -14
  301. package/src/compat/register/{usecache.ts → use-cache.ts} +39 -39
  302. package/src/compat/register/validation.ts +18 -18
  303. package/src/compat/segment/loading-boundary.ts +43 -45
  304. package/src/compat/segment/page-slot.ts +69 -69
  305. package/src/compat/segment/serve.ts +1884 -0
  306. package/src/compat/segment/tree.ts +113 -112
  307. package/src/compat/segment/vary-key.ts +38 -38
  308. package/src/compat/segment/vary-params.ts +138 -142
  309. package/src/compat/static-params.ts +14 -12
  310. package/src/compat/tsconfig-defaults.ts +87 -91
  311. package/src/compat/typecheck/{index.ts → check.ts} +234 -212
  312. package/src/compat/typecheck/worker.ts +15 -12
  313. package/src/compat/typed-routes/{index.ts → generate.ts} +36 -36
  314. package/src/compat/typed-routes/manifest.ts +174 -170
  315. package/src/compat/typed-routes/typegen.ts +127 -110
  316. package/src/compat/validation/errors.ts +16 -19
  317. package/src/compat/validation/prerender-diagnostics.ts +521 -504
  318. package/src/compat/validation/{index.ts → validate.ts} +647 -648
  319. package/src/compat-bootstrap.ts +16 -16
  320. package/src/config.ts +69 -69
  321. package/src/css/build.ts +230 -227
  322. package/src/css/postcss.ts +79 -80
  323. package/src/css/worker.ts +14 -15
  324. package/src/dev/client-actions.ts +10 -10
  325. package/src/dev/client-chunk-store.ts +27 -27
  326. package/src/dev/{client-key-cache.ts → restart/client-key.ts} +76 -76
  327. package/src/dev/{restart-cache.ts → restart/enabled.ts} +1 -1
  328. package/src/dev/{global-css-cache.ts → restart/global-css.ts} +91 -83
  329. package/src/dev/{node-module-bundle-cache.ts → restart/node-modules.ts} +24 -24
  330. package/src/dev/{route-bundle-key-cache.ts → restart/route-bundle-key.ts} +53 -53
  331. package/src/dev/{route-facts-cache.ts → restart/route-facts.ts} +82 -82
  332. package/src/dev/server.ts +804 -820
  333. package/src/env.ts +46 -43
  334. package/src/extensions.ts +491 -478
  335. package/src/index.ts +8 -8
  336. package/src/internal.ts +20 -23
  337. package/src/{islands → render}/boundary-error.ts +3 -3
  338. package/src/render/hooks.ts +71 -71
  339. package/src/render/island-context.ts +14 -14
  340. package/src/render/metadata.ts +310 -310
  341. package/src/{ppr-postpone.ts → render/postpone.ts} +5 -5
  342. package/src/{ppr.ts → render/ppr.ts} +244 -245
  343. package/src/render/renderer.ts +2076 -2082
  344. package/src/render/resource-hints.ts +16 -17
  345. package/src/render/slots.tsx +224 -235
  346. package/src/{islands → render}/static-children.ts +9 -12
  347. package/src/{islands → render}/static-slots.ts +37 -37
  348. package/src/{cache/context.ts → request/cache.ts} +20 -20
  349. package/src/request/context.ts +107 -107
  350. package/src/{dynamic/source.ts → resolve/dynamic.ts} +139 -139
  351. package/src/resolve/engine.ts +90 -77
  352. package/src/resolve/imports.ts +475 -463
  353. package/src/resolve/scan-facts.ts +318 -296
  354. package/src/resolve/source-text.ts +37 -37
  355. package/src/{dynamic → resolve}/tree-shake.ts +132 -128
  356. package/src/routing/forwarded.ts +19 -19
  357. package/src/routing/handler.ts +84 -91
  358. package/src/routing/href.ts +69 -70
  359. package/src/routing/{metadata.ts → metadata-files.ts} +403 -401
  360. package/src/{proxy.ts → routing/proxy.ts} +306 -312
  361. package/src/routing/{request-runtime.ts → request-environment.ts} +10 -10
  362. package/src/routing/routes.ts +827 -815
  363. package/src/routing/slots.ts +164 -160
  364. package/src/runtime/loader.ts +952 -0
  365. package/src/{dev → runtime}/module-cache.ts +309 -287
  366. package/src/{dev → runtime}/module-generations.ts +9 -9
  367. package/src/{dev → runtime}/module-transform.ts +81 -72
  368. package/src/{dev/imports.ts → runtime/modules.ts} +934 -847
  369. package/src/runtime/{server.ts → vendor-build.ts} +848 -1696
  370. package/src/runtime/vendor.ts +425 -404
  371. package/src/styles.d.ts +9 -0
  372. package/src/types.ts +320 -335
  373. package/src/utils/ansi.ts +5 -5
  374. package/src/utils/{source.ts → code.ts} +15 -12
  375. package/src/utils/content-type.ts +3 -3
  376. package/src/utils/decode.ts +2 -2
  377. package/src/utils/dev-profile.ts +13 -13
  378. package/src/utils/error-log.ts +6 -6
  379. package/src/utils/esbuild.ts +18 -18
  380. package/src/utils/fs-cache.ts +13 -13
  381. package/src/utils/fs.ts +57 -49
  382. package/src/utils/html.ts +20 -24
  383. package/src/utils/native-require.ts +8 -8
  384. package/src/utils/serialize.ts +139 -146
  385. package/src/utils/verbose.ts +18 -18
  386. package/src/cli/analyze-print.ts +0 -181
  387. package/src/compat/middleware/manifest.ts +0 -210
  388. package/src/compat/next/image-client.tsx +0 -215
  389. package/src/compat/next/link-usage.ts +0 -29
  390. package/src/css/index.ts +0 -2
  391. package/src/render/index.ts +0 -1
  392. package/src/style-modules.d.ts +0 -9
@@ -1,37 +1,37 @@
1
- import { createRequire } from 'node:module';
2
- import { access, mkdir, readdir, readFile, writeFile } from 'node:fs/promises';
3
- import path from 'node:path';
4
- import type { ResolvedConfig } from '../config';
5
- import type { BuildManifest, RouteManifestEntry, StaticFileMetadata } from '../types';
6
- import { nextCompatEnabled } from './index';
7
- import { discoverStaticMetadataFiles } from '../routing/metadata';
8
- import { toPosixPath } from '../utils/fs';
1
+ import { createRequire } from 'node:module'
2
+ import { access, mkdir, readdir, readFile, writeFile } from 'node:fs/promises'
3
+ import path from 'node:path'
4
+ import type { ResolvedConfig } from '../config'
5
+ import type { BuildManifest, RouteManifestEntry, StaticFileMetadata } from '../types'
6
+ import { nextCompatEnabled } from './aliases'
7
+ import { discoverStaticMetadataFiles } from '../routing/metadata-files'
8
+ import { toPosixPath } from '../utils/fs'
9
9
 
10
10
  interface EmitMetadataRouteArtifactsContext {
11
- config: ResolvedConfig;
12
- manifest: BuildManifest;
11
+ config: ResolvedConfig
12
+ manifest: BuildManifest
13
13
  }
14
14
 
15
15
  interface RouteManifestFile {
16
- version?: number;
17
- middleware?: Record<string, Record<string, unknown>>;
18
- functions?: Record<string, Record<string, unknown>>;
19
- sortedMiddleware?: unknown[];
16
+ version?: number
17
+ middleware?: Record<string, Record<string, unknown>>
18
+ functions?: Record<string, Record<string, unknown>>
19
+ sortedMiddleware?: unknown[]
20
20
  }
21
21
 
22
- let foundGeistFontPath: string | undefined;
22
+ let foundGeistFontPath: string | undefined
23
23
 
24
24
  export async function emitMetadataRouteArtifacts(
25
25
  ctx: EmitMetadataRouteArtifactsContext,
26
26
  ): Promise<void> {
27
- if (!nextCompatEnabled(ctx.config)) return;
27
+ if (!nextCompatEnabled(ctx.config)) return
28
28
 
29
29
  const routes = ctx.manifest.routes.filter(
30
30
  route => route.kind === 'handler' && route.metadataRoute !== undefined,
31
- );
32
- if (routes.length === 0) return;
31
+ )
32
+ if (routes.length === 0) return
33
33
 
34
- const outPath = ctx.config.outPath;
34
+ const outPath = ctx.config.outPath
35
35
  const outputRoots = Array.from(
36
36
  new Set([
37
37
  outPath,
@@ -39,33 +39,33 @@ export async function emitMetadataRouteArtifacts(
39
39
  path.join(path.dirname(outPath), '.next'),
40
40
  path.resolve(process.cwd(), '.next'),
41
41
  ]),
42
- );
43
- const staticFiles = ctx.manifest.staticFiles ?? {};
44
- const routeFilesById = staticFilesByRouteId(staticFiles);
45
- const appDir = path.join(ctx.config.root, ctx.config.appDir);
42
+ )
43
+ const staticFiles = ctx.manifest.staticFiles ?? {}
44
+ const routeFilesById = staticFilesByRouteId(staticFiles)
45
+ const appDir = path.join(ctx.config.root, ctx.config.appDir)
46
46
 
47
- const emittedRouteDirs = new Set<string>();
47
+ const emittedRouteDirs = new Set<string>()
48
48
 
49
49
  for (const route of routes) {
50
- const nextPath = toAppPath(route, appDir);
51
- const routeDir = removeLeadingSlash(nextPath);
52
- emittedRouteDirs.add(routeDir);
50
+ const nextPath = toAppPath(route, appDir)
51
+ const routeDir = removeLeadingSlash(nextPath)
52
+ emittedRouteDirs.add(routeDir)
53
53
  // A dynamic-code metadata route handler executes user code, so Next lists
54
54
  // its client-reference manifest in the route trace (route.js.nft.json) —
55
55
  // the same shape as an app page's page_client-reference-manifest.js. The
56
56
  // opengraph/icon image routes additionally trace the Geist font they load.
57
57
  const fontPaths =
58
- route.metadataRoute?.kind === 'opengraph-image' ? await resolveGeistFontFiles() : [];
58
+ route.metadataRoute?.kind === 'opengraph-image' ? await resolveGeistFontFiles() : []
59
59
 
60
60
  for (const root of outputRoots) {
61
- const routeModuleDir = path.join(root, 'server', 'app', routeDir);
62
- await mkdir(routeModuleDir, { recursive: true });
63
- await writeFile(path.join(routeModuleDir, 'route.js'), routeJsModule(route), 'utf8');
61
+ const routeModuleDir = path.join(root, 'server', 'app', routeDir)
62
+ await mkdir(routeModuleDir, { recursive: true })
63
+ await writeFile(path.join(routeModuleDir, 'route.js'), routeJsModule(route), 'utf8')
64
64
  await writeFile(
65
65
  path.join(routeModuleDir, 'route_client-reference-manifest.js'),
66
66
  'self.__RSC_MANIFEST={}\n',
67
67
  'utf8',
68
- );
68
+ )
69
69
  await writeFile(
70
70
  path.join(routeModuleDir, 'route.js.nft.json'),
71
71
  `${JSON.stringify(
@@ -74,21 +74,21 @@ export async function emitMetadataRouteArtifacts(
74
74
  2,
75
75
  )}\n`,
76
76
  'utf8',
77
- );
77
+ )
78
78
 
79
- if (isForceDynamicRoute(route)) continue;
79
+ if (isForceDynamicRoute(route)) continue
80
80
 
81
- const outputs = routeFilesById.get(route.id) ?? [];
81
+ const outputs = routeFilesById.get(route.id) ?? []
82
82
  for (const relative of outputs) {
83
- await writeStaticMetadataArtifacts(outPath, root, relative, staticFiles[relative]);
83
+ await writeStaticMetadataArtifacts(outPath, root, relative, staticFiles[relative])
84
84
  }
85
85
  }
86
86
  }
87
87
 
88
- await emitStaticMetadataRouteTraces(outputRoots, appDir, emittedRouteDirs);
89
- await writeAppPathsManifest(outputRoots, routes, appDir);
90
- await mergeMiddlewareFunctionsManifest(outputRoots, routes, appDir, ctx.manifest.routes);
91
- await writePrerenderManifests(outputRoots, ctx.manifest);
88
+ await emitStaticMetadataRouteTraces(outputRoots, appDir, emittedRouteDirs)
89
+ await writeAppPathsManifest(outputRoots, routes, appDir)
90
+ await mergeMiddlewareFunctionsManifest(outputRoots, routes, appDir, ctx.manifest.routes)
91
+ await writePrerenderManifests(outputRoots, ctx.manifest)
92
92
  }
93
93
 
94
94
  const prerenderAllowHeader = [
@@ -98,22 +98,22 @@ const prerenderAllowHeader = [
98
98
  'x-prerender-revalidate-if-generated',
99
99
  'x-next-revalidated-tags',
100
100
  'x-next-revalidate-tag-token',
101
- ];
101
+ ]
102
102
 
103
103
  const prerenderBypass = [
104
104
  { key: 'next-action', type: 'header' },
105
105
  { key: 'content-type', type: 'header', value: 'multipart/form-data;.*' },
106
- ];
106
+ ]
107
107
 
108
108
  async function writePrerenderManifests(outputRoots: string[], manifest: BuildManifest) {
109
- const byId = new Map(manifest.routes.map(route => [route.id, route]));
110
- const entries: Record<string, unknown> = {};
109
+ const byId = new Map(manifest.routes.map(route => [route.id, route]))
110
+ const entries: Record<string, unknown> = {}
111
111
 
112
112
  for (const [relative, metadata] of Object.entries(manifest.staticFiles ?? {})) {
113
- const route = metadata.routeId ? byId.get(metadata.routeId) : undefined;
114
- if (route && isEdgeRoute(route)) continue;
115
- const pathname = staticFilePathname(relative);
116
- entries[pathname] = prerenderEntry(pathname, metadata, route);
113
+ const route = metadata.routeId ? byId.get(metadata.routeId) : undefined
114
+ if (route && isEdgeRoute(route)) continue
115
+ const pathname = staticFilePathname(relative)
116
+ entries[pathname] = prerenderEntry(pathname, metadata, route)
117
117
  }
118
118
 
119
119
  for (const route of manifest.routes) {
@@ -121,22 +121,22 @@ async function writePrerenderManifests(outputRoots: string[], manifest: BuildMan
121
121
  // generated id; Next lists each as a prerendered route even though the
122
122
  // pattern itself carries a param.
123
123
  for (const generated of route.metadataRoute?.generatedRoutes ?? []) {
124
- if (entries[generated] || isEdgeRoute(route) || route.usesRequest) continue;
125
- entries[generated] = prerenderEntry(generated, undefined, route);
124
+ if (entries[generated] || isEdgeRoute(route) || route.usesRequest) continue
125
+ entries[generated] = prerenderEntry(generated, undefined, route)
126
126
  }
127
- if (entries[route.route] || !isStaticPrerenderRoute(route)) continue;
128
- entries[route.route] = prerenderEntry(route.route, undefined, route);
127
+ if (entries[route.route] || !isStaticPrerenderRoute(route)) continue
128
+ entries[route.route] = prerenderEntry(route.route, undefined, route)
129
129
  }
130
130
 
131
131
  for (const root of outputRoots) {
132
- const file = path.join(root, 'prerender-manifest.json');
132
+ const file = path.join(root, 'prerender-manifest.json')
133
133
  const existing = await readJsonManifest<{
134
- routes?: Record<string, unknown>;
135
- dynamicRoutes?: Record<string, unknown>;
136
- notFoundRoutes?: string[];
137
- preview?: Record<string, string>;
138
- }>(file);
139
- await mkdir(path.dirname(file), { recursive: true });
134
+ routes?: Record<string, unknown>
135
+ dynamicRoutes?: Record<string, unknown>
136
+ notFoundRoutes?: string[]
137
+ preview?: Record<string, string>
138
+ }>(file)
139
+ await mkdir(path.dirname(file), { recursive: true })
140
140
  await writeFile(
141
141
  file,
142
142
  `${JSON.stringify(
@@ -154,28 +154,27 @@ async function writePrerenderManifests(outputRoots: string[], manifest: BuildMan
154
154
  null,
155
155
  2,
156
156
  )}\n`,
157
- );
157
+ )
158
158
  }
159
159
  }
160
160
 
161
161
  function staticFilePathname(relative: string) {
162
- if (relative === 'index.html') return '/';
163
- if (relative.endsWith('/index.html')) return `/${relative.slice(0, -'/index.html'.length)}`;
164
- if (relative.endsWith('.html')) return `/${relative.slice(0, -'.html'.length)}`;
165
- return `/${relative}`;
162
+ if (relative === 'index.html') return '/'
163
+ if (relative.endsWith('/index.html')) return `/${relative.slice(0, -'/index.html'.length)}`
164
+ if (relative.endsWith('.html')) return `/${relative.slice(0, -'.html'.length)}`
165
+ return `/${relative}`
166
166
  }
167
167
 
168
168
  function isStaticPrerenderRoute(route: RouteManifestEntry) {
169
- if (route.mode !== 'static' || route.usesRequest || isEdgeRoute(route)) return false;
170
- if (route.kind === 'page') return route.params.length === 0 && !route.catchAll;
171
- return route.kind === 'handler' && route.metadataRoute !== undefined && route.params.length === 0;
169
+ if (route.mode !== 'static' || route.usesRequest || isEdgeRoute(route)) return false
170
+ if (route.kind === 'page') return route.params.length === 0 && !route.catchAll
171
+ return route.kind === 'handler' && route.metadataRoute !== undefined && route.params.length === 0
172
172
  }
173
173
 
174
174
  function isEdgeRoute(route: RouteManifestEntry) {
175
175
  return (
176
- route.segmentConfig?.runtime === 'edge' ||
177
- route.segmentConfig?.runtime === 'experimental-edge'
178
- );
176
+ route.segmentConfig?.runtime === 'edge' || route.segmentConfig?.runtime === 'experimental-edge'
177
+ )
179
178
  }
180
179
 
181
180
  function prerenderEntry(
@@ -189,20 +188,20 @@ function prerenderEntry(
189
188
  dataRoute: pathname === '/' ? '/index.rsc' : `${pathname}.rsc`,
190
189
  allowHeader: prerenderAllowHeader,
191
190
  experimentalBypassFor: prerenderBypass,
192
- };
191
+ }
193
192
  }
194
193
 
195
194
  function staticFilesByRouteId(
196
195
  staticFiles: Record<string, StaticFileMetadata>,
197
196
  ): Map<string, string[]> {
198
- const routeFilesById = new Map<string, string[]>();
197
+ const routeFilesById = new Map<string, string[]>()
199
198
  for (const [relative, metadata] of Object.entries(staticFiles)) {
200
- if (!metadata.routeId) continue;
201
- const existing = routeFilesById.get(metadata.routeId) ?? [];
202
- existing.push(relative);
203
- routeFilesById.set(metadata.routeId, existing);
199
+ if (!metadata.routeId) continue
200
+ const existing = routeFilesById.get(metadata.routeId) ?? []
201
+ existing.push(relative)
202
+ routeFilesById.set(metadata.routeId, existing)
204
203
  }
205
- return routeFilesById;
204
+ return routeFilesById
206
205
  }
207
206
 
208
207
  /**
@@ -217,17 +216,17 @@ async function emitStaticMetadataRouteTraces(
217
216
  emittedRouteDirs: Set<string>,
218
217
  ): Promise<void> {
219
218
  for (const file of discoverStaticMetadataFiles(appDir)) {
220
- const routeDir = file.outputPath;
221
- if (emittedRouteDirs.has(routeDir)) continue;
219
+ const routeDir = file.outputPath
220
+ if (emittedRouteDirs.has(routeDir)) continue
222
221
  for (const root of outputRoots) {
223
- const dir = path.join(root, 'server', 'app', routeDir);
224
- await mkdir(dir, { recursive: true });
225
- await writeFile(path.join(dir, 'route.js'), 'export default {}\n', 'utf8');
222
+ const dir = path.join(root, 'server', 'app', routeDir)
223
+ await mkdir(dir, { recursive: true })
224
+ await writeFile(path.join(dir, 'route.js'), 'export default {}\n', 'utf8')
226
225
  await writeFile(
227
226
  path.join(dir, 'route.js.nft.json'),
228
227
  `${JSON.stringify({ version: 1, files: [] }, null, 2)}\n`,
229
228
  'utf8',
230
- );
229
+ )
231
230
  }
232
231
  }
233
232
  }
@@ -237,21 +236,18 @@ async function writeAppPathsManifest(
237
236
  routes: RouteManifestEntry[],
238
237
  appDir: string,
239
238
  ): Promise<void> {
240
- const nextEntries: Record<string, string> = {};
239
+ const nextEntries: Record<string, string> = {}
241
240
  for (const route of routes) {
242
- const appPath = toAppPath(route, appDir);
243
- const key = `${appPath}/route`;
244
- nextEntries[key] = `app${appPath}/route.js`;
241
+ const appPath = toAppPath(route, appDir)
242
+ const key = `${appPath}/route`
243
+ nextEntries[key] = `app${appPath}/route.js`
245
244
  }
246
245
 
247
246
  for (const root of outputRoots) {
248
- const manifestPath = path.join(root, 'server', 'app-paths-manifest.json');
249
- const existing = (await readJsonManifest<Record<string, string>>(manifestPath)) ?? {};
250
- await mkdir(path.dirname(manifestPath), { recursive: true });
251
- await writeFile(
252
- manifestPath,
253
- `${JSON.stringify({ ...existing, ...nextEntries }, null, 2)}\n`,
254
- );
247
+ const manifestPath = path.join(root, 'server', 'app-paths-manifest.json')
248
+ const existing = (await readJsonManifest<Record<string, string>>(manifestPath)) ?? {}
249
+ await mkdir(path.dirname(manifestPath), { recursive: true })
250
+ await writeFile(manifestPath, `${JSON.stringify({ ...existing, ...nextEntries }, null, 2)}\n`)
255
251
  }
256
252
  }
257
253
 
@@ -262,60 +258,68 @@ async function mergeMiddlewareFunctionsManifest(
262
258
  allRoutes: RouteManifestEntry[],
263
259
  ): Promise<void> {
264
260
  const edgeRoutes = routes.filter(
265
- route => route.segmentConfig?.runtime === 'edge' || route.segmentConfig?.runtime === 'experimental-edge',
266
- );
267
- const edgePages = allRoutes.filter(route => route.kind === 'page' && isEdgeRoute(route));
268
- if (edgeRoutes.length === 0 && edgePages.length === 0) return;
269
-
270
- const routeEntries = edgeRoutes.map(route => ({ route: `${toAppPath(route, appDir)}/route`, value: {} }));
271
- const sharedImageChunk = 'server/edge-chunks/image-response.js';
261
+ route =>
262
+ route.segmentConfig?.runtime === 'edge' ||
263
+ route.segmentConfig?.runtime === 'experimental-edge',
264
+ )
265
+ const edgePages = allRoutes.filter(route => route.kind === 'page' && isEdgeRoute(route))
266
+ if (edgeRoutes.length === 0 && edgePages.length === 0) return
267
+
268
+ const routeEntries = edgeRoutes.map(route => ({
269
+ route: `${toAppPath(route, appDir)}/route`,
270
+ value: {},
271
+ }))
272
+ const sharedImageChunk = 'server/edge-chunks/image-response.js'
272
273
  const hasImageResponseRoute = routes.some(route =>
273
274
  ['opengraph-image', 'twitter-image', 'apple-icon', 'icon'].includes(
274
275
  route.metadataRoute?.kind ?? '',
275
276
  ),
276
- );
277
+ )
277
278
 
278
279
  for (const root of outputRoots) {
279
- const manifestPath = path.join(root, 'server', 'middleware-manifest.json');
280
- const manifest = await readJsonManifest<RouteManifestFile>(manifestPath);
281
- const target: RouteManifestFile = {
282
- version: 3,
283
- sortedMiddleware: [],
284
- middleware: {},
285
- functions: {},
286
- ...(manifest ?? {}),
287
- };
288
- target.functions = target.functions ?? {};
280
+ const manifestPath = path.join(root, 'server', 'middleware-manifest.json')
281
+ const manifest = await readJsonManifest<RouteManifestFile>(manifestPath)
282
+ const target: RouteManifestFile = {
283
+ version: 3,
284
+ sortedMiddleware: [],
285
+ middleware: {},
286
+ functions: {},
287
+ ...(manifest ?? {}),
288
+ }
289
+ target.functions = target.functions ?? {}
289
290
  for (const { route, value } of routeEntries) {
290
- target.functions[route] = target.functions[route] ?? value;
291
+ target.functions[route] = target.functions[route] ?? value
291
292
  }
292
293
  if (hasImageResponseRoute && edgePages.length > 0) {
293
- const chunkPath = path.join(root, sharedImageChunk);
294
- await mkdir(path.dirname(chunkPath), { recursive: true });
295
- await writeFile(chunkPath, 'export const loadAdditionalAsset = true\n');
294
+ const chunkPath = path.join(root, sharedImageChunk)
295
+ await mkdir(path.dirname(chunkPath), { recursive: true })
296
+ await writeFile(chunkPath, 'export const loadAdditionalAsset = true\n')
296
297
  for (const page of edgePages) {
297
- const key = page.route === '/' ? '/page' : `${page.route}/page`;
298
- target.functions[key] = { files: [sharedImageChunk] };
298
+ const key = page.route === '/' ? '/page' : `${page.route}/page`
299
+ target.functions[key] = { files: [sharedImageChunk] }
299
300
  }
300
301
  }
301
- await mkdir(path.dirname(manifestPath), { recursive: true });
302
- await writeFile(manifestPath, `${JSON.stringify(target, null, 2)}\n`);
302
+ await mkdir(path.dirname(manifestPath), { recursive: true })
303
+ await writeFile(manifestPath, `${JSON.stringify(target, null, 2)}\n`)
303
304
  }
304
305
  }
305
306
 
306
307
  function isForceDynamicRoute(route: RouteManifestEntry): boolean {
307
- return route.segmentConfig?.dynamic === 'force-dynamic';
308
+ return route.segmentConfig?.dynamic === 'force-dynamic'
308
309
  }
309
310
 
310
- function toRouteMeta(metadata: StaticFileMetadata): { status: number; headers: Record<string, string> } {
311
- const headers: Record<string, string> = {};
311
+ function toRouteMeta(metadata: StaticFileMetadata): {
312
+ status: number
313
+ headers: Record<string, string>
314
+ } {
315
+ const headers: Record<string, string> = {}
312
316
  for (const [name, value] of metadata.headers ?? []) {
313
- headers[name.toLowerCase()] = value;
317
+ headers[name.toLowerCase()] = value
314
318
  }
315
319
  return {
316
320
  status: metadata.status,
317
321
  headers,
318
- };
322
+ }
319
323
  }
320
324
 
321
325
  async function writeStaticMetadataArtifacts(
@@ -324,135 +328,135 @@ async function writeStaticMetadataArtifacts(
324
328
  relative: string,
325
329
  metadata: StaticFileMetadata | undefined,
326
330
  ): Promise<void> {
327
- if (!metadata) return;
328
- const source = path.join(outPath, 'public', relative);
329
- const outputBase = path.join(root, 'server', 'app', toPosixPath(relative));
330
- await mkdir(path.dirname(outputBase), { recursive: true });
331
- const routeMeta = JSON.stringify(toRouteMeta(metadata));
332
- await writeFile(`${outputBase}.meta`, routeMeta, 'utf8');
331
+ if (!metadata) return
332
+ const source = path.join(outPath, 'public', relative)
333
+ const outputBase = path.join(root, 'server', 'app', toPosixPath(relative))
334
+ await mkdir(path.dirname(outputBase), { recursive: true })
335
+ const routeMeta = JSON.stringify(toRouteMeta(metadata))
336
+ await writeFile(`${outputBase}.meta`, routeMeta, 'utf8')
333
337
  try {
334
- await access(source);
338
+ await access(source)
335
339
  } catch {
336
- return;
340
+ return
337
341
  }
338
- await writeFile(`${outputBase}.body`, await readFile(source));
342
+ await writeFile(`${outputBase}.body`, await readFile(source))
339
343
  }
340
344
 
341
345
  function routeJsModule(route: RouteManifestEntry): string {
342
- const runtime = route.segmentConfig?.runtime ?? 'nodejs';
346
+ const runtime = route.segmentConfig?.runtime ?? 'nodejs'
343
347
  const data = JSON.stringify({
344
348
  segmentConfig: route.segmentConfig ?? null,
345
349
  runtime,
346
350
  metadataRoute: route.metadataRoute?.kind,
347
351
  route: route.route,
348
- });
349
- return `export default ${data}\n`;
352
+ })
353
+ return `export default ${data}\n`
350
354
  }
351
355
 
352
356
  function toAppPath(route: RouteManifestEntry, appDir: string): string {
353
- const generated = route.metadataRoute?.generatedParam;
354
- const normalized = route.route.replace(/^\/+|\/+$/g, '');
355
- const fileSegments = routeFileGroups(route.file, appDir);
356
- const routeSegments = normalized.length > 0 ? normalized.split('/') : [];
357
- const converted = routeSegments.map(segment => routeSegmentToNextPath(segment, generated));
358
- const nextPathSegments = [...fileSegments, ...converted];
359
- return `/${nextPathSegments.join('/')}`;
357
+ const generated = route.metadataRoute?.generatedParam
358
+ const normalized = route.route.replace(/^\/+|\/+$/g, '')
359
+ const fileSegments = routeFileGroups(route.file, appDir)
360
+ const routeSegments = normalized.length > 0 ? normalized.split('/') : []
361
+ const converted = routeSegments.map(segment => routeSegmentToNextPath(segment, generated))
362
+ const nextPathSegments = [...fileSegments, ...converted]
363
+ return `/${nextPathSegments.join('/')}`
360
364
  }
361
365
 
362
366
  function routeSegmentToNextPath(segment: string, generatedParam?: string): string {
363
- const match = /^:([^*.]+)(\*)?(\..*)?$/.exec(segment);
364
- if (!match) return segment;
365
- const name = match[1] ?? '';
366
- const star = match[2] ? '...' : '';
367
- const suffix = match[3] ?? '';
368
- const key = generatedParam && name === 'id' ? generatedParam : name;
369
- return `[${star}${key}]${generatedParam && name === 'id' ? '' : suffix}`;
367
+ const match = /^:([^*.]+)(\*)?(\..*)?$/.exec(segment)
368
+ if (!match) return segment
369
+ const name = match[1] ?? ''
370
+ const star = match[2] ? '...' : ''
371
+ const suffix = match[3] ?? ''
372
+ const key = generatedParam && name === 'id' ? generatedParam : name
373
+ return `[${star}${key}]${generatedParam && name === 'id' ? '' : suffix}`
370
374
  }
371
375
 
372
376
  function routeFileGroups(file: string, appDir: string): string[] {
373
- const relative = toPosixPath(path.relative(appDir, file));
374
- const parts = relative.split('/').filter(Boolean);
375
- const withoutLeaf = parts.slice(0, -1);
376
- const groups: string[] = [];
377
+ const relative = toPosixPath(path.relative(appDir, file))
378
+ const parts = relative.split('/').filter(Boolean)
379
+ const withoutLeaf = parts.slice(0, -1)
380
+ const groups: string[] = []
377
381
  for (const segment of withoutLeaf) {
378
- if (!segment.startsWith('(') || !segment.endsWith(')')) break;
379
- groups.push(segment);
382
+ if (!segment.startsWith('(') || !segment.endsWith(')')) break
383
+ groups.push(segment)
380
384
  }
381
- return groups;
385
+ return groups
382
386
  }
383
387
 
384
388
  function removeLeadingSlash(pathValue: string) {
385
- return pathValue.replace(/^\//, '');
389
+ return pathValue.replace(/^\//, '')
386
390
  }
387
391
 
388
392
  async function readJsonManifest<T>(filePath: string): Promise<T | undefined> {
389
393
  try {
390
- const raw = await readFile(filePath, 'utf8');
391
- return JSON.parse(raw) as T;
394
+ const raw = await readFile(filePath, 'utf8')
395
+ return JSON.parse(raw) as T
392
396
  } catch {
393
- return undefined;
397
+ return undefined
394
398
  }
395
399
  }
396
400
 
397
401
  async function resolveGeistFontFiles(): Promise<string[]> {
398
- if (foundGeistFontPath) return [foundGeistFontPath];
399
- const req = createRequire(process.cwd() + '/');
400
- const candidateRoots = resolveVercelOgRoots(req);
402
+ if (foundGeistFontPath) return [foundGeistFontPath]
403
+ const req = createRequire(process.cwd() + '/')
404
+ const candidateRoots = resolveVercelOgRoots(req)
401
405
  for (const root of candidateRoots) {
402
- const files = await findFiles(root, 'Geist-Regular.ttf');
403
- if (files.length === 0) continue;
404
- foundGeistFontPath = files[0];
405
- return files.slice(0, 1);
406
+ const files = await findFiles(root, 'Geist-Regular.ttf')
407
+ if (files.length === 0) continue
408
+ foundGeistFontPath = files[0]
409
+ return files.slice(0, 1)
406
410
  }
407
- return [];
411
+ return []
408
412
  }
409
413
 
410
414
  function resolveVercelOgRoots(req: ReturnType<typeof createRequire>): string[] {
411
- const roots: string[] = [];
415
+ const roots: string[] = []
412
416
  for (const spec of ['@vercel/og/package.json', 'next/package.json']) {
413
417
  try {
414
- roots.push(path.dirname(req.resolve(spec)));
418
+ roots.push(path.dirname(req.resolve(spec)))
415
419
  } catch {
416
420
  // package not present in the app; skip
417
421
  }
418
422
  }
419
- return roots;
423
+ return roots
420
424
  }
421
425
 
422
426
  async function findFiles(root: string, targetName: string): Promise<string[]> {
423
- const found: string[] = [];
424
- const stack = [root];
425
- const maxDepth = 6;
427
+ const found: string[] = []
428
+ const stack = [root]
429
+ const maxDepth = 6
426
430
  while (stack.length > 0) {
427
- const current = stack.pop();
428
- if (!current) continue;
429
- const normalizedRoot = root.replace(/\\/g, '/');
430
- const normalizedCurrent = current.replace(/\\/g, '/');
431
+ const current = stack.pop()
432
+ if (!current) continue
433
+ const normalizedRoot = root.replace(/\\/g, '/')
434
+ const normalizedCurrent = current.replace(/\\/g, '/')
431
435
  if (
432
436
  normalizedCurrent.includes(`${path.sep}.next${path.sep}`) ||
433
437
  normalizedCurrent.includes(`${path.sep}.git${path.sep}`) ||
434
438
  normalizedCurrent.includes(`${path.sep}node_modules${path.sep}.cache${path.sep}`)
435
439
  ) {
436
- continue;
440
+ continue
437
441
  }
438
- const depth = normalizedCurrent.split('/').length;
439
- if (depth > normalizedRoot.split('/').length + maxDepth) continue;
440
- let entries;
442
+ const depth = normalizedCurrent.split('/').length
443
+ if (depth > normalizedRoot.split('/').length + maxDepth) continue
444
+ let entries
441
445
  try {
442
- entries = await readdir(current, { withFileTypes: true });
446
+ entries = await readdir(current, { withFileTypes: true })
443
447
  } catch {
444
- continue;
448
+ continue
445
449
  }
446
450
  for (const entry of entries) {
447
- const child = path.join(current, entry.name);
451
+ const child = path.join(current, entry.name)
448
452
  if (entry.isDirectory()) {
449
- stack.push(child);
450
- continue;
453
+ stack.push(child)
454
+ continue
451
455
  }
452
456
  if (entry.isFile() && entry.name === targetName) {
453
- found.push(child);
457
+ found.push(child)
454
458
  }
455
459
  }
456
460
  }
457
- return found;
461
+ return found
458
462
  }