getsentry / getsentry/sentry-java
Nav3: Multistack support
- Linguagem predominante
- Kotlin
- Estrelas
- 1.4k
- Forks
- 478
- Merge médio
- 3d 4h
- PRs com merge (30d)
- 72
Descrição
### Problem Statement
Apps with bottom tabs, drawer navigation, or similar patterns often maintain multiple independent backstacks – one per top-level destination – so that users can switch tabs without losing their place. [Nav3]() doesn't provide a built-in multi-back-stack API; instead, apps own multiple `NavBackStack` instances and merge their entries before passing them to `NavDisplay` (see the [`multiplestacks` recipe]()).
The Stage 1 integration (getsentry/sentry-java#5000) and multipane support (getsentry/sentry-java#5649) handle a single `SnapshotStateList` backstack. When an app uses multiple stacks, the SDK needs to understand which stack is active and scope its telemetry accordingly.
### Solution Brainstorm
* **Stack identification.** Introduce a `stack_id` concept so breadcrumbs, transactions, and crash context can group navigations per stack. This could be a user-supplied label per stack (e.g. the tab route key's name), or inferred from the `NavBackStack` identity.
* **API surface.** Provide a way to register multiple backstacks with a shared `SentryNavStateHolder`, or create per-stack holders that coordinate. The app tells us which stack is currently active (likely by passing the active `topLevelRoute` or equivalent).
* `scope.screen` – set to the active stack's top route. When the user switches tabs, this triggers a navigation breadcrumb and updates `scope.screen` to the new stack's current top.
* **Breadcrumbs** – capture both intra-stack navigation (push/pop within a tab) and inter-stack switches (tab change). Include `stack_id` in breadcrumb data so the two can be distinguished. A tab switch breadcrumb might look like `{ from: "/settings/profile", to: "/home/feed", stack_id: "home" }`.
* **Transactions** – when the user switches to a stack whose top entry hasn't changed, should we start a new transaction? Probably not – the screen was already loaded. Only start a transaction on an actual new destination within the stack.
* **Crash context (**`contexts.navigation`**)** – include all stacks (not just the active one), capped by `maxBackstackSize` total across stacks. Mark which stack is active.
Open questions:
* Should `contexts.navigation.backstack` flatten all stacks into one list, or nest them by `stack_id`?
* How do multistack and multipane compose? A tablet app might have bottom tabs (multistack) where one tab shows a list-detail layout (multipane). The primary pane logic from Stage 2 should still apply within the active stack.
* Should tab switches reuse the existing `"navigation"` breadcrumb category or get a distinct one (e.g. `"stack_switch"`)?
* Do we want to revisit Nav2 simplifications alongside this (nested nav graphs, dialog/bottom-sheet transaction behavior)?
### Existing Nav2 support
Nav2 supports multiple backstacks natively via `NavController.navigate()` with `saveState = true` / `restoreState = true`, commonly used with `NavigationBar` or `BottomNavigation`. However, the current Nav2 integration does not distinguish between stacks – it sees a flat stream of destination changes on a single `NavController` and treats every destination change identically. There is no `stack_id`, no differentiation between intra-tab navigation and tab switches, and no per-stack grouping in crash context. A tab switch looks the same as a forward navigation in telemetry.
Guia de contribuição
Direção de pesquisa
Comece revisando a receita de multistacks do Nav3 e as integrações de Stage 1 e multipane referenciadas na issue. Determine como várias instâncias de NavBackStack, a rota top-level ativa e NavDisplay são representadas antes de resolver as questões em aberto sobre a API e a telemetria. O trabalho estará concluído quando o comportamento de multistack e sua interação com Nav2, o suporte a multipane, breadcrumbs, transações e o contexto de navegação estiverem especificados e cobertos por testes.
Escrita pelo modelo de indexação a partir do texto da issue.
Avaliação
- Stack de tecnologia
- android, kotlin
- Domínio
- mobile, observability
- Tipo de issue
- Funcionalidade
- Dificuldade
- 5/5
- Tempo estimado
- Mais de uma semana
- Status de atividade
- Pouca atividade
- Clareza
- Precisa de esclarecimento
- Facilidade para iniciantes
- 30/100