next 15.2.1-canary.1 → 15.2.1-canary.2

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.

Potentially problematic release.


This version of next might be problematic. Click here for more details.

Files changed (81) hide show
  1. package/dist/bin/next +1 -1
  2. package/dist/build/handle-externals.d.ts +2 -3
  3. package/dist/build/handle-externals.js +4 -4
  4. package/dist/build/handle-externals.js.map +1 -1
  5. package/dist/build/index.js +2 -2
  6. package/dist/build/swc/index.js +1 -1
  7. package/dist/build/webpack/plugins/build-manifest-plugin.js +3 -5
  8. package/dist/build/webpack/plugins/build-manifest-plugin.js.map +1 -1
  9. package/dist/build/webpack/plugins/css-minimizer-plugin.js +2 -2
  10. package/dist/build/webpack/plugins/css-minimizer-plugin.js.map +1 -1
  11. package/dist/build/webpack/plugins/minify-webpack-plugin/src/index.js +2 -2
  12. package/dist/build/webpack/plugins/minify-webpack-plugin/src/index.js.map +1 -1
  13. package/dist/build/webpack/plugins/next-trace-entrypoints-plugin.d.ts +1 -3
  14. package/dist/build/webpack/plugins/next-trace-entrypoints-plugin.js +5 -6
  15. package/dist/build/webpack/plugins/next-trace-entrypoints-plugin.js.map +1 -1
  16. package/dist/build/webpack/utils.d.ts +3 -1
  17. package/dist/build/webpack/utils.js +10 -0
  18. package/dist/build/webpack/utils.js.map +1 -1
  19. package/dist/build/webpack-config.js +2 -4
  20. package/dist/build/webpack-config.js.map +1 -1
  21. package/dist/client/app-bootstrap.js +1 -1
  22. package/dist/client/components/react-dev-overlay/server/shared.d.ts +0 -3
  23. package/dist/client/components/react-dev-overlay/server/shared.js.map +1 -1
  24. package/dist/client/components/react-dev-overlay/ui/styles/colors.js +1 -1
  25. package/dist/client/components/react-dev-overlay/ui/styles/colors.js.map +1 -1
  26. package/dist/client/components/react-dev-overlay/utils/stack-frame.d.ts +11 -3
  27. package/dist/client/components/react-dev-overlay/utils/stack-frame.js +2 -5
  28. package/dist/client/components/react-dev-overlay/utils/stack-frame.js.map +1 -1
  29. package/dist/client/components/router-reducer/reducers/navigate-reducer.js +29 -9
  30. package/dist/client/components/router-reducer/reducers/navigate-reducer.js.map +1 -1
  31. package/dist/client/components/segment-cache/navigation.d.ts +5 -1
  32. package/dist/client/components/segment-cache/navigation.js +28 -19
  33. package/dist/client/components/segment-cache/navigation.js.map +1 -1
  34. package/dist/client/index.js +1 -1
  35. package/dist/compiled/next-server/app-page-experimental.runtime.dev.js +2 -2
  36. package/dist/compiled/next-server/app-page-experimental.runtime.dev.js.map +1 -1
  37. package/dist/compiled/next-server/app-page.runtime.dev.js +2 -2
  38. package/dist/compiled/next-server/app-page.runtime.dev.js.map +1 -1
  39. package/dist/esm/build/handle-externals.js +4 -4
  40. package/dist/esm/build/handle-externals.js.map +1 -1
  41. package/dist/esm/build/index.js +2 -2
  42. package/dist/esm/build/swc/index.js +1 -1
  43. package/dist/esm/build/webpack/plugins/build-manifest-plugin.js +3 -5
  44. package/dist/esm/build/webpack/plugins/build-manifest-plugin.js.map +1 -1
  45. package/dist/esm/build/webpack/plugins/css-minimizer-plugin.js +2 -2
  46. package/dist/esm/build/webpack/plugins/css-minimizer-plugin.js.map +1 -1
  47. package/dist/esm/build/webpack/plugins/minify-webpack-plugin/src/index.js +2 -2
  48. package/dist/esm/build/webpack/plugins/minify-webpack-plugin/src/index.js.map +1 -1
  49. package/dist/esm/build/webpack/plugins/next-trace-entrypoints-plugin.js +5 -6
  50. package/dist/esm/build/webpack/plugins/next-trace-entrypoints-plugin.js.map +1 -1
  51. package/dist/esm/build/webpack/utils.js +6 -0
  52. package/dist/esm/build/webpack/utils.js.map +1 -1
  53. package/dist/esm/build/webpack-config.js +2 -4
  54. package/dist/esm/build/webpack-config.js.map +1 -1
  55. package/dist/esm/client/app-bootstrap.js +1 -1
  56. package/dist/esm/client/components/react-dev-overlay/server/shared.js.map +1 -1
  57. package/dist/esm/client/components/react-dev-overlay/ui/styles/colors.js +1 -1
  58. package/dist/esm/client/components/react-dev-overlay/ui/styles/colors.js.map +1 -1
  59. package/dist/esm/client/components/react-dev-overlay/utils/stack-frame.js +2 -5
  60. package/dist/esm/client/components/react-dev-overlay/utils/stack-frame.js.map +1 -1
  61. package/dist/esm/client/components/router-reducer/reducers/navigate-reducer.js +29 -9
  62. package/dist/esm/client/components/router-reducer/reducers/navigate-reducer.js.map +1 -1
  63. package/dist/esm/client/components/segment-cache/navigation.js +28 -19
  64. package/dist/esm/client/components/segment-cache/navigation.js.map +1 -1
  65. package/dist/esm/client/index.js +1 -1
  66. package/dist/esm/lib/server-external-packages.json +4 -0
  67. package/dist/esm/server/config.js +1 -1
  68. package/dist/esm/server/dev/hot-reloader-turbopack.js +1 -1
  69. package/dist/esm/server/dev/hot-reloader-webpack.js +1 -1
  70. package/dist/esm/server/lib/app-info-log.js +1 -1
  71. package/dist/esm/server/lib/start-server.js +1 -1
  72. package/dist/lib/server-external-packages.json +4 -0
  73. package/dist/server/config.js +1 -1
  74. package/dist/server/dev/hot-reloader-turbopack.js +1 -1
  75. package/dist/server/dev/hot-reloader-webpack.js +1 -1
  76. package/dist/server/lib/app-info-log.js +1 -1
  77. package/dist/server/lib/start-server.js +1 -1
  78. package/dist/telemetry/anonymous-meta.js +1 -1
  79. package/dist/telemetry/events/session-stopped.js +2 -2
  80. package/dist/telemetry/events/version.js +2 -2
  81. package/package.json +15 -15
