@@ -88,6 +88,8 @@ export function startPPRNavigation(
8888 oldRouterState : FlightRouterState ,
8989 newRouterState : FlightRouterState ,
9090 shouldRefreshDynamicData : boolean ,
91+ seedData : CacheNodeSeedData | null ,
92+ seedHead : HeadData | null ,
9193 prefetchData : CacheNodeSeedData | null ,
9294 prefetchHead : HeadData | null ,
9395 isPrefetchHeadPartial : boolean ,
@@ -106,6 +108,8 @@ export function startPPRNavigation(
106108 newRouterState ,
107109 shouldRefreshDynamicData ,
108110 didFindRootLayout ,
111+ seedData ,
112+ seedHead ,
109113 prefetchData ,
110114 prefetchHead ,
111115 isPrefetchHeadPartial ,
@@ -125,6 +129,8 @@ function updateCacheNodeOnNavigation(
125129 newRouterState : FlightRouterState ,
126130 shouldRefreshDynamicData : boolean ,
127131 didFindRootLayout : boolean ,
132+ seedData : CacheNodeSeedData | null ,
133+ seedHead : HeadData | null ,
128134 prefetchData : CacheNodeSeedData | null ,
129135 prefetchHead : HeadData | null ,
130136 isPrefetchHeadPartial : boolean ,
@@ -146,6 +152,8 @@ function updateCacheNodeOnNavigation(
146152
147153 // Since we're switching to a different route tree, these are no
148154 // longer valid, because they correspond to the outer tree.
155+ seedData = null
156+ seedHead = null
149157 prefetchData = null
150158 prefetchHead = null
151159 isPrefetchHeadPartial = false
@@ -183,6 +191,8 @@ function updateCacheNodeOnNavigation(
183191 newRouterState ,
184192 oldCacheNode ,
185193 shouldRefreshDynamicData ,
194+ seedData ,
195+ seedHead ,
186196 prefetchData ,
187197 prefetchHead ,
188198 isPrefetchHeadPartial ,
@@ -194,6 +204,7 @@ function updateCacheNodeOnNavigation(
194204
195205 const newRouterStateChildren = newRouterState [ 1 ]
196206 const oldRouterStateChildren = oldRouterState [ 1 ]
207+ const seedDataChildren = seedData !== null ? seedData [ 1 ] : null
197208 const prefetchDataChildren = prefetchData !== null ? prefetchData [ 1 ] : null
198209
199210 // We're currently traversing the part of the tree that was also part of
@@ -242,6 +253,28 @@ function updateCacheNodeOnNavigation(
242253 // Reuse the existing CacheNode
243254 newCacheNode = reuseDynamicCacheNode ( oldCacheNode , newParallelRoutes )
244255 needsDynamicRequest = false
256+ } else if ( seedData !== null ) {
257+ // If this navigation was the result of an action, then check if the
258+ // server sent back data in the action response. We should favor using
259+ // that, rather than performing a separate request. This is both better
260+ // for performance and it's more likely to be consistent with any
261+ // writes that were just performed by the action, compared to a
262+ // separate request.
263+ const seedRsc = seedData [ 0 ]
264+ const seedLoading = seedData [ 2 ]
265+ const isSeedRscPartial = false
266+ const isSeedHeadPartial = seedHead !== null
267+ newCacheNode = readCacheNodeFromSeedData (
268+ seedRsc ,
269+ seedLoading ,
270+ isSeedRscPartial ,
271+ seedHead ,
272+ isSeedHeadPartial ,
273+ isLeafSegment ,
274+ newParallelRoutes ,
275+ navigatedAt
276+ )
277+ needsDynamicRequest = isLeafSegment && isSeedHeadPartial
245278 } else if ( prefetchData !== null ) {
246279 // Consult the prefetch cache.
247280 const prefetchRsc = prefetchData [ 0 ]
@@ -335,6 +368,8 @@ function updateCacheNodeOnNavigation(
335368 oldParallelRoutes !== undefined
336369 ? oldParallelRoutes . get ( parallelRouteKey )
337370 : undefined
371+ const seedDataChild : CacheNodeSeedData | void | null =
372+ seedDataChildren !== null ? seedDataChildren [ parallelRouteKey ] : null
338373 const prefetchDataChild : CacheNodeSeedData | void | null =
339374 prefetchDataChildren !== null
340375 ? prefetchDataChildren [ parallelRouteKey ]
@@ -360,6 +395,8 @@ function updateCacheNodeOnNavigation(
360395 newRouterStateChild ,
361396 shouldRefreshDynamicData ,
362397 childDidFindRootLayout ,
398+ seedDataChild ?? null ,
399+ seedHead ,
363400 prefetchDataChild ?? null ,
364401 prefetchHead ,
365402 isPrefetchHeadPartial ,
@@ -384,7 +421,9 @@ function updateCacheNodeOnNavigation(
384421 taskChildren . set ( parallelRouteKey , taskChild )
385422 const newCacheNodeChild = taskChild . node
386423 if ( newCacheNodeChild !== null ) {
387- const newSegmentMapChild : ChildSegmentMap = new Map ( oldSegmentMapChild )
424+ const newSegmentMapChild : ChildSegmentMap = new Map (
425+ shouldRefreshDynamicData ? undefined : oldSegmentMapChild
426+ )
388427 newSegmentMapChild . set ( newSegmentKeyChild , newCacheNodeChild )
389428 newParallelRoutes . set ( parallelRouteKey , newSegmentMapChild )
390429 }
@@ -434,6 +473,8 @@ function createCacheNodeOnNavigation(
434473 newRouterState : FlightRouterState ,
435474 oldCacheNode : CacheNode | void ,
436475 shouldRefreshDynamicData : boolean ,
476+ seedData : CacheNodeSeedData | null ,
477+ seedHead : HeadData | null ,
437478 prefetchData : CacheNodeSeedData | null ,
438479 prefetchHead : HeadData | null ,
439480 isPrefetchHeadPartial : boolean ,
@@ -452,6 +493,7 @@ function createCacheNodeOnNavigation(
452493 // diverges, which is why we keep them separate.
453494 const newRouterStateChildren = newRouterState [ 1 ]
454495 const prefetchDataChildren = prefetchData !== null ? prefetchData [ 1 ] : null
496+ const seedDataChildren = seedData !== null ? seedData [ 1 ] : null
455497 const oldParallelRoutes =
456498 oldCacheNode !== undefined ? oldCacheNode . parallelRoutes : undefined
457499 const newParallelRoutes = new Map (
@@ -489,6 +531,28 @@ function createCacheNodeOnNavigation(
489531 // Reuse the existing CacheNode
490532 newCacheNode = reuseDynamicCacheNode ( oldCacheNode , newParallelRoutes )
491533 needsDynamicRequest = false
534+ } else if ( seedData !== null ) {
535+ // If this navigation was the result of an action, then check if the
536+ // server sent back data in the action response. We should favor using
537+ // that, rather than performing a separate request. This is both better
538+ // for performance and it's more likely to be consistent with any
539+ // writes that were just performed by the action, compared to a
540+ // separate request.
541+ const seedRsc = seedData [ 0 ]
542+ const seedLoading = seedData [ 2 ]
543+ const isSeedRscPartial = false
544+ const isSeedHeadPartial = seedHead !== null
545+ newCacheNode = readCacheNodeFromSeedData (
546+ seedRsc ,
547+ seedLoading ,
548+ isSeedRscPartial ,
549+ seedHead ,
550+ isSeedHeadPartial ,
551+ isLeafSegment ,
552+ newParallelRoutes ,
553+ navigatedAt
554+ )
555+ needsDynamicRequest = isLeafSegment && isSeedHeadPartial
492556 } else if ( prefetchData !== null ) {
493557 // Consult the prefetch cache.
494558 const prefetchRsc = prefetchData [ 0 ]
@@ -533,6 +597,8 @@ function createCacheNodeOnNavigation(
533597 oldParallelRoutes !== undefined
534598 ? oldParallelRoutes . get ( parallelRouteKey )
535599 : undefined
600+ const seedDataChild : CacheNodeSeedData | void | null =
601+ seedDataChildren !== null ? seedDataChildren [ parallelRouteKey ] : null
536602 const prefetchDataChild : CacheNodeSeedData | void | null =
537603 prefetchDataChildren !== null
538604 ? prefetchDataChildren [ parallelRouteKey ]
@@ -555,6 +621,8 @@ function createCacheNodeOnNavigation(
555621 newRouterStateChild ,
556622 oldCacheNodeChild ,
557623 shouldRefreshDynamicData ,
624+ seedDataChild ?? null ,
625+ seedHead ,
558626 prefetchDataChild ?? null ,
559627 prefetchHead ,
560628 isPrefetchHeadPartial ,
@@ -569,7 +637,9 @@ function createCacheNodeOnNavigation(
569637 taskChildren . set ( parallelRouteKey , taskChild )
570638 const newCacheNodeChild = taskChild . node
571639 if ( newCacheNodeChild !== null ) {
572- const newSegmentMapChild : ChildSegmentMap = new Map ( oldSegmentMapChild )
640+ const newSegmentMapChild : ChildSegmentMap = new Map (
641+ shouldRefreshDynamicData ? undefined : oldSegmentMapChild
642+ )
573643 newSegmentMapChild . set ( newSegmentKeyChild , newCacheNodeChild )
574644 newParallelRoutes . set ( parallelRouteKey , newSegmentMapChild )
575645 }
0 commit comments