You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Experimental bfcache: Restore state w/ <Activity> (#77992)
> [!NOTE]
> This feature does not affect the caching of dynamic data — only UI
state. Dynamic data is cached during back/forward navigations using a
different, preexisting mechanism; during normal navigations, dynamic
data is never cached, unless you opt in via
`experimental.staleTimes.dynamic`.
When navigating to a route that has already been visited, we should
restore as much of its previous state as we reasonably can — not only
state tracked by the browser, like scroll position and form inputs, but
also state owned by React, like `useState`.
The browser's native bfcache provides some of this automatically when
you use the back/forward buttons, or the history API. But it has
limitations, mainly that it can't restore state controlled by React. It
also doesn't work with navigations by regular links.
React has an experimental API called `<Activity>` that is designed for
this purpose. Content inside an Activity boundary can be hidden from the
UI without unmounting it; later, it can be restored to the UI without
having lost any state. React optimizes hidden Activity boundaries by
skipping over them during rendering, similar to how the browser handles
`content-visibility`. Later, during idle time, React will prerender the
boundaries so they are ready by the time they are revealed again.
In this PR, I've added an Activity boundary around every route segment
(i.e. layout or page). For each level of the route tree, the router will
render the N most recently active routes, and automatically toggle their
visibility as the user navigates, regardless of whether it's via the
back/forward buttons or regular links.
Aside from preserving state, keeping the inactive routes mounted also
makes navigations faster, since by the time you navigate the next screen
has already been prerendered.
In the future, we'll use this same mechanism to speculatively/
optimistically prerender routes that haven't yet been visited.
This is a nested bfcache — we track the history separately at each level
of the route tree. The lifetime of the bfcache is tied to the lifetime
of the React tree.
For now, the maximum number of entries per level is hardcoded to 3.
Eventually this will likely need to configurable per segment, but the
plan is for the default to be some smallish non-zero number. We'll
tinker with the heuristic before the feature is shipped to stable.
0 commit comments