@@ -1 +1 @@
1
- {"version":3,"sources":["../../../../src/client/components/segment-cache/navigation.ts"],"sourcesContent":["import type {\n CacheNodeSeedData,\n FlightRouterState,\n FlightSegmentPath,\n} from '../../../server/app-render/types'\nimport type {\n CacheNode,\n HeadData,\n LoadingModuleData,\n} from '../../../shared/lib/app-router-context.shared-runtime'\nimport type { NormalizedFlightData } from '../../flight-data-helpers'\nimport { fetchServerResponse } from '../router-reducer/fetch-server-response'\nimport {\n startPPRNavigation,\n listenForDynamicRequest,\n type Task as PPRNavigationTask,\n} from '../router-reducer/ppr-navigations'\nimport { createHrefFromUrl as createCanonicalUrl } from '../router-reducer/create-href-from-url'\nimport {\n EntryStatus,\n readRouteCacheEntry,\n readSegmentCacheEntry,\n waitForSegmentCacheEntry,\n type RouteTree,\n} from './cache'\nimport { createCacheKey } from './cache-key'\n\nexport const enum NavigationResultTag {\n MPA,\n Success,\n NoOp,\n Async,\n}\n\ntype MPANavigationResult = {\n tag: NavigationResultTag.MPA\n data: string\n}\n\ntype NoOpNavigationResult = {\n tag: NavigationResultTag.NoOp\n data: null\n}\n\ntype SuccessfulNavigationResult = {\n tag: NavigationResultTag.Success\n data: {\n flightRouterState: FlightRouterState\n cacheNode: CacheNode\n canonicalUrl: string\n scrollableSegments: Array<FlightSegmentPath>\n shouldScroll: boolean\n }\n}\n\ntype AsyncNavigationResult = {\n tag: NavigationResultTag.Async\n data: Promise<\n MPANavigationResult | NoOpNavigationResult | SuccessfulNavigationResult\n >\n}\n\nexport type NavigationResult =\n | MPANavigationResult\n | SuccessfulNavigationResult\n | NoOpNavigationResult\n | AsyncNavigationResult\n\nconst noOpNavigationResult: NoOpNavigationResult = {\n tag: NavigationResultTag.NoOp,\n data: null,\n}\n\n/**\n * Navigate to a new URL, using the Segment Cache to construct a response.\n *\n * To allow for synchronous navigations whenever possible, this is not an async\n * function. It returns a promise only if there's no matching prefetch in\n * the cache. Otherwise it returns an immediate result and uses Suspense/RSC to\n * stream in any missing data.\n */\nexport function navigate(\n url: URL,\n currentCacheNode: CacheNode,\n currentFlightRouterState: FlightRouterState,\n nextUrl: string | null,\n shouldScroll: boolean\n): NavigationResult {\n const now = Date.now()\n\n const cacheKey = createCacheKey(url.href, nextUrl)\n const route = readRouteCacheEntry(now, cacheKey)\n if (route !== null && route.status === EntryStatus.Fulfilled) {\n // We have a matching prefetch.\n const snapshot = readRenderSnapshotFromCache(now, route.tree)\n const prefetchFlightRouterState = snapshot.flightRouterState\n const prefetchSeedData = snapshot.seedData\n const prefetchHead = route.head\n const isPrefetchHeadPartial = route.isHeadPartial\n const canonicalUrl = route.canonicalUrl\n return navigateUsingPrefetchedRouteTree(\n url,\n nextUrl,\n currentCacheNode,\n currentFlightRouterState,\n prefetchFlightRouterState,\n prefetchSeedData,\n prefetchHead,\n isPrefetchHeadPartial,\n canonicalUrl,\n shouldScroll\n )\n }\n // There's no matching prefetch for this route in the cache.\n return {\n tag: NavigationResultTag.Async,\n data: navigateDynamicallyWithNoPrefetch(\n url,\n nextUrl,\n currentCacheNode,\n currentFlightRouterState,\n shouldScroll\n ),\n }\n}\n\nfunction navigateUsingPrefetchedRouteTree(\n url: URL,\n nextUrl: string | null,\n currentCacheNode: CacheNode,\n currentFlightRouterState: FlightRouterState,\n prefetchFlightRouterState: FlightRouterState,\n prefetchSeedData: CacheNodeSeedData | null,\n prefetchHead: HeadData | null,\n isPrefetchHeadPartial: boolean,\n canonicalUrl: string,\n shouldScroll: boolean\n): SuccessfulNavigationResult | NoOpNavigationResult | MPANavigationResult {\n // Recursively construct a prefetch tree by reading from the Segment Cache. To\n // maintain compatibility, we output the same data structures as the old\n // prefetching implementation: FlightRouterState and CacheNodeSeedData.\n // TODO: Eventually updateCacheNodeOnNavigation (or the equivalent) should\n // read from the Segment Cache directly. It's only structured this way for now\n // so we can share code with the old prefetching implementation.\n const scrollableSegments: Array<FlightSegmentPath> = []\n const task = startPPRNavigation(\n currentCacheNode,\n currentFlightRouterState,\n prefetchFlightRouterState,\n prefetchSeedData,\n prefetchHead,\n isPrefetchHeadPartial,\n scrollableSegments\n )\n if (task !== null) {\n const dynamicRequestTree = task.dynamicRequestTree\n if (dynamicRequestTree !== null) {\n const promiseForDynamicServerResponse = fetchServerResponse(url, {\n flightRouterState: dynamicRequestTree,\n nextUrl,\n })\n listenForDynamicRequest(task, promiseForDynamicServerResponse)\n } else {\n // The prefetched tree does not contain dynamic holes — it's\n // fully static. We can skip the dynamic request.\n }\n return navigationTaskToResult(\n task,\n currentCacheNode,\n canonicalUrl,\n scrollableSegments,\n shouldScroll\n )\n }\n // The server sent back an empty tree patch. There's nothing to update.\n return noOpNavigationResult\n}\n\nfunction navigationTaskToResult(\n task: PPRNavigationTask,\n currentCacheNode: CacheNode,\n canonicalUrl: string,\n scrollableSegments: Array<FlightSegmentPath>,\n shouldScroll: boolean\n): SuccessfulNavigationResult | MPANavigationResult {\n const flightRouterState = task.route\n if (flightRouterState === null) {\n // When no router state is provided, it signals that we should perform an\n // MPA navigation.\n return {\n tag: NavigationResultTag.MPA,\n data: canonicalUrl,\n }\n }\n const newCacheNode = task.node\n return {\n tag: NavigationResultTag.Success,\n data: {\n flightRouterState,\n cacheNode: newCacheNode !== null ? newCacheNode : currentCacheNode,\n canonicalUrl,\n scrollableSegments,\n shouldScroll,\n },\n }\n}\n\nfunction readRenderSnapshotFromCache(\n now: number,\n tree: RouteTree\n): { flightRouterState: FlightRouterState; seedData: CacheNodeSeedData } {\n let childRouterStates: { [parallelRouteKey: string]: FlightRouterState } = {}\n let childSeedDatas: {\n [parallelRouteKey: string]: CacheNodeSeedData | null\n } = {}\n const slots = tree.slots\n if (slots !== null) {\n for (const parallelRouteKey in slots) {\n const childTree = slots[parallelRouteKey]\n const childResult = readRenderSnapshotFromCache(now, childTree)\n childRouterStates[parallelRouteKey] = childResult.flightRouterState\n childSeedDatas[parallelRouteKey] = childResult.seedData\n }\n }\n\n let rsc: React.ReactNode | null = null\n let loading: LoadingModuleData | Promise<LoadingModuleData> = null\n let isPartial: boolean = true\n\n const segmentEntry = readSegmentCacheEntry(now, tree.key)\n if (segmentEntry !== null) {\n switch (segmentEntry.status) {\n case EntryStatus.Fulfilled: {\n // Happy path: a cache hit\n rsc = segmentEntry.rsc\n loading = segmentEntry.loading\n isPartial = segmentEntry.isPartial\n break\n }\n case EntryStatus.Pending: {\n // We haven't received data for this segment yet, but there's already\n // an in-progress request. Since it's extremely likely to arrive\n // before the dynamic data response, we might as well use it.\n const promiseForFulfilledEntry = waitForSegmentCacheEntry(segmentEntry)\n rsc = promiseForFulfilledEntry.then((entry) =>\n entry !== null ? entry.rsc : null\n )\n loading = promiseForFulfilledEntry.then((entry) =>\n entry !== null ? entry.loading : null\n )\n // Since we don't know yet whether the segment is partial or fully\n // static, we must assume it's partial; we can't skip the\n // dynamic request.\n isPartial = true\n break\n }\n case EntryStatus.Empty:\n case EntryStatus.Rejected:\n break\n default:\n segmentEntry satisfies never\n }\n }\n\n return {\n flightRouterState: [\n tree.segment,\n childRouterStates,\n null,\n null,\n tree.isRootLayout,\n ],\n seedData: [tree.segment, rsc, childSeedDatas, loading, isPartial],\n }\n}\n\nasync function navigateDynamicallyWithNoPrefetch(\n url: URL,\n nextUrl: string | null,\n currentCacheNode: CacheNode,\n currentFlightRouterState: FlightRouterState,\n shouldScroll: boolean\n): Promise<\n MPANavigationResult | SuccessfulNavigationResult | NoOpNavigationResult\n> {\n // Runs when a navigation happens but there's no cached prefetch we can use.\n // Don't bother to wait for a prefetch response; go straight to a full\n // navigation that contains both static and dynamic data in a single stream.\n // (This is unlike the old navigation implementation, which instead blocks\n // the dynamic request until a prefetch request is received.)\n //\n // To avoid duplication of logic, we're going to pretend that the tree\n // returned by the dynamic request is, in fact, a prefetch tree. Then we can\n // use the same server response to write the actual data into the CacheNode\n // tree. So it's the same flow as the \"happy path\" (prefetch, then\n // navigation), except we use a single server response for both stages.\n\n const promiseForDynamicServerResponse = fetchServerResponse(url, {\n flightRouterState: currentFlightRouterState,\n nextUrl,\n })\n const { flightData, canonicalUrl: canonicalUrlOverride } =\n await promiseForDynamicServerResponse\n\n // TODO: Detect if the only thing that changed was the hash, like we do in\n // in navigateReducer\n\n if (typeof flightData === 'string') {\n // This is an MPA navigation.\n const newUrl = flightData\n return {\n tag: NavigationResultTag.MPA,\n data: newUrl,\n }\n }\n\n // Since the response format of dynamic requests and prefetches is slightly\n // different, we'll need to massage the data a bit. Create FlightRouterState\n // tree that simulates what we'd receive as the result of a prefetch.\n const prefetchFlightRouterState = simulatePrefetchTreeUsingDynamicTreePatch(\n currentFlightRouterState,\n flightData\n )\n\n // In our simulated prefetch payload, we pretend that there's no seed data\n // nor a prefetch head.\n const prefetchSeedData = null\n const prefetchHead = null\n const isPrefetchHeadPartial = true\n\n const canonicalUrl = createCanonicalUrl(\n canonicalUrlOverride ? canonicalUrlOverride : url\n )\n\n // Now we proceed exactly as we would for normal navigation.\n const scrollableSegments: Array<FlightSegmentPath> = []\n const task = startPPRNavigation(\n currentCacheNode,\n currentFlightRouterState,\n prefetchFlightRouterState,\n prefetchSeedData,\n prefetchHead,\n isPrefetchHeadPartial,\n scrollableSegments\n )\n if (task !== null) {\n // In this case, we've already sent the dynamic request, so we don't\n // actually use the request tree created by `startPPRNavigation`,\n // except to check if it contains dynamic holes.\n //\n // This is almost always true, but it could be false if all the segment data\n // was present in the cache, but the route tree was not. E.g. navigating\n // to a URL that was not prefetched but rewrites to a different URL\n // that was.\n const hasDynamicHoles = task.dynamicRequestTree !== null\n if (hasDynamicHoles) {\n listenForDynamicRequest(task, promiseForDynamicServerResponse)\n } else {\n // The prefetched tree does not contain dynamic holes — it's\n // fully static. We don't need to process the server response further.\n }\n return navigationTaskToResult(\n task,\n currentCacheNode,\n canonicalUrl,\n scrollableSegments,\n shouldScroll\n )\n }\n // The server sent back an empty tree patch. There's nothing to update.\n return noOpNavigationResult\n}\n\nfunction simulatePrefetchTreeUsingDynamicTreePatch(\n currentTree: FlightRouterState,\n flightData: Array<NormalizedFlightData>\n): FlightRouterState {\n // Takes the current FlightRouterState and applies the router state patch\n // received from the server, to create a full FlightRouterState tree that we\n // can pretend was returned by a prefetch.\n //\n // (It sounds similar to what applyRouterStatePatch does, but it doesn't need\n // to handle stuff like interception routes or diffing since that will be\n // handled later.)\n let baseTree = currentTree\n for (const { segmentPath, tree: treePatch } of flightData) {\n // If the server sends us multiple tree patches, we only need to clone the\n // base tree when applying the first patch. After the first patch, we can\n // apply the remaining patches in place without copying.\n const canMutateInPlace = baseTree !== currentTree\n baseTree = simulatePrefetchTreeUsingDynamicTreePatchImpl(\n baseTree,\n treePatch,\n segmentPath,\n canMutateInPlace,\n 0\n )\n }\n\n return baseTree\n}\n\nfunction simulatePrefetchTreeUsingDynamicTreePatchImpl(\n baseRouterState: FlightRouterState,\n patch: FlightRouterState,\n segmentPath: FlightSegmentPath,\n canMutateInPlace: boolean,\n index: number\n) {\n if (index === segmentPath.length) {\n // We reached the part of the tree that we need to patch.\n return patch\n }\n\n // segmentPath represents the parent path of subtree. It's a repeating\n // pattern of parallel route key and segment:\n //\n // [string, Segment, string, Segment, string, Segment, ...]\n //\n // This path tells us which part of the base tree to apply the tree patch.\n //\n // NOTE: In the case of a fully dynamic request with no prefetch, we receive\n // the FlightRouterState patch in the same request as the dynamic data.\n // Therefore we don't need to worry about diffing the segment values; we can\n // assume the server sent us a correct result.\n const updatedParallelRouteKey: string = segmentPath[index]\n // const segment: Segment = segmentPath[index + 1] <-- Not used, see note above\n\n const baseChildren = baseRouterState[1]\n const newChildren: { [parallelRouteKey: string]: FlightRouterState } = {}\n for (const parallelRouteKey in baseChildren) {\n if (parallelRouteKey === updatedParallelRouteKey) {\n const childBaseRouterState = baseChildren[parallelRouteKey]\n newChildren[parallelRouteKey] =\n simulatePrefetchTreeUsingDynamicTreePatchImpl(\n childBaseRouterState,\n patch,\n segmentPath,\n canMutateInPlace,\n // Advance the index by two and keep cloning until we reach\n // the end of the segment path.\n index + 2\n )\n } else {\n // This child is not being patched. Copy it over as-is.\n newChildren[parallelRouteKey] = baseChildren[parallelRouteKey]\n }\n }\n\n if (canMutateInPlace) {\n // We can mutate the base tree in place, because the base tree is already\n // a clone.\n baseRouterState[1] = newChildren\n return baseRouterState\n }\n\n // Clone all the fields except the children.\n //\n // Based on equivalent logic in apply-router-state-patch-to-tree, but should\n // confirm whether we need to copy all of these fields. Not sure the server\n // ever sends, e.g. the refetch marker.\n const clone: FlightRouterState = [baseRouterState[0], newChildren]\n if (2 in baseRouterState) {\n clone[2] = baseRouterState[2]\n }\n if (3 in baseRouterState) {\n clone[3] = baseRouterState[3]\n }\n if (4 in baseRouterState) {\n clone[4] = baseRouterState[4]\n }\n return clone\n}\n"],"names":["NavigationResultTag","navigate","noOpNavigationResult","tag","data","url","currentCacheNode","currentFlightRouterState","nextUrl","shouldScroll","now","Date","cacheKey","createCacheKey","href","route","readRouteCacheEntry","status","EntryStatus","Fulfilled","snapshot","readRenderSnapshotFromCache","tree","prefetchFlightRouterState","flightRouterState","prefetchSeedData","seedData","prefetchHead","head","isPrefetchHeadPartial","isHeadPartial","canonicalUrl","navigateUsingPrefetchedRouteTree","navigateDynamicallyWithNoPrefetch","scrollableSegments","task","startPPRNavigation","dynamicRequestTree","promiseForDynamicServerResponse","fetchServerResponse","listenForDynamicRequest","navigationTaskToResult","newCacheNode","node","cacheNode","childRouterStates","childSeedDatas","slots","parallelRouteKey","childTree","childResult","rsc","loading","isPartial","segmentEntry","readSegmentCacheEntry","key","Pending","promiseForFulfilledEntry","waitForSegmentCacheEntry","then","entry","Empty","Rejected","segment","isRootLayout","flightData","canonicalUrlOverride","newUrl","simulatePrefetchTreeUsingDynamicTreePatch","createCanonicalUrl","hasDynamicHoles","currentTree","baseTree","segmentPath","treePatch","canMutateInPlace","simulatePrefetchTreeUsingDynamicTreePatchImpl","baseRouterState","patch","index","length","updatedParallelRouteKey","baseChildren","newChildren","childBaseRouterState","clone"],"mappings":"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"}
1
+ {"version":3,"sources":["../../../../src/client/components/segment-cache/navigation.ts"],"sourcesContent":["import type {\n CacheNodeSeedData,\n FlightRouterState,\n FlightSegmentPath,\n} from '../../../server/app-render/types'\nimport type {\n CacheNode,\n HeadData,\n LoadingModuleData,\n} from '../../../shared/lib/app-router-context.shared-runtime'\nimport type { NormalizedFlightData } from '../../flight-data-helpers'\nimport { fetchServerResponse } from '../router-reducer/fetch-server-response'\nimport {\n startPPRNavigation,\n listenForDynamicRequest,\n type Task as PPRNavigationTask,\n} from '../router-reducer/ppr-navigations'\nimport { createHrefFromUrl as createCanonicalUrl } from '../router-reducer/create-href-from-url'\nimport {\n EntryStatus,\n readRouteCacheEntry,\n readSegmentCacheEntry,\n waitForSegmentCacheEntry,\n type RouteTree,\n} from './cache'\nimport { createCacheKey } from './cache-key'\n\nexport const enum NavigationResultTag {\n MPA,\n Success,\n NoOp,\n Async,\n}\n\ntype MPANavigationResult = {\n tag: NavigationResultTag.MPA\n data: string\n}\n\ntype NoOpNavigationResult = {\n tag: NavigationResultTag.NoOp\n data: {\n canonicalUrl: string\n shouldScroll: boolean\n }\n}\n\ntype SuccessfulNavigationResult = {\n tag: NavigationResultTag.Success\n data: {\n flightRouterState: FlightRouterState\n cacheNode: CacheNode\n canonicalUrl: string\n scrollableSegments: Array<FlightSegmentPath>\n shouldScroll: boolean\n hash: string\n }\n}\n\ntype AsyncNavigationResult = {\n tag: NavigationResultTag.Async\n data: Promise<\n MPANavigationResult | NoOpNavigationResult | SuccessfulNavigationResult\n >\n}\n\nexport type NavigationResult =\n | MPANavigationResult\n | SuccessfulNavigationResult\n | NoOpNavigationResult\n | AsyncNavigationResult\n\n/**\n * Navigate to a new URL, using the Segment Cache to construct a response.\n *\n * To allow for synchronous navigations whenever possible, this is not an async\n * function. It returns a promise only if there's no matching prefetch in\n * the cache. Otherwise it returns an immediate result and uses Suspense/RSC to\n * stream in any missing data.\n */\nexport function navigate(\n url: URL,\n currentCacheNode: CacheNode,\n currentFlightRouterState: FlightRouterState,\n nextUrl: string | null,\n shouldScroll: boolean\n): NavigationResult {\n const now = Date.now()\n\n const cacheKey = createCacheKey(url.href, nextUrl)\n const route = readRouteCacheEntry(now, cacheKey)\n if (route !== null && route.status === EntryStatus.Fulfilled) {\n // We have a matching prefetch.\n const snapshot = readRenderSnapshotFromCache(now, route.tree)\n const prefetchFlightRouterState = snapshot.flightRouterState\n const prefetchSeedData = snapshot.seedData\n const prefetchHead = route.head\n const isPrefetchHeadPartial = route.isHeadPartial\n const newCanonicalUrl = route.canonicalUrl\n return navigateUsingPrefetchedRouteTree(\n url,\n nextUrl,\n currentCacheNode,\n currentFlightRouterState,\n prefetchFlightRouterState,\n prefetchSeedData,\n prefetchHead,\n isPrefetchHeadPartial,\n newCanonicalUrl,\n shouldScroll,\n url.hash\n )\n }\n // There's no matching prefetch for this route in the cache.\n return {\n tag: NavigationResultTag.Async,\n data: navigateDynamicallyWithNoPrefetch(\n url,\n nextUrl,\n currentCacheNode,\n currentFlightRouterState,\n shouldScroll,\n url.hash\n ),\n }\n}\n\nfunction navigateUsingPrefetchedRouteTree(\n url: URL,\n nextUrl: string | null,\n currentCacheNode: CacheNode,\n currentFlightRouterState: FlightRouterState,\n prefetchFlightRouterState: FlightRouterState,\n prefetchSeedData: CacheNodeSeedData | null,\n prefetchHead: HeadData | null,\n isPrefetchHeadPartial: boolean,\n canonicalUrl: string,\n shouldScroll: boolean,\n hash: string\n): SuccessfulNavigationResult | NoOpNavigationResult | MPANavigationResult {\n // Recursively construct a prefetch tree by reading from the Segment Cache. To\n // maintain compatibility, we output the same data structures as the old\n // prefetching implementation: FlightRouterState and CacheNodeSeedData.\n // TODO: Eventually updateCacheNodeOnNavigation (or the equivalent) should\n // read from the Segment Cache directly. It's only structured this way for now\n // so we can share code with the old prefetching implementation.\n const scrollableSegments: Array<FlightSegmentPath> = []\n const task = startPPRNavigation(\n currentCacheNode,\n currentFlightRouterState,\n prefetchFlightRouterState,\n prefetchSeedData,\n prefetchHead,\n isPrefetchHeadPartial,\n scrollableSegments\n )\n if (task !== null) {\n const dynamicRequestTree = task.dynamicRequestTree\n if (dynamicRequestTree !== null) {\n const promiseForDynamicServerResponse = fetchServerResponse(url, {\n flightRouterState: dynamicRequestTree,\n nextUrl,\n })\n listenForDynamicRequest(task, promiseForDynamicServerResponse)\n } else {\n // The prefetched tree does not contain dynamic holes — it's\n // fully static. We can skip the dynamic request.\n }\n return navigationTaskToResult(\n task,\n currentCacheNode,\n canonicalUrl,\n scrollableSegments,\n shouldScroll,\n hash\n )\n }\n // The server sent back an empty tree patch. There's nothing to update, except\n // possibly the URL.\n return {\n tag: NavigationResultTag.NoOp,\n data: {\n canonicalUrl,\n shouldScroll,\n },\n }\n}\n\nfunction navigationTaskToResult(\n task: PPRNavigationTask,\n currentCacheNode: CacheNode,\n canonicalUrl: string,\n scrollableSegments: Array<FlightSegmentPath>,\n shouldScroll: boolean,\n hash: string\n): SuccessfulNavigationResult | MPANavigationResult {\n const flightRouterState = task.route\n if (flightRouterState === null) {\n // When no router state is provided, it signals that we should perform an\n // MPA navigation.\n return {\n tag: NavigationResultTag.MPA,\n data: canonicalUrl,\n }\n }\n const newCacheNode = task.node\n return {\n tag: NavigationResultTag.Success,\n data: {\n flightRouterState,\n cacheNode: newCacheNode !== null ? newCacheNode : currentCacheNode,\n canonicalUrl,\n scrollableSegments,\n shouldScroll,\n hash,\n },\n }\n}\n\nfunction readRenderSnapshotFromCache(\n now: number,\n tree: RouteTree\n): { flightRouterState: FlightRouterState; seedData: CacheNodeSeedData } {\n let childRouterStates: { [parallelRouteKey: string]: FlightRouterState } = {}\n let childSeedDatas: {\n [parallelRouteKey: string]: CacheNodeSeedData | null\n } = {}\n const slots = tree.slots\n if (slots !== null) {\n for (const parallelRouteKey in slots) {\n const childTree = slots[parallelRouteKey]\n const childResult = readRenderSnapshotFromCache(now, childTree)\n childRouterStates[parallelRouteKey] = childResult.flightRouterState\n childSeedDatas[parallelRouteKey] = childResult.seedData\n }\n }\n\n let rsc: React.ReactNode | null = null\n let loading: LoadingModuleData | Promise<LoadingModuleData> = null\n let isPartial: boolean = true\n\n const segmentEntry = readSegmentCacheEntry(now, tree.key)\n if (segmentEntry !== null) {\n switch (segmentEntry.status) {\n case EntryStatus.Fulfilled: {\n // Happy path: a cache hit\n rsc = segmentEntry.rsc\n loading = segmentEntry.loading\n isPartial = segmentEntry.isPartial\n break\n }\n case EntryStatus.Pending: {\n // We haven't received data for this segment yet, but there's already\n // an in-progress request. Since it's extremely likely to arrive\n // before the dynamic data response, we might as well use it.\n const promiseForFulfilledEntry = waitForSegmentCacheEntry(segmentEntry)\n rsc = promiseForFulfilledEntry.then((entry) =>\n entry !== null ? entry.rsc : null\n )\n loading = promiseForFulfilledEntry.then((entry) =>\n entry !== null ? entry.loading : null\n )\n // Since we don't know yet whether the segment is partial or fully\n // static, we must assume it's partial; we can't skip the\n // dynamic request.\n isPartial = true\n break\n }\n case EntryStatus.Empty:\n case EntryStatus.Rejected:\n break\n default:\n segmentEntry satisfies never\n }\n }\n\n return {\n flightRouterState: [\n tree.segment,\n childRouterStates,\n null,\n null,\n tree.isRootLayout,\n ],\n seedData: [tree.segment, rsc, childSeedDatas, loading, isPartial],\n }\n}\n\nasync function navigateDynamicallyWithNoPrefetch(\n url: URL,\n nextUrl: string | null,\n currentCacheNode: CacheNode,\n currentFlightRouterState: FlightRouterState,\n shouldScroll: boolean,\n hash: string\n): Promise<\n MPANavigationResult | SuccessfulNavigationResult | NoOpNavigationResult\n> {\n // Runs when a navigation happens but there's no cached prefetch we can use.\n // Don't bother to wait for a prefetch response; go straight to a full\n // navigation that contains both static and dynamic data in a single stream.\n // (This is unlike the old navigation implementation, which instead blocks\n // the dynamic request until a prefetch request is received.)\n //\n // To avoid duplication of logic, we're going to pretend that the tree\n // returned by the dynamic request is, in fact, a prefetch tree. Then we can\n // use the same server response to write the actual data into the CacheNode\n // tree. So it's the same flow as the \"happy path\" (prefetch, then\n // navigation), except we use a single server response for both stages.\n\n const promiseForDynamicServerResponse = fetchServerResponse(url, {\n flightRouterState: currentFlightRouterState,\n nextUrl,\n })\n const { flightData, canonicalUrl: canonicalUrlOverride } =\n await promiseForDynamicServerResponse\n\n if (typeof flightData === 'string') {\n // This is an MPA navigation.\n const newUrl = flightData\n return {\n tag: NavigationResultTag.MPA,\n data: newUrl,\n }\n }\n\n // Since the response format of dynamic requests and prefetches is slightly\n // different, we'll need to massage the data a bit. Create FlightRouterState\n // tree that simulates what we'd receive as the result of a prefetch.\n const prefetchFlightRouterState = simulatePrefetchTreeUsingDynamicTreePatch(\n currentFlightRouterState,\n flightData\n )\n\n // In our simulated prefetch payload, we pretend that there's no seed data\n // nor a prefetch head.\n const prefetchSeedData = null\n const prefetchHead = null\n const isPrefetchHeadPartial = true\n\n const canonicalUrl = createCanonicalUrl(\n canonicalUrlOverride ? canonicalUrlOverride : url\n )\n\n // Now we proceed exactly as we would for normal navigation.\n const scrollableSegments: Array<FlightSegmentPath> = []\n const task = startPPRNavigation(\n currentCacheNode,\n currentFlightRouterState,\n prefetchFlightRouterState,\n prefetchSeedData,\n prefetchHead,\n isPrefetchHeadPartial,\n scrollableSegments\n )\n if (task !== null) {\n // In this case, we've already sent the dynamic request, so we don't\n // actually use the request tree created by `startPPRNavigation`,\n // except to check if it contains dynamic holes.\n //\n // This is almost always true, but it could be false if all the segment data\n // was present in the cache, but the route tree was not. E.g. navigating\n // to a URL that was not prefetched but rewrites to a different URL\n // that was.\n const hasDynamicHoles = task.dynamicRequestTree !== null\n if (hasDynamicHoles) {\n listenForDynamicRequest(task, promiseForDynamicServerResponse)\n } else {\n // The prefetched tree does not contain dynamic holes — it's\n // fully static. We don't need to process the server response further.\n }\n return navigationTaskToResult(\n task,\n currentCacheNode,\n canonicalUrl,\n scrollableSegments,\n shouldScroll,\n hash\n )\n }\n // The server sent back an empty tree patch. There's nothing to update, except\n // possibly the URL.\n return {\n tag: NavigationResultTag.NoOp,\n data: {\n canonicalUrl,\n shouldScroll,\n },\n }\n}\n\nfunction simulatePrefetchTreeUsingDynamicTreePatch(\n currentTree: FlightRouterState,\n flightData: Array<NormalizedFlightData>\n): FlightRouterState {\n // Takes the current FlightRouterState and applies the router state patch\n // received from the server, to create a full FlightRouterState tree that we\n // can pretend was returned by a prefetch.\n //\n // (It sounds similar to what applyRouterStatePatch does, but it doesn't need\n // to handle stuff like interception routes or diffing since that will be\n // handled later.)\n let baseTree = currentTree\n for (const { segmentPath, tree: treePatch } of flightData) {\n // If the server sends us multiple tree patches, we only need to clone the\n // base tree when applying the first patch. After the first patch, we can\n // apply the remaining patches in place without copying.\n const canMutateInPlace = baseTree !== currentTree\n baseTree = simulatePrefetchTreeUsingDynamicTreePatchImpl(\n baseTree,\n treePatch,\n segmentPath,\n canMutateInPlace,\n 0\n )\n }\n\n return baseTree\n}\n\nfunction simulatePrefetchTreeUsingDynamicTreePatchImpl(\n baseRouterState: FlightRouterState,\n patch: FlightRouterState,\n segmentPath: FlightSegmentPath,\n canMutateInPlace: boolean,\n index: number\n) {\n if (index === segmentPath.length) {\n // We reached the part of the tree that we need to patch.\n return patch\n }\n\n // segmentPath represents the parent path of subtree. It's a repeating\n // pattern of parallel route key and segment:\n //\n // [string, Segment, string, Segment, string, Segment, ...]\n //\n // This path tells us which part of the base tree to apply the tree patch.\n //\n // NOTE: In the case of a fully dynamic request with no prefetch, we receive\n // the FlightRouterState patch in the same request as the dynamic data.\n // Therefore we don't need to worry about diffing the segment values; we can\n // assume the server sent us a correct result.\n const updatedParallelRouteKey: string = segmentPath[index]\n // const segment: Segment = segmentPath[index + 1] <-- Not used, see note above\n\n const baseChildren = baseRouterState[1]\n const newChildren: { [parallelRouteKey: string]: FlightRouterState } = {}\n for (const parallelRouteKey in baseChildren) {\n if (parallelRouteKey === updatedParallelRouteKey) {\n const childBaseRouterState = baseChildren[parallelRouteKey]\n newChildren[parallelRouteKey] =\n simulatePrefetchTreeUsingDynamicTreePatchImpl(\n childBaseRouterState,\n patch,\n segmentPath,\n canMutateInPlace,\n // Advance the index by two and keep cloning until we reach\n // the end of the segment path.\n index + 2\n )\n } else {\n // This child is not being patched. Copy it over as-is.\n newChildren[parallelRouteKey] = baseChildren[parallelRouteKey]\n }\n }\n\n if (canMutateInPlace) {\n // We can mutate the base tree in place, because the base tree is already\n // a clone.\n baseRouterState[1] = newChildren\n return baseRouterState\n }\n\n // Clone all the fields except the children.\n //\n // Based on equivalent logic in apply-router-state-patch-to-tree, but should\n // confirm whether we need to copy all of these fields. Not sure the server\n // ever sends, e.g. the refetch marker.\n const clone: FlightRouterState = [baseRouterState[0], newChildren]\n if (2 in baseRouterState) {\n clone[2] = baseRouterState[2]\n }\n if (3 in baseRouterState) {\n clone[3] = baseRouterState[3]\n }\n if (4 in baseRouterState) {\n clone[4] = baseRouterState[4]\n }\n return clone\n}\n"],"names":["NavigationResultTag","navigate","url","currentCacheNode","currentFlightRouterState","nextUrl","shouldScroll","now","Date","cacheKey","createCacheKey","href","route","readRouteCacheEntry","status","EntryStatus","Fulfilled","snapshot","readRenderSnapshotFromCache","tree","prefetchFlightRouterState","flightRouterState","prefetchSeedData","seedData","prefetchHead","head","isPrefetchHeadPartial","isHeadPartial","newCanonicalUrl","canonicalUrl","navigateUsingPrefetchedRouteTree","hash","tag","data","navigateDynamicallyWithNoPrefetch","scrollableSegments","task","startPPRNavigation","dynamicRequestTree","promiseForDynamicServerResponse","fetchServerResponse","listenForDynamicRequest","navigationTaskToResult","newCacheNode","node","cacheNode","childRouterStates","childSeedDatas","slots","parallelRouteKey","childTree","childResult","rsc","loading","isPartial","segmentEntry","readSegmentCacheEntry","key","Pending","promiseForFulfilledEntry","waitForSegmentCacheEntry","then","entry","Empty","Rejected","segment","isRootLayout","flightData","canonicalUrlOverride","newUrl","simulatePrefetchTreeUsingDynamicTreePatch","createCanonicalUrl","hasDynamicHoles","currentTree","baseTree","segmentPath","treePatch","canMutateInPlace","simulatePrefetchTreeUsingDynamicTreePatchImpl","baseRouterState","patch","index","length","updatedParallelRouteKey","baseChildren","newChildren","childBaseRouterState","clone"],"mappings":"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"}
@@ -61,7 +61,7 @@ const _hooksclientcontextsharedruntime = require("../shared/lib/hooks-client-con
61
61
  const _onrecoverableerror = require("./react-client-callbacks/on-recoverable-error");
62
62
  const _tracer = /*#__PURE__*/ _interop_require_default._(require("./tracing/tracer"));
63
63
  const _isnextroutererror = require("./components/is-next-router-error");
64
- const version = "15.2.1-canary.1";
64
+ const version = "15.2.1-canary.2";
65
65
  let router;
66
66
  const emitter = (0, _mitt.default)();
67
67
  const looseToArray = (input)=>[].slice.call(input);