vinext 0.1.1 → 0.1.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (266) hide show
  1. package/README.md +2 -5
  2. package/dist/build/client-build-config.d.ts +7 -1
  3. package/dist/build/client-build-config.js +9 -1
  4. package/dist/build/prerender.d.ts +9 -1
  5. package/dist/build/prerender.js +41 -12
  6. package/dist/build/run-prerender.d.ts +10 -2
  7. package/dist/build/run-prerender.js +15 -1
  8. package/dist/check.js +4 -3
  9. package/dist/client/app-nav-failure-handler.d.ts +8 -0
  10. package/dist/client/app-nav-failure-handler.js +44 -0
  11. package/dist/client/navigation-runtime.d.ts +3 -2
  12. package/dist/client/vinext-next-data.d.ts +18 -1
  13. package/dist/client/window-next.d.ts +8 -5
  14. package/dist/client/window-next.js +12 -1
  15. package/dist/cloudflare/src/cache/cdn-adapter.runtime.js +6 -1
  16. package/dist/config/config-matchers.d.ts +11 -4
  17. package/dist/config/config-matchers.js +88 -16
  18. package/dist/config/next-config.d.ts +59 -4
  19. package/dist/config/next-config.js +149 -48
  20. package/dist/deploy.d.ts +30 -11
  21. package/dist/deploy.js +189 -101
  22. package/dist/entries/app-browser-entry.d.ts +9 -3
  23. package/dist/entries/app-browser-entry.js +21 -3
  24. package/dist/entries/app-rsc-entry.d.ts +2 -0
  25. package/dist/entries/app-rsc-entry.js +71 -6
  26. package/dist/entries/app-rsc-manifest.js +2 -0
  27. package/dist/entries/app-ssr-entry.js +1 -1
  28. package/dist/entries/pages-client-entry.js +54 -9
  29. package/dist/entries/pages-server-entry.js +48 -11
  30. package/dist/index.d.ts +0 -2
  31. package/dist/index.js +285 -139
  32. package/dist/plugins/dynamic-preload-metadata.d.ts +13 -0
  33. package/dist/plugins/dynamic-preload-metadata.js +415 -0
  34. package/dist/plugins/extensionless-dynamic-import.d.ts +6 -0
  35. package/dist/plugins/extensionless-dynamic-import.js +152 -0
  36. package/dist/plugins/og-assets.js +2 -2
  37. package/dist/plugins/optimize-imports.d.ts +10 -5
  38. package/dist/plugins/optimize-imports.js +27 -21
  39. package/dist/plugins/postcss.js +7 -7
  40. package/dist/plugins/sass.d.ts +53 -24
  41. package/dist/plugins/sass.js +249 -1
  42. package/dist/plugins/typeof-window.d.ts +14 -0
  43. package/dist/plugins/typeof-window.js +150 -0
  44. package/dist/plugins/wasm-module-import.d.ts +15 -0
  45. package/dist/plugins/wasm-module-import.js +50 -0
  46. package/dist/routing/app-route-graph.d.ts +25 -2
  47. package/dist/routing/app-route-graph.js +91 -22
  48. package/dist/routing/file-matcher.d.ts +10 -1
  49. package/dist/routing/file-matcher.js +23 -2
  50. package/dist/routing/pages-router.js +3 -3
  51. package/dist/routing/utils.d.ts +35 -6
  52. package/dist/routing/utils.js +59 -7
  53. package/dist/server/api-handler.d.ts +6 -1
  54. package/dist/server/api-handler.js +21 -15
  55. package/dist/server/app-browser-action-result.d.ts +19 -6
  56. package/dist/server/app-browser-action-result.js +19 -10
  57. package/dist/server/app-browser-entry.js +269 -297
  58. package/dist/server/app-browser-error.d.ts +10 -3
  59. package/dist/server/app-browser-error.js +47 -6
  60. package/dist/server/app-browser-history-controller.d.ts +104 -0
  61. package/dist/server/app-browser-history-controller.js +210 -0
  62. package/dist/server/app-browser-hydration.d.ts +2 -0
  63. package/dist/server/app-browser-hydration.js +1 -0
  64. package/dist/server/app-browser-navigation-controller.d.ts +7 -4
  65. package/dist/server/app-browser-navigation-controller.js +33 -9
  66. package/dist/server/app-browser-rsc-redirect.d.ts +11 -2
  67. package/dist/server/app-browser-rsc-redirect.js +30 -8
  68. package/dist/server/app-browser-server-action-navigation.d.ts +6 -0
  69. package/dist/server/app-browser-server-action-navigation.js +9 -0
  70. package/dist/server/app-browser-state.js +4 -7
  71. package/dist/server/app-browser-stream.js +86 -43
  72. package/dist/server/app-browser-visible-commit.js +1 -1
  73. package/dist/server/app-elements-wire.d.ts +6 -1
  74. package/dist/server/app-elements-wire.js +14 -4
  75. package/dist/server/app-elements.d.ts +2 -2
  76. package/dist/server/app-elements.js +2 -2
  77. package/dist/server/app-fallback-renderer.d.ts +3 -1
  78. package/dist/server/app-fallback-renderer.js +6 -2
  79. package/dist/server/app-middleware.js +1 -0
  80. package/dist/server/app-optimistic-routing.js +24 -3
  81. package/dist/server/app-page-boundary-render.d.ts +3 -1
  82. package/dist/server/app-page-boundary-render.js +31 -16
  83. package/dist/server/app-page-cache-render.d.ts +53 -0
  84. package/dist/server/app-page-cache-render.js +91 -0
  85. package/dist/server/app-page-cache.d.ts +16 -2
  86. package/dist/server/app-page-cache.js +71 -8
  87. package/dist/server/app-page-dispatch.d.ts +34 -0
  88. package/dist/server/app-page-dispatch.js +167 -97
  89. package/dist/server/app-page-element-builder.d.ts +23 -2
  90. package/dist/server/app-page-element-builder.js +42 -10
  91. package/dist/server/app-page-execution.d.ts +7 -2
  92. package/dist/server/app-page-execution.js +53 -18
  93. package/dist/server/app-page-probe.d.ts +1 -0
  94. package/dist/server/app-page-probe.js +4 -0
  95. package/dist/server/app-page-render-observation.d.ts +3 -1
  96. package/dist/server/app-page-render-observation.js +17 -1
  97. package/dist/server/app-page-render.d.ts +13 -2
  98. package/dist/server/app-page-render.js +48 -17
  99. package/dist/server/app-page-request.d.ts +3 -0
  100. package/dist/server/app-page-request.js +5 -3
  101. package/dist/server/app-page-response.js +1 -1
  102. package/dist/server/app-page-route-wiring.d.ts +5 -1
  103. package/dist/server/app-page-route-wiring.js +21 -11
  104. package/dist/server/app-page-stream.d.ts +16 -9
  105. package/dist/server/app-page-stream.js +12 -9
  106. package/dist/server/app-pages-bridge.d.ts +18 -0
  107. package/dist/server/app-pages-bridge.js +22 -5
  108. package/dist/server/app-ppr-fallback-shell-render.d.ts +17 -0
  109. package/dist/server/app-ppr-fallback-shell-render.js +26 -0
  110. package/dist/server/app-ppr-fallback-shell.d.ts +13 -1
  111. package/dist/server/app-ppr-fallback-shell.js +8 -1
  112. package/dist/server/app-route-handler-dispatch.js +9 -2
  113. package/dist/server/app-route-handler-policy.d.ts +1 -0
  114. package/dist/server/app-route-handler-response.js +11 -10
  115. package/dist/server/app-route-handler-runtime.js +12 -1
  116. package/dist/server/app-router-entry.js +5 -0
  117. package/dist/server/app-rsc-cache-busting.js +2 -0
  118. package/dist/server/app-rsc-handler.d.ts +25 -0
  119. package/dist/server/app-rsc-handler.js +153 -53
  120. package/dist/server/app-rsc-response-finalizer.js +1 -1
  121. package/dist/server/app-rsc-route-matching.d.ts +3 -0
  122. package/dist/server/app-rsc-route-matching.js +2 -0
  123. package/dist/server/app-segment-config.d.ts +9 -1
  124. package/dist/server/app-segment-config.js +12 -3
  125. package/dist/server/app-server-action-execution.d.ts +12 -0
  126. package/dist/server/app-server-action-execution.js +47 -15
  127. package/dist/server/app-ssr-entry.d.ts +2 -0
  128. package/dist/server/app-ssr-entry.js +81 -8
  129. package/dist/server/app-ssr-stream.js +9 -1
  130. package/dist/server/cache-control.js +4 -0
  131. package/dist/server/dev-lockfile.js +2 -1
  132. package/dist/server/dev-server.d.ts +2 -2
  133. package/dist/server/dev-server.js +287 -63
  134. package/dist/server/headers.d.ts +8 -1
  135. package/dist/server/headers.js +8 -1
  136. package/dist/server/hybrid-route-priority.d.ts +22 -0
  137. package/dist/server/hybrid-route-priority.js +33 -0
  138. package/dist/server/image-optimization.d.ts +18 -9
  139. package/dist/server/image-optimization.js +37 -23
  140. package/dist/server/implicit-tags.d.ts +2 -1
  141. package/dist/server/implicit-tags.js +4 -1
  142. package/dist/server/instrumentation-runtime.d.ts +6 -0
  143. package/dist/server/instrumentation-runtime.js +8 -0
  144. package/dist/server/isr-decision.d.ts +79 -0
  145. package/dist/server/isr-decision.js +70 -0
  146. package/dist/server/metadata-route-response.js +5 -3
  147. package/dist/server/middleware-runtime.d.ts +13 -0
  148. package/dist/server/middleware-runtime.js +11 -7
  149. package/dist/server/middleware.js +1 -0
  150. package/dist/server/navigation-planner.d.ts +186 -22
  151. package/dist/server/navigation-planner.js +302 -0
  152. package/dist/server/navigation-trace.d.ts +18 -1
  153. package/dist/server/navigation-trace.js +18 -1
  154. package/dist/server/normalize-path.d.ts +0 -8
  155. package/dist/server/normalize-path.js +3 -1
  156. package/dist/server/otel-tracer-extension.d.ts +45 -0
  157. package/dist/server/otel-tracer-extension.js +89 -0
  158. package/dist/server/pages-api-route.d.ts +20 -3
  159. package/dist/server/pages-api-route.js +19 -3
  160. package/dist/server/pages-asset-tags.d.ts +16 -4
  161. package/dist/server/pages-asset-tags.js +22 -12
  162. package/dist/server/pages-data-route.d.ts +8 -1
  163. package/dist/server/pages-data-route.js +16 -3
  164. package/dist/server/pages-get-initial-props.d.ts +54 -4
  165. package/dist/server/pages-get-initial-props.js +43 -1
  166. package/dist/server/pages-node-compat.d.ts +3 -11
  167. package/dist/server/pages-node-compat.js +175 -122
  168. package/dist/server/pages-page-data.d.ts +39 -2
  169. package/dist/server/pages-page-data.js +261 -46
  170. package/dist/server/pages-page-handler.d.ts +5 -2
  171. package/dist/server/pages-page-handler.js +78 -25
  172. package/dist/server/pages-page-response.d.ts +47 -2
  173. package/dist/server/pages-page-response.js +73 -9
  174. package/dist/server/pages-readiness.d.ts +1 -1
  175. package/dist/server/pages-request-pipeline.d.ts +16 -1
  176. package/dist/server/pages-request-pipeline.js +96 -38
  177. package/dist/server/pregenerated-concrete-paths.d.ts +1 -17
  178. package/dist/server/pregenerated-concrete-paths.js +2 -19
  179. package/dist/server/prerender-manifest.d.ts +33 -0
  180. package/dist/server/prerender-manifest.js +54 -0
  181. package/dist/server/prerender-route-params.d.ts +1 -2
  182. package/dist/server/prod-server.d.ts +39 -1
  183. package/dist/server/prod-server.js +107 -37
  184. package/dist/server/request-pipeline.d.ts +3 -15
  185. package/dist/server/request-pipeline.js +58 -47
  186. package/dist/server/rsc-stream-hints.d.ts +5 -1
  187. package/dist/server/rsc-stream-hints.js +6 -1
  188. package/dist/server/seed-cache.js +10 -18
  189. package/dist/shims/app-router-scroll-state.d.ts +3 -1
  190. package/dist/shims/app-router-scroll-state.js +14 -2
  191. package/dist/shims/app-router-scroll.d.ts +3 -0
  192. package/dist/shims/app-router-scroll.js +28 -18
  193. package/dist/shims/cache-runtime.js +12 -4
  194. package/dist/shims/cache.d.ts +1 -0
  195. package/dist/shims/cache.js +1 -1
  196. package/dist/shims/cdn-cache.d.ts +5 -5
  197. package/dist/shims/dynamic-preload-chunks.d.ts +8 -0
  198. package/dist/shims/dynamic-preload-chunks.js +79 -0
  199. package/dist/shims/dynamic.d.ts +4 -0
  200. package/dist/shims/dynamic.js +4 -2
  201. package/dist/shims/error-boundary.d.ts +6 -4
  202. package/dist/shims/error-boundary.js +7 -0
  203. package/dist/shims/error.js +38 -11
  204. package/dist/shims/error.react-server.d.ts +9 -0
  205. package/dist/shims/error.react-server.js +6 -0
  206. package/dist/shims/fetch-cache.d.ts +11 -1
  207. package/dist/shims/fetch-cache.js +55 -20
  208. package/dist/shims/hash-scroll.js +6 -1
  209. package/dist/shims/head.js +6 -1
  210. package/dist/shims/headers.d.ts +16 -2
  211. package/dist/shims/headers.js +66 -5
  212. package/dist/shims/image-config.js +7 -1
  213. package/dist/shims/internal/als-registry.js +28 -1
  214. package/dist/shims/internal/app-route-detection.d.ts +6 -3
  215. package/dist/shims/internal/app-route-detection.js +18 -23
  216. package/dist/shims/internal/app-router-context.d.ts +5 -0
  217. package/dist/shims/internal/hybrid-client-route-owner.d.ts +31 -0
  218. package/dist/shims/internal/hybrid-client-route-owner.js +143 -0
  219. package/dist/shims/internal/navigation-untracked.d.ts +35 -0
  220. package/dist/shims/internal/navigation-untracked.js +55 -0
  221. package/dist/shims/internal/pages-data-target.d.ts +7 -2
  222. package/dist/shims/internal/pages-data-target.js +17 -8
  223. package/dist/shims/internal/pages-router-accessor.d.ts +19 -0
  224. package/dist/shims/internal/pages-router-accessor.js +13 -0
  225. package/dist/shims/internal/router-context.d.ts +2 -1
  226. package/dist/shims/internal/router-context.js +3 -1
  227. package/dist/shims/link.js +12 -5
  228. package/dist/shims/metadata.d.ts +6 -2
  229. package/dist/shims/metadata.js +32 -14
  230. package/dist/shims/navigation.d.ts +14 -17
  231. package/dist/shims/navigation.js +93 -46
  232. package/dist/shims/ppr-fallback-shell.d.ts +5 -1
  233. package/dist/shims/ppr-fallback-shell.js +28 -7
  234. package/dist/shims/router.d.ts +13 -2
  235. package/dist/shims/router.js +434 -116
  236. package/dist/shims/script-nonce-context.d.ts +1 -1
  237. package/dist/shims/script-nonce-context.js +11 -3
  238. package/dist/shims/server.d.ts +33 -2
  239. package/dist/shims/server.js +75 -18
  240. package/dist/shims/slot.js +1 -1
  241. package/dist/shims/unified-request-context.js +2 -0
  242. package/dist/typegen.js +1 -0
  243. package/dist/utils/built-asset-url.d.ts +4 -0
  244. package/dist/utils/built-asset-url.js +11 -0
  245. package/dist/utils/client-build-manifest.js +15 -5
  246. package/dist/utils/client-runtime-metadata.d.ts +45 -0
  247. package/dist/utils/client-runtime-metadata.js +63 -0
  248. package/dist/utils/commonjs-loader.d.ts +16 -0
  249. package/dist/utils/commonjs-loader.js +100 -0
  250. package/dist/utils/deployment-id.d.ts +8 -0
  251. package/dist/utils/deployment-id.js +22 -0
  252. package/dist/utils/hash.d.ts +17 -1
  253. package/dist/utils/hash.js +36 -1
  254. package/dist/utils/html-limited-bots.d.ts +18 -1
  255. package/dist/utils/html-limited-bots.js +23 -1
  256. package/dist/utils/lazy-chunks.d.ts +27 -1
  257. package/dist/utils/lazy-chunks.js +65 -1
  258. package/dist/utils/manifest-paths.d.ts +20 -2
  259. package/dist/utils/manifest-paths.js +38 -3
  260. package/dist/utils/parse-cookie.d.ts +13 -0
  261. package/dist/utils/parse-cookie.js +52 -0
  262. package/dist/utils/path.d.ts +8 -1
  263. package/dist/utils/path.js +13 -1
  264. package/package.json +2 -2
  265. package/dist/shims/internal/parse-cookie-header.d.ts +0 -14
  266. package/dist/shims/internal/parse-cookie-header.js +0 -30
