Skip to content

Split the navigation graph per feature - #72

Merged
AhmadKharfan merged 2 commits into
developfrom
refactor/split-nav-graphs
Jul 29, 2026
Merged

Split the navigation graph per feature#72
AhmadKharfan merged 2 commits into
developfrom
refactor/split-nav-graphs

Conversation

@AhmadKharfan

Copy link
Copy Markdown
Owner

Why

AslNavHost.kt was 296 lines with a single 254-line composable holding 24 destinations for every feature in the app — onboarding, hub, projects, terminal, editor, git, settings, crash report, all interleaved.

Finding how one screen was wired meant scrolling the whole file, and adding a destination for any feature meant editing the one file every feature shares.

What changed

Destinations moved into per-feature NavGraphBuilder extension functions in a new navigation/NavGraphs.kt:

NavHost(...) {
    onboardingGraph(navController)
    projectsGraph(navController)
    utilityGraph(navController)
    editorGraph(navController)
    settingsGraph(navController)
    deviceSupportGraph()
}

editorGraph further delegates to one function per destination (editorDestination, gitDiffDestination, gitHistoryDestination, gitBlameDestination, gitRefsDestination, gitConflictsDestination), since those carry the parameterised routes.

AslNavHost drops from 296 lines to 44 and now reads as a table of contents. Every extension takes a single navController parameter.

Behavior

No behavior change — and since navigation here is stringly-typed, the compiler verifies almost none of that, so it was checked by diffing against develop:

  • Route registrations: identical list, identical order. Order matters for deep links and ambiguous matches.
  • navArgument definitions: identical names and configuration. A typo here is a runtime crash on navigation, not a compile error.
  • Routes.kt: untouched.
  • savedStateHandle handoffs: unchanged — folder picker writes picked_folder to the previous entry for Hub and Create Project to consume; conflicts writes git_conflict_path for the editor.

rememberUpdatedState(onOpenProjectConsumed) stays in the @Composable AslNavHost. NavGraphBuilder extensions are not composable and cannot call it, and it exists specifically to stop a stale callback being invoked — the same bug class fixed in #70. The resolved value is passed down as a plain parameter.

Nav transitions (aslEnter/aslExit/aslPopEnter/aslPopExit) remain NavHost-level defaults rather than moving onto individual graphs.

Scope

:app navigation wiring only. No feature module, no route constant, and no detekt configuration was touched.

Tests

No new tests. A structural move with no new logic; the full suite passes.

Verification

  • ./gradlew test — all modules pass.
  • ./gradlew :app:compileDebugKotlin — passes.
  • ./gradlew detekt — passes.
  • Route list, route order and navArgument configuration each diffed against develop and confirmed identical.
  • rememberUpdatedState confirmed present in AslNavHost and absent from every graph extension.

Baseline

app/detekt-baseline.xml regenerated — 1 removed, 0 added: LongMethod:AslNavHost. Project total 243 → 242.

ParameterNaming:AslNavHost$onOpenProjectConsumed correctly remains: it names a completed event, where past tense is right and the compose-rules present-tense convention does not apply.

@AhmadKharfan
AhmadKharfan merged commit 26b49ed into develop Jul 29, 2026
2 checks passed
@AhmadKharfan
AhmadKharfan deleted the refactor/split-nav-graphs branch July 29, 2026 18:00
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant