android-development

Android Navigation 3: State-Aware Routing Without the Boilerplate

State restoration is the tax every Android developer pays. `rememberSaveable` for UI fragments, `SavedStateHandle` for ViewModels, and the hope that process death does not arrive between two screens. The pattern works. The boilerplate is also real, and it leaks across the entire architecture.

Navigation 3 and its `NavKey` interface propose a different deal. Instead of patching state survival into individual components, the navigation layer becomes the state container. The back stack itself is serialized. Configuration changes and process death are handled at the navigation layer, not in each composable.

What changes in Navigation 3

The traditional two-engine split disappears. `rememberSaveable` handles UI state; `SavedStateHandle` handles ViewModel arguments. Both connect to Android's saved state registry, but they remain separate systems with separate mental models.

Navigation 3 promotes the back stack to the source of truth. Destinations are defined as typed, serializable data structures—sealed classes or interfaces annotated for the serialization library. Each screen becomes a self-contained unit that carries its own arguments. The framework can now bundle the entire navigation state because every entry knows how to serialize itself.

Routes replace the old nav argument pattern. A detail screen that previously required a string ID extracted from a generic map now receives that value directly from the route object. No registry lookup, no key extraction, no nullability juggling.

Why this is a real shift

The old model scatters state across three locations: the nav graph, the ViewModel, and the composable. Lose track of which field lives where, and a process death returns the user to the wrong screen with the wrong data—or no data at all.

Navigation 3 collapses that mental overhead. A route object is not just a destination label; it contains the arguments, it serializes itself, and it survives process death as part of the back stack. Restore the list, restore the app. Configuration changes and process death are handled at the architectural root, not the leaf nodes.

The trade-off is real but bounded. Anything that does not belong in a route still needs the old tools. Transient UI state, form input, animation positions—these remain `rememberSaveable` territory. The shift targets navigation arguments and the screen state that rides with them.

Who should care

Scenario Verdict
Starting a new app Adopt Navigation 3 from day one. The type safety and reduced boilerplate pay off immediately.
Maintaining an app with years of `SavedStateHandle` Migrate new feature areas only. Keep the old system for existing screens.
Team unfamiliar with Kotlinx Serialization Budget for a learning sprint. The pattern is clean but requires comfort with sealed interfaces and serializable data structures.
Project on a tight timeline Wait. Navigation 3 is experimental. APIs can move, and migration cost is non-zero.

What to watch next

The AndroidX release notes are the primary feed. Navigation 3 is still experimental, which means the API surface can shift. If you adopt it today, build migration buffers into your roadmap. The old pattern is not dead, but the direction is clear.

Key takeaways

  • Navigation 3 makes the back stack the primary state container for navigation arguments.
  • Routes are typed serializable objects, which enables native process death survival.
  • `SavedStateHandle` and `rememberSaveable` remain relevant for non-navigation state.
  • The API is experimental; plan for migration work if you adopt now.

Frequently asked questions

What is NavKey in Android Navigation 3?

NavKey is a marker interface that signals a route object can be serialized. When a destination implements NavKey, it can carry arguments and survive process death as part of the back stack.

Can Navigation 3 fully replace SavedStateHandle?

For navigation arguments, yes. For other ViewModel state that does not belong in a route, SavedStateHandle or a similar mechanism is still required.

Is Navigation 3 stable?

The reference describes the APIs as experimental. Treat them as moving targets and monitor the AndroidX navigation release notes for updates.

What is the role of Kotlinx Serialization?

It provides compile-time type safety for routes and enables the back stack to be saved to the Android saved state registry as a serializable structure.

Do I need to rewrite my existing app?

No. For existing apps, a phased migration starting with new feature areas is the safer path. Run both systems in parallel until the API stabilizes.

Related