@@ -1,6 +1,6 @@
1
1
  "use client";
2
2
  import { decodeHashFragment } from "./hash-scroll.js";
3
- import { consumeAppRouterScrollIntent, getPendingAppRouterScrollIntent } from "./app-router-scroll-state.js";
3
+ import { consumeAppRouterScrollIntent, getPendingAppRouterScrollIntent, markAppRouterScrollIntentHeadHoisted } from "./app-router-scroll-state.js";
4
4
  import * as React$1 from "react";
5
5
  import { jsx } from "react/jsx-runtime";
6
6
  import * as ReactDOM from "react-dom";
@@ -46,8 +46,7 @@ function topOfElementInViewport(element, viewportHeight) {
46
46
  function getHashFragmentDomNode(hash) {
47
47
  const fragment = decodeHashFragment(hash.startsWith("#") ? hash.slice(1) : hash);
48
48
  if (fragment === "top") return document.body;
49
- const element = document.getElementById(fragment) ?? document.getElementsByName(fragment)[0];
50
- return element instanceof HTMLElement ? element : null;
49
+ return document.getElementById(fragment) ?? document.getElementsByName(fragment)[0] ?? null;
51
50
  }
52
51
  function isInDocumentHead(node) {
53
52
  const head = node.ownerDocument?.head;
@@ -55,7 +54,7 @@ function isInDocumentHead(node) {
55
54
  }
56
55
  function findNextScrollTarget(node) {
57
56
  if (!(node instanceof Element)) return null;
58
- if (isInDocumentHead(node)) return { kind: "document-top" };
57
+ if (isInDocumentHead(node)) return null;
59
58
  let target = node;
60
59
  while (!(target instanceof HTMLElement) || shouldSkipElement(target)) {
61
60
  if (target.nextElementSibling === null) return null;
@@ -82,34 +81,45 @@ function scrollToElement(target, hash) {
82
81
  });
83
82
  }
84
83
  var AppRouterScrollTargetInner = class extends React$1.Component {
84
+ scheduledCommitId = null;
85
+ schedulePotentialScroll = () => {
86
+ const commitId = this.props.commitId;
87
+ this.scheduledCommitId = commitId;
88
+ queueMicrotask(() => {
89
+ if (this.scheduledCommitId !== commitId) return;
90
+ this.handlePotentialScroll();
91
+ });
92
+ };
85
93
  handlePotentialScroll = () => {
86
94
  const intent = getPendingAppRouterScrollIntent();
87
95
  if (intent === null) return;
88
96
  if (this.props.commitId === null || intent.commitId !== this.props.commitId) return;
89
- let target;
90
- if (intent.hash !== null) {
91
- target = getHashFragmentDomNode(intent.hash);
92
- if (target === null) return;
93
- } else {
94
- const next = findNextScrollTarget(findDOMNode(this));
95
- if (next === null) return;
96
- if (next.kind === "document-top") {
97
- if (consumeAppRouterScrollIntent(intent, this.props.commitId) === null) return;
98
- document.documentElement.scrollTop = 0;
97
+ let node;
98
+ if (intent.hash !== null) node = getHashFragmentDomNode(intent.hash);
99
+ else node = null;
100
+ if (node === null) {
101
+ node = findDOMNode(this);
102
+ if (node !== null && isInDocumentHead(node)) {
103
+ markAppRouterScrollIntentHeadHoisted(intent, this.props.commitId);
99
104
  return;
100
105
  }
101
- target = next.element;
102
106
  }
107
+ const next = findNextScrollTarget(node);
108
+ if (next === null) return;
109
+ const target = next.element;
103
110
  const consumed = consumeAppRouterScrollIntent(intent, this.props.commitId);
104
111
  if (consumed === null) return;
105
112
  scrollToElement(target, consumed.hash);
106
- target.focus({ preventScroll: true });
113
+ target.focus();
107
114
  };
108
115
  componentDidMount() {
109
- this.handlePotentialScroll();
116
+ this.schedulePotentialScroll();
110
117
  }
111
118
  componentDidUpdate() {
112
- this.handlePotentialScroll();
119
+ this.schedulePotentialScroll();
120
+ }
121
+ componentWillUnmount() {
122
+ this.scheduledCommitId = null;
113
123
  }
114
124
  render() {
115
125
  return this.props.children;
@@ -1,9 +1,10 @@
1
1
  import { getOrCreateAls } from "./internal/als-registry.js";
2
2
  import { getRequestContext, isInsideUnifiedScope, runWithUnifiedStateMutation } from "./unified-request-context.js";
3
3
  import { VINEXT_RSC_MARKER_HEADER } from "../server/headers.js";
4
+ import { trackPprFallbackShellCacheTask } from "./ppr-fallback-shell.js";
4
5
  import { markDynamicUsage } from "./headers.js";
5
6
  import { _registerCacheContextAccessor, _setRequestScopedCacheLife, cacheLifeProfiles, getDataCacheHandler } from "./cache.js";
6
- import { addCollectedRequestTags } from "./fetch-cache.js";
7
+ import { addCollectedRequestTags, getCurrentFetchSoftTags } from "./fetch-cache.js";
7
8
  //#region src/shims/cache-runtime.ts
8
9
  /**
9
10
  * "use cache" runtime
@@ -243,7 +244,7 @@ function registerCachedFunction(fn, id, variant, options = {}) {
243
244
  const cacheVariant = variant ?? "";
244
245
  const omitAppPageSearchParamsFromFirstArg = options.appPageDefaultExport === true;
245
246
  const isDev = typeof process !== "undefined" && process.env.NODE_ENV === "development";
246
- const cachedFn = async (...args) => {
247
+ const cachedFn = (...args) => trackPprFallbackShellCacheTask(async () => {
247
248
  const rsc = await getRscModule();
248
249
  const keySeed = getUseCacheKeySeed();
249
250
  let cacheKey;
@@ -269,7 +270,11 @@ function registerCachedFunction(fn, id, variant, options = {}) {
269
270
  }
270
271
  if (isDev) return executeWithContext(fn, args, cacheVariant);
271
272
  const handler = getDataCacheHandler();
272
- const existing = await handler.get(cacheKey, { kind: "FETCH" });
273
+ const softTags = getCurrentFetchSoftTags();
274
+ const existing = await handler.get(cacheKey, {
275
+ kind: "FETCH",
276
+ softTags
277
+ });
273
278
  if (existing?.value && existing.value.kind === "FETCH" && existing.cacheState !== "stale") try {
274
279
  propagateCacheTagsToRequest(existing.value.tags);
275
280
  if (rsc && existing.value.data.headers["x-vinext-rsc"] === "1") {
@@ -316,13 +321,16 @@ function registerCachedFunction(fn, id, variant, options = {}) {
316
321
  });
317
322
  } catch {}
318
323
  return result;
319
- };
324
+ }, cacheVariant);
320
325
  Object.defineProperty(cachedFn, "length", {
321
326
  value: fn.length,
322
327
  configurable: true
323
328
  });
329
+ cachedFn[USE_CACHE_FUNCTION_SYMBOL] = true;
324
330
  return cachedFn;
325
331
  }
332
+ /** @internal Symbol used to identify "use cache" wrapper functions. */
333
+ const USE_CACHE_FUNCTION_SYMBOL = Symbol.for("vinext.useCacheFunction");
326
334
  function throwPrivateUseCacheInsidePublicUseCacheError() {
327
335
  const error = /* @__PURE__ */ new Error("\"use cache: private\" must not be used within \"use cache\". It can only be nested inside of another \"use cache: private\".");
328
336
  const ctx = getRequestContext();
@@ -53,6 +53,7 @@ type CachedPagesValue = {
53
53
  kind: "PAGES";
54
54
  html: string;
55
55
  pageData: object;
56
+ generatedFromDataRequest?: boolean;
56
57
  headers: Record<string, string | string[]> | undefined;
57
58
  status: number | undefined;
58
59
  };
@@ -1,10 +1,10 @@
1
1
  import { getOrCreateAls } from "./internal/als-registry.js";
2
2
  import { getRequestContext, isInsideUnifiedScope, runWithUnifiedStateMutation } from "./unified-request-context.js";
3
3
  import { getRequestExecutionContext, runWithExecutionContext } from "./request-context.js";
4
+ import { makeHangingPromise } from "./internal/make-hanging-promise.js";
4
5
  import { getHeadersAccessPhase, markDynamicUsage } from "./headers.js";
5
6
  import { fnv1a64 } from "../utils/hash.js";
6
7
  import { workUnitAsyncStorage } from "./internal/work-unit-async-storage.js";
7
- import { makeHangingPromise } from "./internal/make-hanging-promise.js";
8
8
  import { readCacheControlNumberField } from "../utils/cache-control-metadata.js";
9
9
  import { encodeCacheTag, encodeCacheTags } from "../utils/encode-cache-tag.js";
10
10
  import { getCdnCacheAdapter } from "./cdn-cache.js";
@@ -1,8 +1,8 @@
1
1
  import { CacheHandlerValue, IncrementalCacheValue } from "./cache.js";
2
2
 
3
3
  //#region src/shims/cdn-cache.d.ts
4
- /** A map of response header name -> value the adapter wants applied. */
5
- type CdnResponseHeaders = Record<string, string>;
4
+ /** A map of response header name -> value the adapter wants applied or removed. */
5
+ type CdnResponseHeaders = Record<string, string | null>;
6
6
  type CdnCacheableHeaderInput = {
7
7
  /**
8
8
  * The cacheable `Cache-Control` value the framework computed for shared
@@ -50,9 +50,9 @@ type CdnCacheAdapter = {
50
50
  */
51
51
  set(key: string, data: IncrementalCacheValue | null, ctx?: Record<string, unknown>): Promise<void>;
52
52
  /**
53
- * Build the response cache headers for a given cacheable policy. Returns a map
54
- * so an adapter can emit more than one header (e.g. `Cache-Control` +
55
- * `CDN-Cache-Control`).
53
+ * Build the response cache headers for a given policy. Returns a map so an
54
+ * adapter can emit more than one header (e.g. `Cache-Control` +
55
+ * `CDN-Cache-Control`) and remove stale adapter-owned headers with `null`.
56
56
  */
57
57
  buildResponseHeaders(input: CdnCacheableHeaderInput): CdnResponseHeaders;
58
58
  /**
@@ -0,0 +1,8 @@
1
+ import React from "react";
2
+
3
+ //#region src/shims/dynamic-preload-chunks.d.ts
4
+ declare function DynamicPreloadChunks(props: {
5
+ moduleIds?: readonly string[];
6
+ }): React.FunctionComponentElement<React.FragmentProps> | null;
7
+ //#endregion
8
+ export { DynamicPreloadChunks };
@@ -0,0 +1,79 @@
1
+ "use client";
2
+ import { appendAssetDeploymentIdQuery } from "../utils/deployment-id.js";
3
+ import { useScriptNonce } from "./script-nonce-context.js";
4
+ import React from "react";
5
+ import * as ReactDOM from "react-dom";
6
+ //#region src/shims/dynamic-preload-chunks.tsx
7
+ /**
8
+ * Preload links for rendered next/dynamic() boundaries.
9
+ *
10
+ * This MUST be a "use client" component. next/dynamic() can be called from
11
+ * either a Server Component or a Client Component. If this rendered in the
12
+ * environment of the call site, a Server-Component call site would render it in
13
+ * the RSC environment, where the script-nonce React context is unavailable
14
+ * (createContext is not callable in react-server), so emitted preload links
15
+ * would drop the request CSP nonce — a CSP violation under
16
+ * `script-src 'nonce-…' 'strict-dynamic'`.
17
+ *
18
+ * Marking it "use client" forces it into the SSR pass (where vinext installs
19
+ * the ScriptNonceProvider via withScriptNonce()), so the nonce is available
20
+ * regardless of whether the dynamic() call site is a Server or Client
21
+ * Component. This mirrors Next.js's <PreloadChunks> ('use client') and vinext's
22
+ * own next/script shim.
23
+ *
24
+ * Deliberate divergence from Next.js: for CSS we render
25
+ * `<link rel="stylesheet">` WITHOUT `as="style"`. Next.js emits `as="style"`,
26
+ * but per the HTML spec `as` is only meaningful on `rel="preload"`/`modulepreload`
27
+ * — on `rel="stylesheet"` it is ignored by browsers and is semantically wrong.
28
+ * React keys stylesheet resources on href + precedence, not `as`, so omitting it
29
+ * is safe. This is an intentional, documented difference, not a parity bug.
30
+ */
31
+ function dynamicPreloadHref(file) {
32
+ if (file.startsWith("/") || file.startsWith("http://") || file.startsWith("https://") || file.startsWith("//")) return file;
33
+ return `/${file}`;
34
+ }
35
+ function resolveDynamicPreloadFiles(moduleIds) {
36
+ if (!moduleIds || moduleIds.length === 0) return [];
37
+ const preloadMap = globalThis.__VINEXT_DYNAMIC_PRELOADS__;
38
+ if (!preloadMap) return [];
39
+ const files = [];
40
+ const seen = /* @__PURE__ */ new Set();
41
+ for (const moduleId of moduleIds) for (const file of preloadMap[moduleId] ?? []) {
42
+ if (seen.has(file)) continue;
43
+ seen.add(file);
44
+ files.push(file);
45
+ }
46
+ return files;
47
+ }
48
+ function DynamicPreloadChunks(props) {
49
+ const nonce = useScriptNonce();
50
+ if (typeof window !== "undefined") return null;
51
+ const files = resolveDynamicPreloadFiles(props.moduleIds);
52
+ if (files.length === 0) return null;
53
+ const stylesheets = [];
54
+ for (const file of files) {
55
+ const assetHref = dynamicPreloadHref(file);
56
+ if (assetHref.endsWith(".css")) {
57
+ const href = appendAssetDeploymentIdQuery(assetHref);
58
+ stylesheets.push(React.createElement("link", {
59
+ key: href,
60
+ rel: "stylesheet",
61
+ href,
62
+ nonce,
63
+ precedence: "dynamic"
64
+ }));
65
+ continue;
66
+ }
67
+ if (assetHref.endsWith(".js") && typeof ReactDOM.preload === "function") {
68
+ const preloadOptions = {
69
+ as: "script",
70
+ fetchPriority: "low",
71
+ nonce
72
+ };
73
+ ReactDOM.preload(assetHref, preloadOptions);
74
+ }
75
+ }
76
+ return stylesheets.length > 0 ? React.createElement(React.Fragment, null, ...stylesheets) : null;
77
+ }
78
+ //#endregion
79
+ export { DynamicPreloadChunks };
@@ -16,6 +16,10 @@ type LoaderFn<P> = () => LoaderComponent<P>;
16
16
  type DynamicOptions<P> = {
17
17
  loading?: ComponentType<DynamicLoadingProps>;
18
18
  loader?: Loader<P>;
19
+ loadableGenerated?: {
20
+ modules?: readonly string[];
21
+ };
22
+ modules?: readonly string[];
19
23
  ssr?: boolean;
20
24
  };
21
25
  type Loader<P> = LoaderFn<P> | LoaderComponent<P>;
@@ -1,3 +1,4 @@
1
+ import { DynamicPreloadChunks } from "./dynamic-preload-chunks.js";
1
2
  import React from "react";
2
3
  //#region src/shims/dynamic.ts
3
4
  /**
@@ -121,8 +122,9 @@ function flushPreloads() {
121
122
  return Promise.all(pending);
122
123
  }
123
124
  function dynamic(dynamicInput, options) {
124
- const { loader: dynamicLoader, loading: LoadingComponent, ssr = true } = normalizeDynamicOptions(dynamicInput, options);
125
+ const { loader: dynamicLoader, loadableGenerated, loading: LoadingComponent, modules, ssr = true } = normalizeDynamicOptions(dynamicInput, options);
125
126
  const loader = dynamicLoader ? normalizeLoader(dynamicLoader) : () => Promise.resolve(() => null);
127
+ const preloadModuleIds = loadableGenerated?.modules ?? modules;
126
128
  if (!ssr) {
127
129
  if (isServer) {
128
130
  const SSRFalse = (_props) => LoadingComponent ? React.createElement(LoadingComponent, createDynamicLoadingProps({ pastDelay: false })) : null;
@@ -174,7 +176,7 @@ function dynamic(dynamicInput, options) {
174
176
  resetKey: 0
175
177
  }, lazyElement);
176
178
  }
177
- return React.createElement(React.Suspense, { fallback }, content);
179
+ return React.createElement(React.Fragment, null, React.createElement(DynamicPreloadChunks, { moduleIds: preloadModuleIds }), React.createElement(React.Suspense, { fallback }, content));
178
180
  };
179
181
  ServerDynamic.displayName = "DynamicServer";
180
182
  return ServerDynamic;
@@ -17,6 +17,7 @@ type RedirectBoundaryState = {
17
17
  redirectType: "push" | "replace" | null;
18
18
  };
19
19
  type ErrorBoundaryInnerProps = {
20
+ isImplicitRootErrorBoundary?: boolean;
20
21
  pathname: string | null;
21
22
  } & ErrorBoundaryProps;
22
23
  type ErrorBoundaryState = {
@@ -31,7 +32,7 @@ declare class RedirectErrorBoundary extends React.Component<{
31
32
  children?: React.ReactNode;
32
33
  });
33
34
  static getDerivedStateFromError(error: unknown): RedirectBoundaryState;
34
- render(): string | number | bigint | boolean | React.JSX.Element | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | null | undefined;
35
+ render(): string | number | bigint | boolean | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | React.JSX.Element | null | undefined;
35
36
  }
36
37
  declare function RedirectBoundary({
37
38
  children
@@ -51,7 +52,7 @@ declare class ErrorBoundaryInner extends React.Component<ErrorBoundaryInnerProps
51
52
  componentDidMount(): void;
52
53
  componentWillUnmount(): void;
53
54
  reset: () => void;
54
- render(): string | number | bigint | boolean | React.JSX.Element | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | null | undefined;
55
+ render(): string | number | bigint | boolean | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | React.JSX.Element | null | undefined;
55
56
  }
56
57
  declare function ErrorBoundary({
57
58
  fallback,
@@ -99,7 +100,7 @@ declare class ForbiddenBoundaryInner extends React.Component<ForbiddenBoundaryIn
99
100
  constructor(props: ForbiddenBoundaryInnerProps);
100
101
  static getDerivedStateFromProps(props: ForbiddenBoundaryInnerProps, state: ForbiddenBoundaryState): ForbiddenBoundaryState | null;
101
102
  static getDerivedStateFromError(error: unknown): Partial<ForbiddenBoundaryState>;
102
- render(): string | number | bigint | boolean | React.JSX.Element | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | null | undefined;
103
+ render(): string | number | bigint | boolean | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | React.JSX.Element | null | undefined;
103
104
  }
104
105
  declare function ForbiddenBoundary({
105
106
  fallback,
@@ -123,7 +124,7 @@ declare class UnauthorizedBoundaryInner extends React.Component<UnauthorizedBoun
123
124
  constructor(props: UnauthorizedBoundaryInnerProps);
124
125
  static getDerivedStateFromProps(props: UnauthorizedBoundaryInnerProps, state: UnauthorizedBoundaryState): UnauthorizedBoundaryState | null;
125
126
  static getDerivedStateFromError(error: unknown): Partial<UnauthorizedBoundaryState>;
126
- render(): string | number | bigint | boolean | React.JSX.Element | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | null | undefined;
127
+ render(): string | number | bigint | boolean | Iterable<React.ReactNode> | Promise<string | number | bigint | boolean | React.ReactPortal | React.ReactElement<unknown, string | React.JSXElementConstructor<any>> | Iterable<React.ReactNode> | null | undefined> | React.JSX.Element | null | undefined;
127
128
  }
128
129
  declare function UnauthorizedBoundary({
129
130
  fallback,
@@ -131,6 +132,7 @@ declare function UnauthorizedBoundary({
131
132
  resetKey
132
133
  }: UnauthorizedBoundaryProps): React.JSX.Element;
133
134
  type DevRecoveryBoundaryProps = {
135
+ isImplicitRootErrorBoundary?: boolean;
134
136
  resetKey: number;
135
137
  onCatch?: (resetKey: number) => void;
136
138
  children?: React.ReactNode;
@@ -1,5 +1,7 @@
1
1
  "use client";
2
+ import { handleAppNavigationFailure } from "../client/app-nav-failure-handler.js";
2
3
  import { decodeRedirectError, isRedirectError, usePathname, useRouter } from "./navigation.js";
4
+ import DefaultGlobalError from "./default-global-error.js";
3
5
  import { VINEXT_DEV_ERROR_RECOVERY_EVENT } from "../utils/dev-error-recovery-event.js";
4
6
  import { isNavigationSignalError } from "../utils/navigation-signal.js";
5
7
  import React from "react";
@@ -98,6 +100,10 @@ var ErrorBoundaryInner = class extends React.Component {
98
100
  }
99
101
  static getDerivedStateFromProps(props, state) {
100
102
  const nextResetState = readBoundaryResetState(props);
103
+ if (state.error && handleAppNavigationFailure(state.error.thrownValue)) return {
104
+ error: null,
105
+ ...nextResetState
106
+ };
101
107
  if (state.error && shouldResetBoundary(nextResetState, state)) return {
102
108
  error: null,
103
109
  ...nextResetState
@@ -150,6 +156,7 @@ function GlobalErrorBoundary({ fallback, children }) {
150
156
  return /* @__PURE__ */ jsx(ErrorBoundaryInner, {
151
157
  pathname: usePathname(),
152
158
  fallback,
159
+ isImplicitRootErrorBoundary: fallback === DefaultGlobalError,
153
160
  children
154
161
  });
155
162
  }
@@ -1,5 +1,7 @@
1
+ import { AppRouterContext } from "./internal/app-router-context.js";
1
2
  import { RouterContext } from "./internal/router-context.js";
2
- import { appRouterInstance, isNextRouterError } from "./navigation.js";
3
+ import { isNextRouterError } from "./navigation.js";
4
+ import { useUntrackedPathname } from "./internal/navigation-untracked.js";
3
5
  import React from "react";
4
6
  //#region src/shims/error.tsx
5
7
  /**
@@ -39,33 +41,53 @@ function ErrorComponent({ statusCode, title }) {
39
41
  margin: 0
40
42
  } }, displayTitle + "."))));
41
43
  }
44
+ const _CatchErrorAppRouterContext = AppRouterContext ?? React.createContext(null);
42
45
  var _CatchError = class extends React.Component {
43
- static contextType = RouterContext;
46
+ static contextType = _CatchErrorAppRouterContext;
44
47
  static displayName = "unstable_catchError(Next.CatchError)";
45
- state = { error: null };
48
+ constructor(props) {
49
+ super(props);
50
+ this.state = {
51
+ error: null,
52
+ previousPathname: props.pathname
53
+ };
54
+ }
46
55
  static getDerivedStateFromError(thrownValue) {
47
56
  if (isNextRouterError(thrownValue)) throw thrownValue;
48
57
  return { error: { thrownValue } };
49
58
  }
59
+ static getDerivedStateFromProps(props, state) {
60
+ if (props.pathname !== state.previousPathname && state.error) return {
61
+ error: null,
62
+ previousPathname: props.pathname
63
+ };
64
+ return {
65
+ error: state.error,
66
+ previousPathname: props.pathname
67
+ };
68
+ }
50
69
  reset = () => {
51
70
  this.setState({ error: null });
52
71
  };
53
72
  unstable_retry = () => {
54
- if (this.context !== null) throw new Error("`unstable_retry()` can only be used in the App Router. Use `reset()` in the Pages Router.");
55
- if (typeof window === "undefined") throw new Error("`unstable_retry()` can only be used on the client. Call it from a user interaction handler inside the error fallback.");
73
+ if (this.props.isPagesRouter) throw new Error("`unstable_retry()` can only be used in the App Router. Use `reset()` in the Pages Router.");
56
74
  React.startTransition(() => {
57
- appRouterInstance.refresh();
75
+ this.context?.refresh();
58
76
  this.reset();
59
77
  });
60
78
  };
61
79
  render() {
62
80
  if (this.state.error) {
81
+ const Fallback = this.props.fallback;
63
82
  const errorInfo = {
64
83
  error: this.state.error.thrownValue,
65
84
  reset: this.reset,
66
85
  unstable_retry: this.unstable_retry
67
86
  };
68
- return this.props.fallback(this.props.forwardedProps, errorInfo);
87
+ return React.createElement(Fallback, {
88
+ props: this.props.props,
89
+ errorInfo
90
+ });
69
91
  }
70
92
  return this.props.children;
71
93
  }
@@ -79,13 +101,18 @@ var _CatchError = class extends React.Component {
79
101
  * https://github.com/vercel/next.js/blob/canary/packages/next/src/client/components/catch-error.tsx
80
102
  */
81
103
  function unstable_catchError(fallback) {
82
- const TypedCatchError = _CatchError;
104
+ const Fallback = ({ props, errorInfo }) => fallback(props, errorInfo);
105
+ Fallback.displayName = fallback.name || "CatchErrorFallback";
83
106
  function CatchErrorBoundary(allProps) {
84
107
  const { children, ...rest } = allProps;
108
+ const pathname = useUntrackedPathname();
109
+ const isPagesRouter = React.useContext(RouterContext) !== null;
85
110
  const forwardedProps = rest;
86
- return React.createElement(TypedCatchError, {
87
- fallback,
88
- forwardedProps
111
+ return React.createElement(_CatchError, {
112
+ fallback: Fallback,
113
+ isPagesRouter,
114
+ pathname,
115
+ props: forwardedProps
89
116
  }, children);
90
117
  }
91
118
  CatchErrorBoundary.displayName = `unstable_catchError(${fallback.name || "CatchErrorFallback"})`;
@@ -0,0 +1,9 @@
1
+ //#region src/shims/error.react-server.d.ts
2
+ type ErrorInfo = {
3
+ error: unknown;
4
+ reset: () => void;
5
+ unstable_retry: () => void;
6
+ };
7
+ declare function unstable_catchError(): never;
8
+ //#endregion
9
+ export { ErrorInfo, unstable_catchError };
@@ -0,0 +1,6 @@
1
+ //#region src/shims/error.react-server.ts
2
+ function unstable_catchError() {
3
+ throw new Error("`unstable_catchError` can only be used in Client Components.");
4
+ }
5
+ //#endregion
6
+ export { unstable_catchError };
@@ -40,6 +40,7 @@ type FetchCacheState = {
40
40
  currentRequestTags: string[];
41
41
  currentFetchSoftTags: string[];
42
42
  currentFetchCacheMode: FetchCacheMode | null;
43
+ currentForceDynamicFetchDefault: boolean;
43
44
  dynamicFetchUrls: Set<string>;
44
45
  isFetchDedupeActive: boolean;
45
46
  currentFetchDedupeEntries: Map<string, FetchDedupeEntry[]>;
@@ -75,7 +76,16 @@ declare function addCollectedRequestTags(tags: readonly string[]): void;
75
76
  * affected route, without permanently coupling a shared fetch entry to one path.
76
77
  */
77
78
  declare function setCurrentFetchSoftTags(tags: string[]): void;
79
+ /**
80
+ * Read the path-derived soft tags for the current render.
81
+ *
82
+ * Used by the "use cache" runtime to pass soft tags to the cache handler
83
+ * so that `revalidatePath()` invalidates "use cache" entries during the
84
+ * affected route's next request, even when the entry carries no hard tags.
85
+ */
86
+ declare function getCurrentFetchSoftTags(): string[];
78
87
  declare function setCurrentFetchCacheMode(mode: FetchCacheMode | null): void;
88
+ declare function setCurrentForceDynamicFetchDefault(enabled: boolean): void;
79
89
  /**
80
90
  * Install the patched fetch and reset per-request tag state.
81
91
  * Returns a cleanup function that clears tags.
@@ -123,4 +133,4 @@ declare function ensureFetchPatch(): void;
123
133
  */
124
134
  declare function getOriginalFetch(): typeof globalThis.fetch;
125
135
  //#endregion
126
- export { FetchCacheMode, FetchCacheState, _resetPendingRefetches, addCollectedRequestTags, consumeDynamicFetchObservations, ensureFetchPatch, getCollectedFetchTags, getOriginalFetch, peekCacheableFetchObservations, peekDynamicFetchObservations, runWithFetchCache, runWithFetchDedupe, setCurrentFetchCacheMode, setCurrentFetchSoftTags, withFetchCache };
136
+ export { FetchCacheMode, FetchCacheState, _resetPendingRefetches, addCollectedRequestTags, consumeDynamicFetchObservations, ensureFetchPatch, getCollectedFetchTags, getCurrentFetchSoftTags, getOriginalFetch, peekCacheableFetchObservations, peekDynamicFetchObservations, runWithFetchCache, runWithFetchDedupe, setCurrentFetchCacheMode, setCurrentFetchSoftTags, setCurrentForceDynamicFetchDefault, withFetchCache };