vinext 1.3.1 → 1.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (271) hide show
  1. package/README.md +25 -22
  2. package/THIRD_PARTY_LICENSES.md +47 -0
  3. package/dist/_virtual/_rolldown/runtime.js +3 -2
  4. package/dist/build/prerender.js +4 -3
  5. package/dist/build/report.d.ts +0 -14
  6. package/dist/build/report.js +1 -51
  7. package/dist/check.js +4 -7
  8. package/dist/cli.js +3 -0
  9. package/dist/client/dev-error-overlay-store.d.ts +1 -0
  10. package/dist/client/dev-error-overlay.d.ts +2 -0
  11. package/dist/client/dev-error-overlay.js +20 -4
  12. package/dist/client/navigation-runtime.d.ts +13 -1
  13. package/dist/client/navigation-runtime.js +1 -1
  14. package/dist/config/config-matchers.js +2 -0
  15. package/dist/config/destination-params.d.ts +2 -1
  16. package/dist/config/destination-params.js +52 -2
  17. package/dist/config/next-config.d.ts +25 -0
  18. package/dist/config/next-config.js +82 -4
  19. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/dbcs-codec.js +327 -0
  20. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/dbcs-data.js +123 -0
  21. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/index.js +29 -0
  22. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/internal.js +134 -0
  23. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/sbcs-codec.js +50 -0
  24. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/sbcs-data-generated.js +455 -0
  25. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/sbcs-data.js +147 -0
  26. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/big5-added.json.js +169 -0
  27. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/cp936.json.js +2584 -0
  28. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/cp949.json.js +2220 -0
  29. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/cp950.json.js +227 -0
  30. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/eucjp.json.js +425 -0
  31. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/gb18030-ranges.json.js +427 -0
  32. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/gbk-added.json.js +229 -0
  33. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/tables/shiftjis.json.js +292 -0
  34. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/utf16.js +106 -0
  35. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/encodings/utf7.js +182 -0
  36. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/lib/bom-handling.js +42 -0
  37. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/lib/extend-node.js +147 -0
  38. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/lib/index.js +94 -0
  39. package/dist/deps/.pnpm/iconv-lite@0.4.24/deps/iconv-lite/lib/streams.js +95 -0
  40. package/dist/deps/.pnpm/safer-buffer@2.1.2/deps/safer-buffer/safer.js +45 -0
  41. package/dist/entries/app-rsc-entry.js +17 -49
  42. package/dist/entries/app-rsc-manifest.js +3 -4
  43. package/dist/entries/app-ssr-entry.js +1 -0
  44. package/dist/entries/pages-server-entry.js +36 -9
  45. package/dist/index.js +112 -90
  46. package/dist/init-cloudflare.d.ts +1 -3
  47. package/dist/init-cloudflare.js +10 -48
  48. package/dist/init-platform.d.ts +2 -0
  49. package/dist/init-platform.js +4 -0
  50. package/dist/plugins/extensionless-dynamic-import.js +6 -2
  51. package/dist/plugins/next-intl-catalog.d.ts +12 -0
  52. package/dist/plugins/next-intl-catalog.js +85 -0
  53. package/dist/plugins/pages-node-externals.d.ts +1 -0
  54. package/dist/plugins/pages-node-externals.js +1 -1
  55. package/dist/plugins/strip-server-exports.js +2 -1
  56. package/dist/plugins/use-cache-callable.d.ts +1 -1
  57. package/dist/plugins/use-cache-callable.js +136 -94
  58. package/dist/routing/app-route-graph.d.ts +6 -0
  59. package/dist/routing/app-route-graph.js +9 -1
  60. package/dist/server/api-handler.js +21 -5
  61. package/dist/server/app-bfcache-identity.js +1 -1
  62. package/dist/server/app-browser-entry.js +86 -66
  63. package/dist/server/app-browser-history-controller.d.ts +5 -4
  64. package/dist/server/app-browser-history-controller.js +93 -15
  65. package/dist/server/app-browser-navigation-controller.d.ts +2 -2
  66. package/dist/server/app-browser-navigation-controller.js +1 -2
  67. package/dist/server/app-browser-rsc-redirect.js +7 -7
  68. package/dist/server/app-browser-server-action-client.d.ts +2 -0
  69. package/dist/server/app-browser-server-action-client.js +5 -4
  70. package/dist/server/app-browser-state.d.ts +2 -4
  71. package/dist/server/app-browser-state.js +9 -4
  72. package/dist/server/app-browser-supplemental-refresh.js +16 -1
  73. package/dist/server/app-browser-visible-commit.d.ts +1 -1
  74. package/dist/server/app-browser-visible-commit.js +4 -14
  75. package/dist/server/app-elements-wire.d.ts +6 -38
  76. package/dist/server/app-elements-wire.js +4 -41
  77. package/dist/server/app-elements.d.ts +2 -2
  78. package/dist/server/app-elements.js +2 -2
  79. package/dist/server/app-history-state.d.ts +2 -2
  80. package/dist/server/app-history-state.js +5 -2
  81. package/dist/server/app-mounted-layouts.d.ts +21 -0
  82. package/dist/server/app-mounted-layouts.js +67 -0
  83. package/dist/server/app-optimistic-routing.d.ts +19 -1
  84. package/dist/server/app-optimistic-routing.js +43 -4
  85. package/dist/server/app-page-boundary-render.js +10 -14
  86. package/dist/server/app-page-boundary.js +2 -2
  87. package/dist/server/app-page-cache-finalizer.d.ts +12 -1
  88. package/dist/server/app-page-cache-finalizer.js +70 -29
  89. package/dist/server/app-page-cache.d.ts +13 -1
  90. package/dist/server/app-page-cache.js +31 -9
  91. package/dist/server/app-page-dispatch.d.ts +5 -11
  92. package/dist/server/app-page-dispatch.js +84 -155
  93. package/dist/server/app-page-element-builder.d.ts +2 -2
  94. package/dist/server/app-page-element-builder.js +13 -12
  95. package/dist/server/app-page-execution.d.ts +17 -52
  96. package/dist/server/app-page-execution.js +102 -95
  97. package/dist/server/app-page-head.d.ts +13 -0
  98. package/dist/server/app-page-head.js +44 -16
  99. package/dist/server/app-page-http-access-fallback-metadata.d.ts +1 -0
  100. package/dist/server/app-page-http-access-fallback-metadata.js +2 -2
  101. package/dist/server/app-page-layout-gate.d.ts +35 -0
  102. package/dist/server/app-page-layout-gate.js +50 -0
  103. package/dist/server/app-page-params.d.ts +0 -1
  104. package/dist/server/app-page-params.js +1 -14
  105. package/dist/server/app-page-probe.d.ts +3 -21
  106. package/dist/server/app-page-probe.js +4 -37
  107. package/dist/server/app-page-render.d.ts +2 -13
  108. package/dist/server/app-page-render.js +103 -234
  109. package/dist/server/app-page-request.d.ts +1 -3
  110. package/dist/server/app-page-request.js +1 -1
  111. package/dist/server/app-page-response.js +3 -3
  112. package/dist/server/app-page-route-wiring.d.ts +13 -6
  113. package/dist/server/app-page-route-wiring.js +86 -63
  114. package/dist/server/app-page-rsc-render-status.d.ts +27 -1
  115. package/dist/server/app-page-rsc-render-status.js +121 -13
  116. package/dist/server/app-page-stream.d.ts +12 -8
  117. package/dist/server/app-page-stream.js +4 -3
  118. package/dist/server/app-pages-bridge.d.ts +4 -0
  119. package/dist/server/app-pages-bridge.js +7 -3
  120. package/dist/server/app-render-dependency.d.ts +11 -4
  121. package/dist/server/app-render-dependency.js +86 -38
  122. package/dist/server/app-request-stage-dispatch.js +1 -1
  123. package/dist/server/app-request-stage-independent-entry.js +1 -1
  124. package/dist/server/app-route-handler-cache.js +2 -2
  125. package/dist/server/app-route-handler-dispatch.js +14 -9
  126. package/dist/server/app-route-handler-execution.js +11 -5
  127. package/dist/server/app-route-handler-policy.d.ts +1 -1
  128. package/dist/server/app-route-handler-policy.js +3 -3
  129. package/dist/server/app-route-handler-response.js +1 -1
  130. package/dist/server/app-route-handler-runtime.d.ts +1 -1
  131. package/dist/server/app-route-handler-runtime.js +28 -11
  132. package/dist/server/app-router-entry.js +1 -1
  133. package/dist/server/app-rsc-cache-busting.d.ts +12 -12
  134. package/dist/server/app-rsc-cache-busting.js +31 -72
  135. package/dist/server/app-rsc-error-handler.d.ts +2 -1
  136. package/dist/server/app-rsc-error-handler.js +10 -2
  137. package/dist/server/app-rsc-errors.d.ts +8 -0
  138. package/dist/server/app-rsc-errors.js +11 -1
  139. package/dist/server/app-rsc-handler.d.ts +5 -5
  140. package/dist/server/app-rsc-handler.js +80 -83
  141. package/dist/server/app-rsc-request-normalization.d.ts +10 -16
  142. package/dist/server/app-rsc-request-normalization.js +12 -18
  143. package/dist/server/app-rsc-response-finalizer.js +2 -2
  144. package/dist/server/app-rsc-response-stage.js +9 -15
  145. package/dist/server/app-server-action-execution.d.ts +3 -1
  146. package/dist/server/app-server-action-execution.js +15 -8
  147. package/dist/server/app-ssr-entry.d.ts +8 -0
  148. package/dist/server/app-ssr-entry.js +22 -16
  149. package/dist/server/app-ssr-stream.js +1 -1
  150. package/dist/server/app-visited-response-cache.d.ts +36 -1
  151. package/dist/server/app-visited-response-cache.js +46 -5
  152. package/dist/server/app-worker-stages.d.ts +37 -6
  153. package/dist/server/app-worker-stages.js +81 -9
  154. package/dist/server/artifact-compatibility.d.ts +0 -1
  155. package/dist/server/artifact-compatibility.js +1 -10
  156. package/dist/server/bfcache-identity.d.ts +7 -0
  157. package/dist/server/bfcache-identity.js +10 -1
  158. package/dist/server/cache-proof.d.ts +1 -115
  159. package/dist/server/cache-proof.js +1 -544
  160. package/dist/server/cacheability-manifest.js +1 -2
  161. package/dist/server/cacheability-request.js +13 -8
  162. package/dist/server/dev-origin-check.d.ts +2 -1
  163. package/dist/server/dev-origin-check.js +2 -1
  164. package/dist/server/dev-server.js +6 -4
  165. package/dist/server/headers.d.ts +6 -3
  166. package/dist/server/headers.js +9 -5
  167. package/dist/server/image-optimization.d.ts +5 -0
  168. package/dist/server/image-optimization.js +6 -1
  169. package/dist/server/isr-cache.d.ts +8 -2
  170. package/dist/server/isr-cache.js +30 -2
  171. package/dist/server/metadata-route-response.js +32 -15
  172. package/dist/server/middleware-matcher.js +19 -6
  173. package/dist/server/middleware-runtime.js +6 -2
  174. package/dist/server/multi-stage.d.ts +57 -12
  175. package/dist/server/multi-stage.js +13 -1
  176. package/dist/server/navigation-planner.js +1 -1
  177. package/dist/server/pages-api-route.js +28 -19
  178. package/dist/server/pages-media-type.d.ts +21 -1
  179. package/dist/server/pages-media-type.js +69 -5
  180. package/dist/server/pages-node-compat.d.ts +1 -1
  181. package/dist/server/pages-node-compat.js +54 -27
  182. package/dist/server/pages-page-data.js +2 -1
  183. package/dist/server/pages-page-handler.js +28 -26
  184. package/dist/server/pages-page-response.d.ts +9 -0
  185. package/dist/server/pages-page-response.js +18 -4
  186. package/dist/server/pages-request-pipeline.d.ts +8 -0
  187. package/dist/server/pages-request-pipeline.js +2 -2
  188. package/dist/server/pages-request-stage-entry.js +36 -14
  189. package/dist/server/pages-response-stage-entry.js +9 -3
  190. package/dist/server/pages-router-entry.js +3 -2
  191. package/dist/server/prod-server.d.ts +2 -2
  192. package/dist/server/prod-server.js +47 -9
  193. package/dist/server/request-error-log.d.ts +9 -0
  194. package/dist/server/request-error-log.js +13 -0
  195. package/dist/server/request-pipeline.d.ts +15 -4
  196. package/dist/server/request-pipeline.js +43 -15
  197. package/dist/server/rsc-completion-metadata.js +3 -0
  198. package/dist/server/shared-cache-identity.d.ts +23 -0
  199. package/dist/server/shared-cache-identity.js +36 -0
  200. package/dist/server/static-file-cache.d.ts +9 -0
  201. package/dist/server/static-file-cache.js +13 -2
  202. package/dist/server/worker-stages.d.ts +16 -3
  203. package/dist/server/worker-stages.js +23 -4
  204. package/dist/shims/cache-handler.js +2 -2
  205. package/dist/shims/cache-request-state.d.ts +23 -26
  206. package/dist/shims/cache-request-state.js +22 -57
  207. package/dist/shims/cache-runtime.d.ts +3 -1
  208. package/dist/shims/cache-runtime.js +94 -48
  209. package/dist/shims/cache.d.ts +16 -10
  210. package/dist/shims/cache.js +47 -36
  211. package/dist/shims/cacheability-classification.d.ts +2 -0
  212. package/dist/shims/cdn-cache.d.ts +22 -5
  213. package/dist/shims/client-hook-error.d.ts +2 -0
  214. package/dist/shims/client-hook-error.js +16 -1
  215. package/dist/shims/client-page-root.js +2 -2
  216. package/dist/shims/dynamic.js +9 -6
  217. package/dist/shims/error-boundary.js +2 -2
  218. package/dist/shims/fetch-cache-state.d.ts +5 -1
  219. package/dist/shims/fetch-cache-state.js +1 -3
  220. package/dist/shims/fetch-cache.d.ts +2 -1
  221. package/dist/shims/fetch-cache.js +39 -25
  222. package/dist/shims/form.js +2 -2
  223. package/dist/shims/headers.d.ts +10 -24
  224. package/dist/shims/headers.js +22 -70
  225. package/dist/shims/internal/cache-context-accessor.d.ts +1 -1
  226. package/dist/shims/internal/navigation-untracked.js +1 -1
  227. package/dist/shims/link.js +8 -11
  228. package/dist/shims/metadata.d.ts +23 -21
  229. package/dist/shims/metadata.js +62 -24
  230. package/dist/shims/navigation-server.js +1 -1
  231. package/dist/shims/navigation.d.ts +74 -7
  232. package/dist/shims/navigation.js +184 -31
  233. package/dist/shims/navigation.react-server.js +2 -2
  234. package/dist/shims/request-state-types.d.ts +3 -2
  235. package/dist/shims/slot.d.ts +16 -0
  236. package/dist/shims/slot.js +44 -9
  237. package/dist/shims/unified-request-context.d.ts +7 -1
  238. package/dist/shims/unified-request-context.js +3 -3
  239. package/dist/utils/cache-control-metadata.d.ts +5 -0
  240. package/dist/utils/cache-control-metadata.js +9 -1
  241. package/dist/utils/cache-life-profiles.d.ts +33 -0
  242. package/dist/utils/cache-life-profiles.js +111 -0
  243. package/dist/utils/middleware-request-headers.d.ts +14 -3
  244. package/dist/utils/middleware-request-headers.js +54 -7
  245. package/dist/utils/project.d.ts +2 -2
  246. package/dist/utils/project.js +3 -16
  247. package/dist/utils/regex.d.ts +5 -0
  248. package/dist/utils/regex.js +11 -1
  249. package/dist/utils/text-stream.d.ts +10 -5
  250. package/dist/utils/text-stream.js +6 -6
  251. package/package.json +2 -1
  252. package/dist/build/layout-classification-types.d.ts +0 -60
  253. package/dist/build/layout-classification-types.js +0 -1
  254. package/dist/build/layout-classification.d.ts +0 -62
  255. package/dist/build/layout-classification.js +0 -98
  256. package/dist/build/route-classification-injector.d.ts +0 -33
  257. package/dist/build/route-classification-injector.js +0 -59
  258. package/dist/build/route-classification-manifest.d.ts +0 -54
  259. package/dist/build/route-classification-manifest.js +0 -143
  260. package/dist/server/app-browser-client-reuse-manifest.d.ts +0 -11
  261. package/dist/server/app-browser-client-reuse-manifest.js +0 -101
  262. package/dist/server/app-layout-param-observation.d.ts +0 -42
  263. package/dist/server/app-layout-param-observation.js +0 -168
  264. package/dist/server/client-reuse-manifest.d.ts +0 -103
  265. package/dist/server/client-reuse-manifest.js +0 -209
  266. package/dist/server/skip-cache-proof.d.ts +0 -60
  267. package/dist/server/skip-cache-proof.js +0 -168
  268. package/dist/server/static-layout-client-reuse-proof.d.ts +0 -14
  269. package/dist/server/static-layout-client-reuse-proof.js +0 -33
  270. package/dist/utils/sorted-array.d.ts +0 -8
  271. package/dist/utils/sorted-array.js +0 -20
@@ -11,24 +11,24 @@ import { resolveDirectHybridClientRouteOwner } from "./internal/hybrid-client-ro
11
11
  import { isHashOnlyBrowserUrlChange, toCanonicalBrowserNavigationHref, toSameOriginAppPath, withBasePath } from "./url-utils.js";
12
12
  import { disableSmoothScrollDuringRouteTransition } from "./disable-smooth-scroll.js";
13
13
  import { retryScrollTo, scrollToHashTarget } from "./hash-scroll.js";
14
- import { AppElementsWire } from "../server/app-elements-wire.js";
15
- import "../server/app-elements.js";
16
- import { GLOBAL_ACCESSORS_KEY, ServerInsertedHTMLContext, _registerStateAccessors, clearClientHydrationContext, clearServerInsertedHTML, flushServerInsertedHTML, getBfcacheIdMapContext, getBfcacheSegmentIdContext, getLayoutSegmentContext, getNavigationContext, registerServerInsertedHTMLCallback, renderServerInsertedHTML, setNavigationContext } from "./navigation-context-state.js";
17
- import { BailoutToCSRError, DynamicServerError, HTTP_ERROR_FALLBACK_ERROR_CODE, RedirectType, decodeRedirectError, forbidden, getAccessFallbackHTTPStatus, isBailoutToCSRError, isDynamicServerError, isHTTPAccessFallbackError, isNextRouterError, isRedirectError, notFound, permanentRedirect, redirect, unauthorized, unstable_rethrow } from "./navigation-errors.js";
14
+ import { VINEXT_RSC_COMPATIBILITY_ID_HEADER, VINEXT_RSC_CONTENT_TYPE, createRscRequestHeaders, createRscRequestUrl, formatRscRequestPath, parseRscRequestPath, stripRscCacheBustingSearchParam } from "../server/app-rsc-cache-busting.js";
18
15
  import { clearAppNavigationFailureTarget, stageAppNavigationFailureTarget } from "../client/app-nav-failure-handler.js";
