[MS-1068] Navigation crash upon state restoration#1609
[MS-1068] Navigation crash upon state restoration#1609BurningAXE wants to merge 3 commits intomainfrom
Conversation
…gation when restoring state
…tion is null (graph not set)
There was a problem hiding this comment.
Pull request overview
Fixes a crash during process-death state restoration where result callbacks can fire before an internal NavHostFragment’s graph is set (notably in face capture and external credential controllers), causing navigation to run against a NavController with no currentDestination.
Changes:
- Reorders internal
NavController.setGraph(...)to occur before registeringhandleResult(...)callbacks in controller fragments. - Updates
NavController.canNavigate(...)to returnfalsewhencurrentDestinationisnull, preventing navigation attempts before a graph is set.
Reviewed changes
Copilot reviewed 3 out of 3 changed files in this pull request and generated 1 comment.
| File | Description |
|---|---|
| infra/ui-base/src/main/java/com/simprints/infra/uibase/navigation/NavigationResultExt.kt | Tightens canNavigate() to block navigation when currentDestination is null (graph not set). |
| feature/external-credential/src/main/java/com/simprints/feature/externalcredential/screens/controller/ExternalCredentialControllerFragment.kt | Sets internal graph before registering result handlers to avoid early callback navigation crashes. |
| face/capture/src/main/java/com/simprints/face/capture/screens/controller/FaceCaptureControllerFragment.kt | Sets internal graph (with dynamic start destination) before result handlers to avoid early callback navigation crashes. |
You can also share your feedback on Copilot code review. Take the survey.
| currentFragment ?: return false | ||
| val currentDest = currentDestination ?: return false | ||
| val targetClassName = (currentDest as? FragmentNavigator.Destination)?.className | ||
| return targetClassName == null || targetClassName == currentFragment::class.java.name |
There was a problem hiding this comment.
canNavigate() now returns false when currentDestination is null. That will route more cases through navigateIfPossible’s failure branch, which logs a Simber.w(..., IllegalStateException(...)). In release builds, Simber.w is forwarded to Crashlytics and records the exception, so this change can create noisy non-fatal Crashlytics issues during state restoration/graph setup races. Consider special-casing the currentDestination == null path to log without a throwable (or at info) and/or include a clearer message like “Nav graph not set yet” so it’s actionable without polluting Crashlytics.
There was a problem hiding this comment.
That's an exceptional situation that we do want to get informed about.
|



JIRA ticket
Will be released in: 2026.2.0
Root cause analysis (for bugfixes only)
First known affected version: since last major refactor
FaceCaptureControllerFragmentnav graph is set after result handlersFaceCaptureControllerFragmentexit screen handler tries to navigate but graph is not yet setNotable changes
setGraph()before result handlers so it's set before any result handler can fireExternalCredentialControllerFragmentwas also vulnerable to this so the same change was applied therecanNavigate()was updated to return false ifcurrentDestinationis null. This would prevent crashing if similar situation arises elsewhere (although user might get stuck).Testing guidance
Additional work checklist