19
- import { beginAppRouterScrollIntent, clearAppRouterScrollIntent, consumeAppRouterScrollIntent, getPendingAppRouterScrollIntent, isLatestAppRouterScrollIntent } from "./app-router-scroll-state.js";
20
- import { VINEXT_RSC_COMPATIBILITY_ID_HEADER, VINEXT_RSC_CONTENT_TYPE, createRscRequestHeaders, createRscRequestUrl, formatRscRequestPath, parseRscRequestPath, stripRscCacheBustingSearchParam, stripRscSuffix } from "../server/app-rsc-cache-busting.js";
21
16
  import { notifyAppRouterTransitionStart } from "../client/instrumentation-client-state.js";
22
17
  import { getNavigationRuntime, hasAppNavigationRuntime, loadNavigationRuntimeRouteManifest } from "../client/navigation-runtime.js";
23
18
  import { UnrecognizedActionError, unstable_isUnrecognizedActionError } from "./unrecognized-action-error.js";
19
+ import { AppElementsWire } from "../server/app-elements-wire.js";
20
+ import "../server/app-elements.js";
24
21
  import { PUBLIC_INITIAL_BFCACHE_ID } from "../server/app-bfcache-id.js";
25
22
  import { resolveManifestNavigationInterceptionContext } from "../server/app-browser-interception-context.js";
26
- import { createExternalHistoryStatePreservingMetadata, createHashOnlyHistoryStatePreservingNavigationMetadata, isAppOwnedHistoryState } from "../server/app-history-state.js";
23
+ import { createExternalHistoryStatePreservingMetadata, createHashOnlyHistoryStatePreservingNavigationMetadata, isAppOwnedHistoryState, readHistoryStateTraversalIndex } from "../server/app-history-state.js";
27
24
  import { hasPendingAppRouterPageRedirect } from "../server/app-browser-mpa-navigation.js";
28
25
  import { extractRscCompletionMetadata } from "../server/rsc-completion-metadata.js";
29
26
  import { navigationPlanner } from "../server/navigation-planner.js";
30
27
  import { ReadonlyURLSearchParams } from "./readonly-url-search-params.js";
28
+ import { BailoutToCSRError, DynamicServerError, HTTP_ERROR_FALLBACK_ERROR_CODE, RedirectType, decodeRedirectError, forbidden, getAccessFallbackHTTPStatus, isBailoutToCSRError, isDynamicServerError, isHTTPAccessFallbackError, isNextRouterError, isRedirectError, notFound, permanentRedirect, redirect, unauthorized, unstable_rethrow } from "./navigation-errors.js";
31
29
  import { getPagesNavigationContext } from "./internal/pages-router-accessor.js";
30
+ import { beginAppRouterScrollIntent, clearAppRouterScrollIntent, consumeAppRouterScrollIntent, getPendingAppRouterScrollIntent, isLatestAppRouterScrollIntent } from "./app-router-scroll-state.js";
31
+ import { GLOBAL_ACCESSORS_KEY, ServerInsertedHTMLContext, _registerStateAccessors, clearClientHydrationContext, clearServerInsertedHTML, flushServerInsertedHTML, getBfcacheIdMapContext, getBfcacheSegmentIdContext, getLayoutSegmentContext, getNavigationContext, registerServerInsertedHTMLCallback, renderServerInsertedHTML, setNavigationContext } from "./navigation-context-state.js";
32
32
  import { cancelAppPrefetchFetch, promoteAppPrefetchFetch, releaseAppPrefetchFetchSlot, scheduleAppPrefetchFetch } from "./internal/app-prefetch-fetch-queue.js";
33
33
  import * as React$1 from "react";
34
34
  //#region src/shims/navigation.ts
@@ -245,8 +245,7 @@ function normalizeRscCacheLookupUrl(rscUrl) {
245
245
  }
246
246
  function normalizeRscCacheLookupPathname(rscUrl) {
247
247
  try {
248
- const url = parseRscRequestPath(rscUrl);
249
- return stripRscSuffix(url.pathname);
248
+ return parseRscRequestPath(rscUrl).pathname;
250
249
  } catch {
251
250
  return null;
252
251
  }
@@ -467,9 +466,13 @@ const retainedPrefetchInvalidations = /* @__PURE__ */ new Set();
467
466
  function retainPrefetchInvalidationAfterConsume(entry) {
468
467
  const callbacks = entry.onInvalidateCallbacks;
469
468
  if (callbacks === void 0 || callbacks.size === 0) return;
470
- const delay = Math.max(0, resolvePrefetchCacheEntryExpiresAt(entry) - Date.now());
469
+ retainPrefetchInvalidation(callbacks, resolvePrefetchCacheEntryExpiresAt(entry));
470
+ }
471
+ function retainPrefetchInvalidation(callbacks, expiresAt, forVisitedResponse = false) {
472
+ const delay = Math.max(0, expiresAt - Date.now());
471
473
  const retained = {
472
474
  callbacks,
475
+ ...forVisitedResponse ? { forVisitedResponse: true } : {},
473
476
  timer: setTimeout(() => fireRetainedPrefetchInvalidation(retained), delay)
474
477
  };
475
478
  retainedPrefetchInvalidations.add(retained);
@@ -570,14 +573,37 @@ function attachPrefetchInvalidationCallback(cacheKey, onInvalidate) {
570
573
  if (!entry) return;
571
574
  attachPrefetchInvalidationToEntry(cacheKey, entry, onInvalidate);
572
575
  }
573
- function invalidatePrefetchCache() {
576
+ function invalidatePrefetchCache(options = {}) {
574
577
  cancelPendingPrefetchSetups(null);
575
578
  const cache = getPrefetchCache();
576
579
  const prefetched = getPrefetchedUrls();
577
580
  for (const [cacheKey, entry] of cache) deletePrefetchCacheEntry(cache, prefetched, cacheKey, entry, true);
578
581
  prefetched.clear();
579
582
  for (const retained of retainedPrefetchInvalidations) fireRetainedPrefetchInvalidation(retained);
580
- if (!isServer) getNavigationRuntime()?.functions.pingVisibleLinks?.();
583
+ if (!isServer && options.pingVisibleLinks !== false) getNavigationRuntime()?.functions.pingVisibleLinks?.();
584
+ }
585
+ /**
586
+ * Evict the prefetch entries that may hold dynamic data, for a Server Action
587
+ * that called `refresh()`. Like Next.js's dynamic-only revalidation, which
588
+ * evicts its BFCache but keeps its prefetch cache, this keeps route trees,
589
+ * static prefetches and full prefetches. It drops navigation responses, and
590
+ * automatic prefetches whose page rendered dynamically or hasn't finished
591
+ * rendering, including those only kept to learn a route: Next.js's automatic
592
+ * prefetches never hold dynamic data.
593
+ */
594
+ function invalidateDynamicPrefetchCache() {
595
+ const cache = getPrefetchCache();
596
+ const prefetched = getPrefetchedUrls();
597
+ const evicted = [];
598
+ for (const [cacheKey, entry] of cache) if (!(entry.prefetchKind === "route-tree" || entry.prefetchKind !== void 0 && (entry.dynamicStaleTime === "full-prefetch" || entry.snapshot !== void 0 && !isStaleTimeSeconds(entry.snapshot.dynamicStaleTimeSeconds)))) evicted.push([cacheKey, entry]);
599
+ for (const [cacheKey, entry] of evicted) deletePrefetchCacheEntry(cache, prefetched, cacheKey, entry, true);
600
+ }
601
+ /**
602
+ * Notify the prefetches that stood in for a visited response (see
603
+ * `hasNavigationFreshVisitedResponse`), as the visited responses are cleared.
604
+ */
605
+ function invalidateVisitedResponsePrefetches() {
606
+ for (const retained of retainedPrefetchInvalidations) if (retained.forVisitedResponse === true) fireRetainedPrefetchInvalidation(retained);
581
607
  }
582
608
  /**
583
609
  * Prevent completed navigation responses from becoming authoritative again
@@ -593,7 +619,7 @@ function disableNavigationResponsePrefetchCacheReuse() {
593
619
  }
594
620
  if (didDemote && !isServer) getNavigationRuntime()?.functions.pingVisibleLinks?.();
595
621
  }
596
- function seedPrefetchResponseSnapshot(rscUrl, snapshot, interceptionContext = null, mountedSlotsHeader = null, fallbackTtlMs = DYNAMIC_NAVIGATION_CACHE_TTL, reuseAfterHistoryRestore = false) {
622
+ function seedPrefetchResponseSnapshot(rscUrl, snapshot, interceptionContext = null, mountedSlotsHeader = null, fallbackTtlMs = DYNAMIC_NAVIGATION_CACHE_TTL, reuseAfterHistoryRestore = false, expiresAt = resolveCachedRscResponseExpiresAt(Date.now(), snapshot, fallbackTtlMs)) {
597
623
  const cacheKey = AppElementsWire.encodeCacheKey(rscUrl, interceptionContext);
598
624
  const cache = getPrefetchCache();
599
625
  const existing = cache.get(cacheKey);
@@ -602,7 +628,7 @@ function seedPrefetchResponseSnapshot(rscUrl, snapshot, interceptionContext = nu
602
628
  const entry = {
603
629
  cacheForNavigation: true,
604
630
  cacheKeys: /* @__PURE__ */ new Set([cacheKey]),
605
- expiresAt: resolveCachedRscResponseExpiresAt(timestamp, snapshot, fallbackTtlMs),
631
+ expiresAt,
606
632
  mountedSlotsHeader,
607
633
  outcome: "cache-seeded",
608
634
  reuseAfterHistoryRestore,
@@ -616,6 +642,35 @@ function seedPrefetchResponseSnapshot(rscUrl, snapshot, interceptionContext = nu
616
642
  schedulePrefetchInvalidation(cacheKey, entry);
617
643
  evictPrefetchCacheIfNeeded();
618
644
  }
645
+ /**
646
+ * Fulfill a full prefetch from the visited response of an earlier navigation,
647
+ * as Next.js does from its BFCache, instead of issuing a request. The data is
648
+ * fresh for the static stale time from the navigation, not the dynamic one
649
+ * (`attemptToFulfillDynamicSegmentFromBFCache`).
650
+ */
651
+ function seedFullPrefetchFromVisitedResponse(rscUrl, interceptionContext, mountedSlotsHeader, additionalRscUrls = [], onInvalidate) {
652
+ const visited = getNavigationRuntime()?.functions.readVisitedResponseForFullPrefetch?.([rscUrl, ...additionalRscUrls], interceptionContext, mountedSlotsHeader);
653
+ if (!visited) return false;
654
+ const expiresAt = visited.navigatedAt + Math.max(PREFETCH_CACHE_TTL, MIN_PREFETCH_STALE_TIME_MS);
655
+ if (expiresAt <= Date.now()) return false;
656
+ seedPrefetchResponseSnapshot(rscUrl, visited.response, interceptionContext, mountedSlotsHeader, void 0, true, expiresAt);
657
+ const cacheKey = AppElementsWire.encodeCacheKey(rscUrl, interceptionContext);
658
+ if (getPrefetchCache().get(cacheKey)?.snapshot !== visited.response) return false;
659
+ attachPrefetchInvalidationCallback(cacheKey, onInvalidate);
660
+ return true;
661
+ }
662
+ /**
663
+ * Whether a navigation to the URL would reuse the response of an earlier one,
664
+ * so a prefetch has nothing to fetch. Like Next.js, whose navigation keeps the
665
+ * route and its segments for `staleTimes.dynamic`. `onInvalidate` fires when
666
+ * that reuse ends.
667
+ */
668
+ function hasNavigationFreshVisitedResponse(rscUrl, interceptionContext, mountedSlotsHeader, additionalRscUrls = [], onInvalidate) {
669
+ const freshUntil = getNavigationRuntime()?.functions.readVisitedResponseForFullPrefetch?.([rscUrl, ...additionalRscUrls], interceptionContext, mountedSlotsHeader)?.navigationFreshUntil;
670
+ if (freshUntil === void 0 || freshUntil === null) return false;
671
+ if (onInvalidate !== void 0) retainPrefetchInvalidation(/* @__PURE__ */ new Set([onInvalidate]), freshUntil, true);
672
+ return true;
673
+ }
619
674
  function deletePrefetchResponseSnapshot(rscUrl, snapshot, interceptionContext = null) {
620
675
  const cacheKey = AppElementsWire.encodeCacheKey(rscUrl, interceptionContext);
621
676
  const cache = getPrefetchCache();
@@ -694,6 +749,7 @@ function createCachedRscResponseSnapshot(response, buffer, responseUrl = null) {
694
749
  ...dynamicStaleTimeSeconds !== void 0 ? { dynamicStaleTimeSeconds } : {},
695
750
  mountedSlotsHeader: response.headers.get(VINEXT_MOUNTED_SLOTS_HEADER),
696
751
  paramsHeader: response.headers.get(VINEXT_PARAMS_HEADER),
752
+ receivedAt: Date.now(),
697
753
  ...redirectHeader === null ? {} : { redirectHeader },
698
754
  ...redirectTypeHeader === null ? {} : { redirectTypeHeader },
699
755
  renderedPathAndSearch: parseRenderedPathAndSearchHeader(response.headers.get(VINEXT_RENDERED_PATH_AND_SEARCH_HEADER)),
@@ -862,7 +918,7 @@ function prefetchRscResponse(rscUrl, fetchPromise, interceptionContext = null, m
862
918
  if (behavior.dynamicStaleTime === "learning-only" && behavior.searchAgnosticShell !== true) {
863
919
  entry.dynamicStaleTime = "learning-only";
864
920
  entry.fallbackTtlMs = behavior.fallbackTtlMs ?? PREFETCH_CACHE_TTL;
865
- }
921
+ } else if (behavior.dynamicStaleTime === "full-prefetch") entry.dynamicStaleTime = "full-prefetch";
866
922
  addPrefetchInvalidationCallback(entry, options?.onInvalidate);
867
923
  entry.fetchPromise = fetchPromise;
868
924
  entry.pending = fetchPromise.then(async (response) => {
@@ -1022,6 +1078,8 @@ function getClientNavigationState() {
1022
1078
  originalPushState: window.history.pushState.bind(window.history),
1023
1079
  originalReplaceState: window.history.replaceState.bind(window.history),
1024
1080
  patchInstalled: false,
1081
+ routerHistoryWriteDepth: 0,
1082
+ routerHistoryWrite: null,
1025
1083
  hasPendingNavigationUpdate: false,
1026
1084
  suppressUrlNotifyCount: 0,
1027
1085
  navigationSnapshotActiveCount: 0
@@ -1365,16 +1423,80 @@ function commitClientNavigationState(navId, options) {
1365
1423
  if (urlChanged || paramsChanged) clearClientHydrationContext();
1366
1424
  if (shouldNotify) notifyNavigationListeners();
1367
1425
  }
1368
- function pushHistoryStateWithoutNotify(data, unused, url) {
1369
- withSuppressedUrlNotifications(() => {
1370
- getClientNavigationState()?.originalPushState.call(window.history, data, unused, url);
1371
- });
1426
+ /** Whether a history entry's state is the data written to it, cloned by the browser. */
1427
+ function isSameHistoryStateData(historyState, data) {
1428
+ try {
1429
+ return JSON.stringify(historyState) === JSON.stringify(data);
1430
+ } catch {
1431
+ return false;
1432
+ }
1433
+ }
1434
+ /** Writes the in-progress router write if this call is it, consuming its marker. */
1435
+ function forwardRouterHistoryWrite(state, method, data, unused, url) {
1436
+ const write = state.routerHistoryWrite;
1437
+ if (write?.method !== method) return false;
1438
+ if (write.threw) {
1439
+ if (url == null || new URL(url, window.location.href).href !== write.href) return false;
1440
+ if (write.data !== data && !(isAppOwnedHistoryState(data) && readHistoryStateTraversalIndex(data) === readHistoryStateTraversalIndex(write.data))) return false;
1441
+ } else if (write.data !== data || write.url !== url) return false;
1442
+ if (write.landed) return true;
1443
+ state.routerHistoryWrite = null;
1444
+ const landing = write.land?.(data);
1445
+ const original = method === "pushState" ? state.originalPushState : state.originalReplaceState;
1446
+ const writtenData = landing ? landing.data : data;
1447
+ const historyStateBeforeWrite = window.history.state;
1448
+ try {
1449
+ original.call(window.history, writtenData, unused, url);
1450
+ } catch (error) {
1451
+ const landed = window.history.state !== historyStateBeforeWrite && window.location.href === write.href && isSameHistoryStateData(window.history.state, writtenData);
1452
+ if (landed) landing?.commit();
1453
+ state.routerHistoryWrite = {
1454
+ ...write,
1455
+ threw: true,
1456
+ landed
1457
+ };
1458
+ throw error;
1459
+ }
1460
+ landing?.commit();
1461
+ if (write.threw) state.routerHistoryWrite = {
1462
+ ...write,
1463
+ landed: true
1464
+ };
1465
+ return true;
1372
1466
  }
1373
- function replaceHistoryStateWithoutNotify(data, unused, url) {
1467
+ function writeRouterHistoryState(method, data, unused, url, land) {
1374
1468
  withSuppressedUrlNotifications(() => {
1375
- getClientNavigationState()?.originalReplaceState.call(window.history, data, unused, url);
1469
+ const state = getClientNavigationState();
1470
+ if (!state) return;
1471
+ if (url == null) {
1472
+ (method === "pushState" ? state.originalPushState : state.originalReplaceState).call(window.history, data, unused, url);
1473
+ return;
1474
+ }
1475
+ const previousWrite = state.routerHistoryWrite;
1476
+ state.routerHistoryWriteDepth += 1;
1477
+ state.routerHistoryWrite = {
1478
+ method,
1479
+ data,
1480
+ url,
1481
+ href: new URL(url, window.location.href).href,
1482
+ land,
1483
+ threw: false,
1484
+ landed: false
1485
+ };
1486
+ try {
1487
+ window.history[method](data, unused, url);
1488
+ } finally {
1489
+ state.routerHistoryWriteDepth -= 1;
1490
+ state.routerHistoryWrite = previousWrite;
1491
+ }
1376
1492
  });
1377
1493
  }
1494
+ function pushHistoryStateWithoutNotify(data, unused, url, land) {
1495
+ writeRouterHistoryState("pushState", data, unused, url, land);
1496
+ }
1497
+ function replaceHistoryStateWithoutNotify(data, unused, url, land) {
1498
+ writeRouterHistoryState("replaceState", data, unused, url, land);
1499
+ }
1378
1500
  /**
1379
1501
  * Save the current scroll position into the current history state.
1380
1502
  * Called before every navigation to enable scroll restoration on back/forward.
@@ -1590,6 +1712,32 @@ function hasScheduledAppRouterNavigation() {
1590
1712
  function releaseScheduledAppRouterNavigationAfterCurrentTask(release) {
1591
1713
  queueMicrotask(release);
1592
1714
  }
1715
+ let inFlightAppRouterNavigationCount = 0;
1716
+ let visibleLinkPingAwaitsNavigations = false;
1717
+ /**
1718
+ * Called by the App Router browser entry for each RSC navigation it runs.
1719
+ * Returns a release callback for the navigation's settlement.
1720
+ */
1721
+ function trackAppRouterNavigationInFlight() {
1722
+ inFlightAppRouterNavigationCount += 1;
1723
+ let released = false;
1724
+ return () => {
1725
+ if (released) return;
1726
+ released = true;
1727
+ inFlightAppRouterNavigationCount = Math.max(0, inFlightAppRouterNavigationCount - 1);
1728
+ if (inFlightAppRouterNavigationCount === 0 && visibleLinkPingAwaitsNavigations) {
1729
+ visibleLinkPingAwaitsNavigations = false;
1730
+ getNavigationRuntime()?.functions.pingVisibleLinks?.();
1731
+ }
1732
+ };
1733
+ }
1734
+ function pingVisibleLinksOnceNavigationsSettle() {
1735
+ if (inFlightAppRouterNavigationCount > 0) {
1736
+ visibleLinkPingAwaitsNavigations = true;
1737
+ return;
1738
+ }
1739
+ getNavigationRuntime()?.functions.pingVisibleLinks?.();
1740
+ }
1593
1741
  /**
1594
1742
  * App Router public router instance. Mirrors Next.js's
1595
1743
  * `publicAppRouterInstance` from
@@ -1641,15 +1789,16 @@ const _appRouter = {
1641
1789
  },
1642
1790
  refresh() {
1643
1791
  if (isServer) return;
1644
- getNavigationRuntime()?.functions.clearNavigationCaches?.();
1645
- if (hasScheduledAppRouterNavigation()) return;
1792
+ getNavigationRuntime()?.functions.clearNavigationCaches?.({ pingVisibleLinks: false });
1646
1793
  const rscNavigate = getNavigationRuntime()?.functions.navigate;
1647
- if (rscNavigate) {
1648
- const navigate = () => {
1649
- rscNavigate(window.location.href, 0, "refresh", void 0, void 0, true);
1650
- };
1651
- React$1.startTransition(navigate);
1794
+ if (hasScheduledAppRouterNavigation() || !rscNavigate) {
1795
+ getNavigationRuntime()?.functions.pingVisibleLinks?.();
1796
+ return;
1652
1797
  }
1798
+ const navigate = () => {
1799
+ rscNavigate(window.location.href, 0, "refresh", void 0, void 0, true).finally(pingVisibleLinksOnceNavigationsSettle);
1800
+ };
1801
+ React$1.startTransition(navigate);
1653
1802
  },
1654
1803
  prefetch(href, options) {
1655
1804
  assertSafeNavigationUrl(href);
@@ -1720,7 +1869,9 @@ const _appRouter = {
1720
1869
  onInvalidate: options?.onInvalidate,
1721
1870
  onReuse: policy.dynamicStaleTime === "full-prefetch" ? (entry, matchedCacheKey) => promotePrefetchCacheEntryForNavigation(matchedCacheKey, entry) : void 0
1722
1871
  })) return;
1872
+ if (policy.dynamicStaleTime === "full-prefetch" && seedFullPrefetchFromVisitedResponse(rscUrl, interceptionContext, mountedSlotsHeader, additionalRscUrls, options?.onInvalidate)) return;
1723
1873
  }
1874
+ if (policy.dynamicStaleTime !== "full-prefetch" && hasNavigationFreshVisitedResponse(rscUrl, interceptionContext, mountedSlotsHeader, additionalRscUrls, options?.onInvalidate)) return;
1724
1875
  prefetched.add(cacheKey);
1725
1876
  const fetchFullRscPayload = () => scheduleAppPrefetchFetch((signal) => fetch(rscUrl, {
1726
1877
  headers,
@@ -1878,7 +2029,8 @@ if (!isServer) {
1878
2029
  }
1879
2030
  });
1880
2031
  window.history.pushState = function patchedPushState(data, unused, url) {
1881
- getNavigationRuntime()?.functions.flushCommittingNavigationUrl?.();
2032
+ if (forwardRouterHistoryWrite(state, "pushState", data, unused, url)) return;
2033
+ if (state.routerHistoryWriteDepth === 0) getNavigationRuntime()?.functions.flushCommittingNavigationUrl?.();
1882
2034
  if (isAppOwnedHistoryState(data)) {
1883
2035
  const previousHistoryState = window.history.state;
1884
2036
  state.originalPushState.call(window.history, data, unused, url);
@@ -1895,7 +2047,8 @@ if (!isServer) {
1895
2047
  }
1896
2048
  };
1897
2049
  window.history.replaceState = function patchedReplaceState(data, unused, url) {
1898
- getNavigationRuntime()?.functions.flushCommittingNavigationUrl?.();
2050
+ if (forwardRouterHistoryWrite(state, "replaceState", data, unused, url)) return;
2051
+ if (state.routerHistoryWriteDepth === 0) getNavigationRuntime()?.functions.flushCommittingNavigationUrl?.();
1899
2052
  if (isAppOwnedHistoryState(data)) {
1900
2053
  const previousHistoryState = window.history.state;
1901
2054
  state.originalReplaceState.call(window.history, data, unused, url);
@@ -1914,4 +2067,4 @@ if (!isServer) {
1914
2067
  }
1915
2068
  }
1916
2069
  //#endregion
1917
- export { BailoutToCSRError, DYNAMIC_NAVIGATION_CACHE_TTL, DynamicServerError, GLOBAL_ACCESSORS_KEY, HTTP_ERROR_FALLBACK_ERROR_CODE, MAX_PREFETCH_CACHE_SIZE, PREFETCH_CACHE_TTL, ReadonlyURLSearchParams, RedirectType, ServerInsertedHTMLContext, UnrecognizedActionError, __basePath, _registerStateAccessors, activateNavigationSnapshot, appRouterInstance, applyAppRouterScrollFallback, clearPendingPathname, clearServerInsertedHTML, commitClientNavigationState, consumePrefetchResponse, consumePrefetchResponseForNavigation, createAppPrefetchRequestHeaders, createCachedRscResponseSnapshot, createClientNavigationRenderSnapshot, createSnapshotPathAndSearch, decodeRedirectError, deletePrefetchResponseSnapshot, disableNavigationResponsePrefetchCacheReuse, discardLearningOnlyPrefetchCacheEntry, fetchRouteTreeGatedPrefetch, flushServerInsertedHTML, forbidden, getAccessFallbackHTTPStatus, getBfcacheIdMapContext, getBfcacheSegmentIdContext, getClientNavigationRenderContext, getClientNavigationState, getClientParams, getCurrentInterceptionContext, getCurrentNextUrl, getFreshPrefetchCacheEntry, getLayoutSegmentContext, getMountedSlotsHeader, getNavigationContext, getPrefetchCache, getPrefetchInterceptionContext, getPrefetchedUrls, hasFreshLearningOnlyPrefetchCacheEntry, hasPrefetchCacheEntryForNavigation, hasSearchAgnosticPrefetchShellForRoute, invalidatePrefetchCache, isBailoutToCSRError, isDynamicServerError, isHTTPAccessFallbackError, isNextRouterError, isRedirectError, navigateClientSide, notFound, parseRenderedPathAndSearchHeader, peekPrefetchResponseForNavigation, permanentRedirect, prefetchRscResponse, preloadHybridClientRouteOwner, prepareNavigationPrefetchSnapshot, promotePrefetchCacheEntryForNavigation, pushHistoryStateWithoutNotify, redirect, renderServerInsertedHTML, replaceClientParamsWithoutNotify, replaceHistoryStateWithoutNotify, resolveCachedRscResponseExpiresAt, resolveCachedRscResponseTtlMs, resolveLoadedHybridClientRewriteHref, resolvePrefetchCacheEntryMountedSlotsHeader, restoreRscResponse, saveScrollPosition, seedPrefetchResponseSnapshot, setClientParams, setMountedSlotsHeader, setNavigationContext, setPendingPathname, snapshotRscResponse, storePrefetchResponse, unauthorized, unstable_isUnrecognizedActionError, unstable_rethrow, useClientNavigationRenderSnapshot, useParams, usePathname, useRouter, useSearchParams, useSelectedLayoutSegment, useSelectedLayoutSegments, useServerInsertedHTML };
2070
+ export { BailoutToCSRError, DYNAMIC_NAVIGATION_CACHE_TTL, DynamicServerError, GLOBAL_ACCESSORS_KEY, HTTP_ERROR_FALLBACK_ERROR_CODE, MAX_PREFETCH_CACHE_SIZE, PREFETCH_CACHE_TTL, ReadonlyURLSearchParams, RedirectType, ServerInsertedHTMLContext, UnrecognizedActionError, __basePath, _registerStateAccessors, activateNavigationSnapshot, appRouterInstance, applyAppRouterScrollFallback, clearPendingPathname, clearServerInsertedHTML, commitClientNavigationState, consumePrefetchResponse, consumePrefetchResponseForNavigation, createAppPrefetchRequestHeaders, createCachedRscResponseSnapshot, createClientNavigationRenderSnapshot, createSnapshotPathAndSearch, decodeRedirectError, deletePrefetchResponseSnapshot, disableNavigationResponsePrefetchCacheReuse, discardLearningOnlyPrefetchCacheEntry, fetchRouteTreeGatedPrefetch, flushServerInsertedHTML, forbidden, getAccessFallbackHTTPStatus, getBfcacheIdMapContext, getBfcacheSegmentIdContext, getClientNavigationRenderContext, getClientNavigationState, getClientParams, getCurrentInterceptionContext, getCurrentNextUrl, getFreshPrefetchCacheEntry, getLayoutSegmentContext, getMountedSlotsHeader, getNavigationContext, getPrefetchCache, getPrefetchInterceptionContext, getPrefetchedUrls, hasFreshLearningOnlyPrefetchCacheEntry, hasNavigationFreshVisitedResponse, hasPrefetchCacheEntryForNavigation, hasSearchAgnosticPrefetchShellForRoute, invalidateDynamicPrefetchCache, invalidatePrefetchCache, invalidateVisitedResponsePrefetches, isBailoutToCSRError, isDynamicServerError, isHTTPAccessFallbackError, isNextRouterError, isRedirectError, navigateClientSide, notFound, parseRenderedPathAndSearchHeader, peekPrefetchResponseForNavigation, permanentRedirect, prefetchRscResponse, preloadHybridClientRouteOwner, prepareNavigationPrefetchSnapshot, promotePrefetchCacheEntryForNavigation, pushHistoryStateWithoutNotify, redirect, renderServerInsertedHTML, replaceClientParamsWithoutNotify, replaceHistoryStateWithoutNotify, resolveCachedRscResponseExpiresAt, resolveCachedRscResponseTtlMs, resolveLoadedHybridClientRewriteHref, resolvePrefetchCacheEntryMountedSlotsHeader, restoreRscResponse, saveScrollPosition, seedFullPrefetchFromVisitedResponse, seedPrefetchResponseSnapshot, setClientParams, setMountedSlotsHeader, setNavigationContext, setPendingPathname, snapshotRscResponse, storePrefetchResponse, trackAppRouterNavigationInFlight, unauthorized, unstable_isUnrecognizedActionError, unstable_rethrow, useClientNavigationRenderSnapshot, useParams, usePathname, useRouter, useSearchParams, useSelectedLayoutSegment, useSelectedLayoutSegments, useServerInsertedHTML };
@@ -1,7 +1,7 @@
1
- import { GLOBAL_ACCESSORS_KEY, ServerInsertedHTMLContext, _registerStateAccessors, clearServerInsertedHTML, flushServerInsertedHTML, getLayoutSegmentContext, getNavigationContext, renderServerInsertedHTML, setNavigationContext } from "./navigation-context-state.js";
1
+ import { ReadonlyURLSearchParams } from "./readonly-url-search-params.js";
2
2
  import { BailoutToCSRError, DynamicServerError, HTTP_ERROR_FALLBACK_ERROR_CODE, RedirectType, forbidden, getAccessFallbackHTTPStatus, isBailoutToCSRError, isDynamicServerError, isHTTPAccessFallbackError, isNextRouterError, isRedirectError, notFound, permanentRedirect, redirect, unauthorized, unstable_rethrow } from "./navigation-errors.js";
3
+ import { GLOBAL_ACCESSORS_KEY, ServerInsertedHTMLContext, _registerStateAccessors, clearServerInsertedHTML, flushServerInsertedHTML, getLayoutSegmentContext, getNavigationContext, renderServerInsertedHTML, setNavigationContext } from "./navigation-context-state.js";
3
4
  import "./navigation-server.js";
4
- import { ReadonlyURLSearchParams } from "./readonly-url-search-params.js";
5
5
  import { throwClientHookError } from "./client-hook-error.js";
6
6
  //#region src/shims/navigation.react-server.ts
7
7
  function usePathname() {
@@ -1,12 +1,13 @@
1
- import { ExecutionContextLike } from "./request-context.js";
1
+ import { CacheLifeConfig } from "../utils/cache-life-profiles.js";
2
2
  import { NavigationContext } from "./navigation-context-state.js";
3
3
  import "./navigation.js";
4
- import { CacheLifeConfig, CacheState } from "./cache-request-state.js";
4
+ import { ExecutionContextLike } from "./request-context.js";
5
5
  import { RootParamsState } from "./root-params.js";
6
6
  import { FetchCacheState } from "./fetch-cache-state.js";
7
7
  import "./fetch-cache.js";
8
8
  import { HeadersAccessPhase, VinextHeadersShimState } from "./internal/headers-state.js";
9
9
  import { HeadersContext } from "./headers.js";
10
+ import { CacheState } from "./cache-request-state.js";
10
11
  import { RouterState, SSRContext } from "./router-state.js";
11
12
  import { PrivateCacheState } from "./cache-runtime.js";
12
13
  import { HeadState } from "./head-state.js";
@@ -40,6 +40,7 @@ type MergeElementsOptions = {
40
40
  clearAbsentSlots?: boolean;
41
41
  preserveAbsentSlots?: boolean;
42
42
  preserveElementIds?: readonly string[];
43
+ preserveElementSeedIds?: readonly string[];
43
44
  preservePreviousSlotIds?: readonly string[];
44
45
  };
45
46
  export declare function updateBfcacheSlotEntryOrder(previousOrder: readonly string[], activeStateKey: string, maxEntries?: number): string[];
@@ -59,6 +60,21 @@ export declare function BfcacheSegmentBoundary({ children, id, stateKey }: {
59
60
  id: string;
60
61
  stateKey: string;
61
62
  }): React$1.JSX.Element;
63
+ /**
64
+ * Retains a layout's children across navigations that change which segment
65
+ * they render. Each child keeps its own wrappers, so a page and a nested layout
66
+ * give the layout's children different element shapes, and a retention list
67
+ * inside the child would remount with them. Next.js keeps this Activity list in
68
+ * the parent's layout router, above the child's boundaries, so a page left for a
69
+ * sibling with its own layout keeps its state when navigating back.
70
+ */
71
+ export declare function BfcacheChildrenBoundary({ children, id, stateKey }: {
72
+ children: React$1.ReactNode;
73
+ /** The child element whose identity keys the entries. */
74
+ id?: string;
75
+ /** A fixed key, for a segment level with no element of its own. */
76
+ stateKey?: string;
77
+ }): React$1.JSX.Element;
62
78
  export declare function getNonCacheComponentsSegmentKey(id: string, activeStateKey: string): string | undefined;
63
79
  export declare function resolveBfcacheSegmentStateKey(id: string, identityMap: Readonly<Record<string, string>>, bfcacheIdMap: Readonly<Record<string, string>> | null): string | undefined;
64
80
  export declare function mergeElements(prev: AppElements, next: AppElements, options?: MergeElementsOptions | boolean): AppElements;
@@ -1,10 +1,10 @@
1
1
  "use client";
2
2
  import { APP_BFCACHE_SEGMENT_IDENTITIES_KEY, AppElementsWire, UNMATCHED_SLOT } from "../server/app-elements-wire.js";
3
3
  import "../server/app-elements.js";
4
- import { getBfcacheIdMapContext, getBfcacheSegmentIdContext } from "./navigation-context-state.js";
4
+ import { isNestedBfcacheSlotSegmentId, isNestedBfcacheSlotSegmentIdFor } from "../server/bfcache-identity.js";
5
5
  import { notFound } from "./navigation-errors.js";
6
+ import { getBfcacheIdMapContext, getBfcacheSegmentIdContext } from "./navigation-context-state.js";
6
7
  import "./navigation-server.js";
7
- import { isNestedBfcacheSlotSegmentId, isNestedBfcacheSlotSegmentIdFor } from "../server/bfcache-identity.js";
8
8
  import * as React$1 from "react";
9
9
  import { Fragment as Fragment$1, jsx } from "react/jsx-runtime";
10
10
  //#region src/shims/slot.tsx
@@ -92,11 +92,6 @@ function stageBfcacheSlotEntryForRender(committedSnapshots, committedOrder, acti
92
92
  snapshots
93
93
  };
94
94
  }
95
- function isLayoutFlagsValue(value) {
96
- if (typeof value !== "object" || value === null || Array.isArray(value)) return false;
97
- const entries = Object.values(value);
98
- return entries.length > 0 && entries.every((entry) => entry === "s" || entry === "d");
99
- }
100
95
  function isArtifactCompatibilityEnvelopeValue(value) {
101
96
  if (typeof value !== "object" || value === null || Array.isArray(value)) return false;
102
97
  return "schemaVersion" in value && "appElementsSchemaVersion" in value && "rscPayloadSchemaVersion" in value && "graphVersion" in value && "deploymentVersion" in value && "rootBoundaryId" in value && "renderEpoch" in value;
@@ -127,7 +122,7 @@ function isCacheEntryReuseProofValue(value) {
127
122
  return "kind" in value && value.kind === "runtime-cache-entry" && "decision" in value;
128
123
  }
129
124
  function isTransportMetadataValue(id, value) {
130
- return isLayoutFlagsValue(value) || isBfcacheSegmentIdentitiesMetadataValue(id, value) || isArtifactCompatibilityEnvelopeValue(value) || isCacheEntryReuseProofValue(value) || isInterceptionMetadataValue(value) || isSkippedLayoutIdsMetadataValue(id, value) || isSlotBindingListValue(value);
125
+ return isBfcacheSegmentIdentitiesMetadataValue(id, value) || isArtifactCompatibilityEnvelopeValue(value) || isCacheEntryReuseProofValue(value) || isInterceptionMetadataValue(value) || isSkippedLayoutIdsMetadataValue(id, value) || isSlotBindingListValue(value);
131
126
  }
132
127
  function warnTransportMetadataEntry(id) {
133
128
  if (process.env.NODE_ENV === "production") return;
@@ -210,6 +205,40 @@ function BfcacheSegmentBoundary({ children, id, stateKey }) {
210
205
  stateKeyMap: identityMap
211
206
  });
212
207
  }
208
+ /**
209
+ * Retains a layout's children across navigations that change which segment
210
+ * they render. Each child keeps its own wrappers, so a page and a nested layout
211
+ * give the layout's children different element shapes, and a retention list
212
+ * inside the child would remount with them. Next.js keeps this Activity list in
213
+ * the parent's layout router, above the child's boundaries, so a page left for a
214
+ * sibling with its own layout keeps its state when navigating back.
215
+ */
216
+ function BfcacheChildrenBoundary({ children, id, stateKey }) {
217
+ if (!BfcacheIdMapContext || !BfcacheSegmentIdContext || !isCacheComponentsEnabled()) return /* @__PURE__ */ jsx(Fragment$1, { children });
218
+ return /* @__PURE__ */ jsx(BfcacheChildrenActivityBoundary, {
219
+ id,
220
+ IdMapContext: BfcacheIdMapContext,
221
+ SegmentContext: BfcacheSegmentIdContext,
222
+ stateKey,
223
+ children
224
+ });
225
+ }
226
+ function BfcacheChildrenActivityBoundary({ children, id, IdMapContext, SegmentContext, stateKey }) {
227
+ const elements = React$1.useContext(ElementsContext);
228
+ const identityMap = React$1.useContext(BfcacheIdentityMapContext);
229
+ const bfcacheIdMap = React$1.useContext(IdMapContext);
230
+ const segmentId = React$1.useContext(SegmentContext);
231
+ const activeStateKey = stateKey ?? (id === void 0 ? void 0 : resolveBfcacheSegmentStateKey(id, identityMap, bfcacheIdMap));
232
+ if (segmentId === null || activeStateKey === void 0) return /* @__PURE__ */ jsx(Fragment$1, { children });
233
+ return /* @__PURE__ */ jsx(BfcacheActivitySlotBoundary, {
234
+ activeStateKey,
235
+ content: children,
236
+ elements,
237
+ id: segmentId,
238
+ SegmentContext,
239
+ stateKeyMap: identityMap
240
+ });
241
+ }
213
242
  function getNonCacheComponentsSegmentKey(id, activeStateKey) {
214
243
  const parsed = AppElementsWire.parseElementKey(id);
215
244
  return parsed !== null && parsed.kind !== "route" ? activeStateKey : void 0;
@@ -244,6 +273,7 @@ function mergeElements(prev, next, options = {}) {
244
273
  const clearAbsentSlots = typeof options === "boolean" ? options : options.clearAbsentSlots ?? false;
245
274
  const preserveAbsentSlots = typeof options === "boolean" ? !options : options.preserveAbsentSlots ?? true;
246
275
  const preserveElementIds = typeof options === "boolean" ? [] : options.preserveElementIds ?? [];
276
+ const preserveElementSeedIds = typeof options === "boolean" ? [] : options.preserveElementSeedIds ?? [];
247
277
  const preservePreviousSlotIds = typeof options === "boolean" ? [] : options.preservePreviousSlotIds ?? [];
248
278
  const merged = { ...next };
249
279
  const preservedIdentityIds = /* @__PURE__ */ new Set();
@@ -254,6 +284,11 @@ function mergeElements(prev, next, options = {}) {
254
284
  preservedIdentityIds.add(id);
255
285
  }
256
286
  }
287
+ for (const id of preserveElementSeedIds) {
288
+ if (preservedIdentityIds.has(id) || !Object.hasOwn(prev, id)) continue;
289
+ const value = prev[id];
290
+ if (value !== void 0) merged[id] = value;
291
+ }
257
292
  const slotKeys = new Set([...Object.keys(prev), ...Object.keys(next)].filter((key) => AppElementsWire.isSlotId(key) && !isNestedBfcacheSlotSegmentId(key)));
258
293
  if (clearAbsentSlots) {
259
294
  for (const key of slotKeys) if (!Object.hasOwn(next, key)) delete merged[key];
@@ -340,4 +375,4 @@ function ParallelSlot({ name }) {
340
375
  return React$1.useContext(ParallelSlotsContext)?.[name] ?? null;
341
376
  }
342
377
  //#endregion
343
- export { BfcacheIdentityMapContext, BfcacheSegmentBoundary, Children, ChildrenContext, ElementsContext, ParallelSlot, ParallelSlotsContext, RenderedSearchContext, Slot, UNMATCHED_SLOT, bindAppElementsRenderedSearch, getNonCacheComponentsSegmentKey, mergeElements, resolveBfcacheSegmentStateKey, setAppElementsRenderedSearch, stageBfcacheSlotEntryForRender, updateBfcacheSlotEntryOrder };
378
+ export { BfcacheChildrenBoundary, BfcacheIdentityMapContext, BfcacheSegmentBoundary, Children, ChildrenContext, ElementsContext, ParallelSlot, ParallelSlotsContext, RenderedSearchContext, Slot, UNMATCHED_SLOT, bindAppElementsRenderedSearch, getNonCacheComponentsSegmentKey, mergeElements, resolveBfcacheSegmentStateKey, setAppElementsRenderedSearch, stageBfcacheSlotEntryForRender, updateBfcacheSlotEntryOrder };
@@ -1,8 +1,8 @@
1
1
  import { ExecutionContextLike } from "./request-context.js";
2
- import { CacheState } from "./cache-request-state.js";
3
2
  import { RootParamsState } from "./root-params.js";
4
3
  import { FetchCacheState } from "./fetch-cache-state.js";
5
4
  import { VinextHeadersShimState } from "./internal/headers-state.js";
5
+ import { CacheState } from "./cache-request-state.js";
6
6
  import { RouterState } from "./router-state.js";
7
7
  import { markFullyBufferedBody, preserveFullyBufferedBodyMetadata } from "../server/fully-buffered-response.js";
8
8
  import { PrivateCacheState } from "./cache-runtime.js";
@@ -30,6 +30,12 @@ export type UnifiedRequestContext = {
30
30
  requestCache: WeakMap<(...args: any[]) => any, unknown>;
31
31
  /** Shared lifecycle state for work deferred until the response closes. */
32
32
  afterContext: AfterRequestContext;
33
+ /**
34
+ * Draft-mode state of the headers context this request last cleared. The
35
+ * render can outlive its headers context (cleared once the response body
36
+ * closes), and so do after() callbacks; cache bypasses keep reading this.
37
+ */
38
+ draftModeAtHeadersClear: boolean;
33
39
  } & VinextHeadersShimState & I18nState & NavigationState & CacheState & PrivateCacheState & FetchCacheState & RouterState & HeadState & RootParamsState;
34
40
  export type AfterRequestContext = {
35
41
  callbacks: Array<() => unknown>;
@@ -18,7 +18,7 @@ function createRequestContext(opts) {
18
18
  return {
19
19
  headersContext: null,
20
20
  actionRevalidationKind: 0,
21
- cacheLifeSink: null,
21
+ isOnDemandRevalidate: false,
22
22
  pendingCdnTagInvalidations: [],
23
23
  pendingRevalidatedTags: /* @__PURE__ */ new Set(),
24
24
  pendingRevalidations: /* @__PURE__ */ new Set(),
@@ -37,15 +37,14 @@ function createRequestContext(opts) {
37
37
  serverContext: null,
38
38
  serverInsertedHTMLCallbacks: [],
39
39
  requestScopedCacheLife: null,
40
- unstableCacheObservations: /* @__PURE__ */ new Map(),
41
40
  unstableCacheRevalidation: "foreground",
42
41
  _privateCache: null,
43
- cacheableFetchUrls: /* @__PURE__ */ new Set(),
44
42
  currentRequestTags: [],
45
43
  currentFetchSoftTags: [],
46
44
  currentFetchCacheMode: null,
47
45
  currentFetchRevalidate: null,
48
46
  currentForceDynamicFetchDefault: false,
47
+ isDraftMode: false,
49
48
  dynamicFetchUrls: /* @__PURE__ */ new Set(),
50
49
  refreshStaleFetchesInForeground: false,
51
50
  isFetchDedupeActive: false,
@@ -54,6 +53,7 @@ function createRequestContext(opts) {
54
53
  executionContext: _getInheritedExecutionContext(),
55
54
  requestSignal: null,
56
55
  requestCache: /* @__PURE__ */ new WeakMap(),
56
+ draftModeAtHeadersClear: false,
57
57
  afterContext: {
58
58
  callbacks: [],
59
59
  responseClosed: false,
@@ -1,5 +1,10 @@
1
1
  //#region src/utils/cache-control-metadata.d.ts
2
2
  export declare function readCacheControlNumberField(ctx: Record<string, unknown> | undefined, field: string): number | undefined;
3
+ /**
4
+ * When a `"use cache"` entry's generation started (`ctx.timestamp`), which dates
5
+ * the entry like Next.js does. Absent, malformed or future values fall back to `now`.
6
+ */
7
+ export declare function readCacheTimestamp(ctx: Record<string, unknown> | undefined, now: number): number;
3
8
  export declare function readCacheControlRevalidateField(ctx: Record<string, unknown> | undefined): number | false | undefined;
4
9
  /**
5
10
  * Client-reuse seconds from a resolved `cacheLife`. Shared by every emitter
@@ -8,6 +8,14 @@ function readCacheControlNumberField(ctx, field) {
8
8
  const value = readRecordField(ctx, "cacheControl")?.[field] ?? ctx?.[field];
9
9
  return typeof value === "number" ? value : void 0;
10
10
  }
11
+ /**
12
+ * When a `"use cache"` entry's generation started (`ctx.timestamp`), which dates
13
+ * the entry like Next.js does. Absent, malformed or future values fall back to `now`.
14
+ */
15
+ function readCacheTimestamp(ctx, now) {
16
+ const value = ctx?.timestamp;
17
+ return typeof value === "number" && Number.isFinite(value) && value > 0 && value <= now ? value : now;
18
+ }
11
19
  function readCacheControlRevalidateField(ctx) {
12
20
  const value = readRecordField(ctx, "cacheControl")?.revalidate ?? ctx?.revalidate;
13
21
  return typeof value === "number" || value === false ? value : void 0;
@@ -29,4 +37,4 @@ function resolveClientStaleTimeSeconds(cacheLife) {
29
37
  return isFiniteNonNegative(stale) ? stale : void 0;
30
38
  }
31
39
  //#endregion
32
- export { readCacheControlNumberField, readCacheControlRevalidateField, resolveClientStaleTimeSeconds };
40
+ export { readCacheControlNumberField, readCacheControlRevalidateField, readCacheTimestamp, resolveClientStaleTimeSeconds };
@@ -0,0 +1,33 @@
1
+ //#region src/utils/cache-life-profiles.d.ts
2
+ export type CacheLifeConfig = {
3
+ stale?: number;
4
+ revalidate?: number;
5
+ expire?: number;
6
+ };
7
+ /** Next.js's built-in profiles (`defaultConfig.cacheLife` in config-shared.ts). */
8
+ export declare const BUILT_IN_CACHE_LIFE_PROFILES: Readonly<Record<string, Readonly<CacheLifeConfig>>>;
9
+ /**
10
+ * Merge next.config `cacheLife` profiles over the built-ins, as Next.js does
11
+ * in `assignDefaultsAndValidate` (server/config.ts): a user profile replaces
12
+ * the built-in of the same name whole, and only `default` gets its missing
13
+ * fields filled: `stale` from `staleTimes.static`, `revalidate` from the
14
+ * built-in, `expire` from `expireTime`. That includes the built-in `default`,
15
+ * whose `stale` is unset in Next.js's defaults too. The other profiles keep
16
+ * their gaps, which the "use cache" store resolves from `default`.
17
+ *
18
+ * Next.js only schema-checks these profiles (fields must be numbers) and
19
+ * warns; `revalidate > expire` is checked for `cacheLife({...})` calls, not
20
+ * for config profiles.
21
+ */
22
+ export declare function resolveCacheLifeProfiles(userProfiles: unknown, defaults: {
23
+ expireTime: number;
24
+ staticStaleTime: number;
25
+ }, warn: (message: string) => void): Record<string, CacheLifeConfig>;
26
+ /** Serialize resolved profiles for the `__VINEXT_CACHE_LIFE_PROFILES` define. */
27
+ export declare function serializeCacheLifeProfiles(profiles: Record<string, CacheLifeConfig>): string;
28
+ /**
29
+ * Read the `__VINEXT_CACHE_LIFE_PROFILES` define. When absent, the profiles a
30
+ * next.config without `cacheLife` resolves to.
31
+ */
32
+ export declare function parseCacheLifeProfiles(serialized: string | undefined): Record<string, CacheLifeConfig>;
33
+ //#endregion