KaustubhPatange / navigator

A small navigation library for Android to ease the use of fragment transactions & handling backstack (also available for Jetpack Compose).
Apache License 2.0
99 stars 5 forks source link

Crash on Production app with IllegalStateException #28

Open shakil807g opened 2 years ago

shakil807g commented 2 years ago

@KaustubhPatange I am getting this crash on Live App, could you please take a look at this issue Thanks.

Exception java.lang.IllegalStateException: Restarter must be created only during owner's initialization stage at androidx.savedstate.SavedStateRegistryController.performAttach (SavedStateRegistryController.kt:45) at androidx.savedstate.SavedStateRegistryController.performRestore (SavedStateRegistryController.kt:63) at com.lengo.uni.navigation.navigator_compose.LifecycleController.performRestore$app_allLangRelease (LifecycleController.java:206) at com.lengo.uni.navigation.navigator_compose.ComposeNavigator$Setup$1$1$1.invoke (ComposeNavigator.kt:1316) at com.lengo.uni.navigation.navigator_compose.ComposeNavigator$Setup$1$1$1.invoke (ComposeNavigator.kt:1310) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:116) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:34) at com.lengo.uni.navigation.navigator_compose.ComposeNavigator$CommonEffect$1$1$1.invoke (ComposeNavigator.kt:1401) at com.lengo.uni.navigation.navigator_compose.ComposeNavigator$CommonEffect$1$1$1.invoke (ComposeNavigator.kt:1390) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:116) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:34) at androidx.compose.foundation.layout.BoxWithConstraintsKt$BoxWithConstraints$1$1$measurables$1.invoke (BoxWithConstraints.kt:69) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:107) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:34) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState$subcompose$2$1$1.invoke (SubcomposeLayout.kt:770) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState$subcompose$2$1$1.invoke (SubcomposeLayout.kt:448) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:107) at androidx.compose.runtime.internal.ComposableLambdaImpl.invoke (ComposableLambda.jvm.kt:34) at androidx.compose.runtime.ActualJvm_jvmKt.invokeComposable (ActualJvm_jvmKt.java:74) at androidx.compose.runtime.ComposerImpl$doCompose$2$5.invoke (Composer.kt:3193) at androidx.compose.runtime.ComposerImpl$doCompose$2$5.invoke (Composer.kt:3183) at androidx.compose.runtime.SnapshotStateKtDerivedStateKt.observeDerivedStateRecalculations (SnapshotStateKtDerivedStateKt.java:252) at androidx.compose.runtime.SnapshotStateKt.observeDerivedStateRecalculations (SnapshotStateKt.java:1) at androidx.compose.runtime.ComposerImpl.doCompose (Composer.kt:3183) at androidx.compose.runtime.ComposerImpl.composeContent$runtime_release (ComposerImpl.java:3119) at androidx.compose.runtime.CompositionImpl.composeContent (Composition.kt:584) at androidx.compose.runtime.Recomposer.composeInitial$runtime_release (Recomposer.kt:811) at androidx.compose.runtime.ComposerImpl$CompositionContextImpl.composeInitial$runtime_release (Composer.kt:3712) at androidx.compose.runtime.ComposerImpl$CompositionContextImpl.composeInitial$runtime_release (Composer.kt:3712) at androidx.compose.runtime.CompositionImpl.setContent (Composition.kt:519) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState.subcomposeInto (SubcomposeLayout.kt:468) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState.subcompose (SubcomposeLayout.kt:441) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState.subcompose (SubcomposeLayout.kt:432) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState.subcompose (LayoutNodeSubcompositionsState.java:421) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState$Scope.subcompose (SubcomposeLayout.kt:732) at androidx.compose.foundation.layout.BoxWithConstraintsKt$BoxWithConstraints$1$1.invoke-0kLqBqw (BoxWithConstraints.kt:69) at androidx.compose.foundation.layout.BoxWithConstraintsKt$BoxWithConstraints$1$1.invoke (BoxWithConstraints.kt:67) at androidx.compose.ui.layout.LayoutNodeSubcompositionsState$createMeasurePolicy$1.measure-3p2s80s (SubcomposeLayout.kt:590) at androidx.compose.ui.node.InnerPlaceable.measure-BRTryo0 (InnerPlaceable.kt:44) at androidx.compose.ui.node.LayoutNode$performMeasure$1.invoke (LayoutNode.kt:1428) at androidx.compose.ui.node.LayoutNode$performMeasure$1.invoke (LayoutNode.kt:1427) at androidx.compose.runtime.snapshots.Snapshot$Companion.observe (Snapshot.kt:2116) at androidx.compose.runtime.snapshots.SnapshotStateObserver.observeReads (SnapshotStateObserver.kt:110) at androidx.compose.ui.node.OwnerSnapshotObserver.observeReads$ui_release (OwnerSnapshotObserver.kt:78) at androidx.compose.ui.node.OwnerSnapshotObserver.observeMeasureSnapshotReads$ui_release (OwnerSnapshotObserver.java:66) at androidx.compose.ui.node.LayoutNode.performMeasure-BRTryo0$ui_release (LayoutNode.java:1427) at androidx.compose.ui.node.OuterMeasurablePlaceable.remeasure-BRTryo0 (OuterMeasurablePlaceable.kt:94) at androidx.compose.ui.node.OuterMeasurablePlaceable.measure-BRTryo0 (OuterMeasurablePlaceable.kt:75) at androidx.compose.ui.node.LayoutNode.measure-BRTryo0 (LayoutNode.kt:1366) at androidx.compose.foundation.layout.BoxKt$boxMeasurePolicy$1.measure-3p2s80s (Box.kt:137) at androidx.compose.ui.node.InnerPlaceable.measure-BRTryo0 (InnerPlaceable.kt:44) at androidx.compose.ui.node.LayoutNode$performMeasure$1.invoke (LayoutNode.kt:1428) at androidx.compose.ui.node.LayoutNode$performMeasure$1.invoke (LayoutNode.kt:1427) at androidx.compose.runtime.snapshots.Snapshot$Companion.observe (Snapshot.kt:2116) at androidx.compose.runtime.snapshots.SnapshotStateObserver.observeReads (SnapshotStateObserver.kt:110) at androidx.compose.ui.node.OwnerSnapshotObserver.observeReads$ui_release (OwnerSnapshotObserver.kt:78) at androidx.compose.ui.node.OwnerSnapshotObserver.observeMeasureSnapshotReads$ui_release (OwnerSnapshotObserver.java:66) at androidx.compose.ui.node.LayoutNode.performMeasure-BRTryo0$ui_release (LayoutNode.java:1427) at androidx.compose.ui.node.OuterMeasurablePlaceable.remeasure-BRTryo0 (OuterMeasurablePlaceable.kt:94) at androidx.compose.ui.node.LayoutNode.remeasure-_Sx5XlM$ui_release (LayoutNode.java:1381) at androidx.compose.ui.node.LayoutNode.remeasure-_Sx5XlM$ui_release$default (LayoutNode.java:1372) at androidx.compose.ui.node.MeasureAndLayoutDelegate.doRemeasure-sdFAvZA (MeasureAndLayoutDelegate.kt:187) at androidx.compose.ui.node.MeasureAndLayoutDelegate.remeasureAndRelayoutIfNeeded (MeasureAndLayoutDelegate.kt:274) at androidx.compose.ui.node.MeasureAndLayoutDelegate.access$remeasureAndRelayoutIfNeeded (MeasureAndLayoutDelegate.kt:38) at androidx.compose.ui.node.MeasureAndLayoutDelegate.measureAndLayout (MeasureAndLayoutDelegate.kt:208) at androidx.compose.ui.platform.AndroidComposeView.measureAndLayout (AndroidComposeView.android.kt:757) at androidx.compose.ui.node.Owner.measureAndLayout$default (Owner.java:196) at androidx.compose.ui.platform.AndroidComposeView.dispatchDraw (AndroidComposeView.android.kt:954) at android.view.View.draw (View.java:23190)

KaustubhPatange commented 2 years ago

Use the latest 0.1-alpha36 release of Compose Navigator that will the fix the issue.

shakil807g commented 2 years ago

@KaustubhPatange I tried updating to 0.1-alpha36 but for some reason still getting the same crash on live play store build.

KaustubhPatange commented 2 years ago

Seems impossible, because everything related to the lifecycle is working fine. Is this crash reproducible?

shakil807g commented 2 years ago

@KaustubhPatange Actually, i was not able to reproduced it, but there many user who are getting this error

Screenshot 2022-10-13 at 12 28 21 PM Screenshot 2022-10-13 at 12 28 28 PM
shakil807g commented 2 years ago

Maybe this could be the reason because i'm using SaveState 1.2.0 https://developer.android.com/jetpack/androidx/releases/savedstate#version_120_3

KaustubhPatange commented 2 years ago

I think you don't need to add savestate dependency. But I'm not sure if this is actually the reason as Gradle picks the latest version if there are dependency collisions.

Now coming to the main part, I faced this error personally & it usually happens when you are popupTo through navigator-compose (Is that the case?), the other I found is that when process death happens. My point is, it is very important to have this reproducible otherwise I'm not able to figure out which screen is causing this failure.

shakil807g commented 2 years ago

@KaustubhPatange I added this check before calling performRestore i think it might resolve this issue if (!lifecycleController.isRestored() && lifecycleController.lifecycle.currentState == Lifecycle.State.INITIALIZED) { lifecycleController.performRestore(null)

Code below is from Androidx SavedStateRegistryController class

@MainThread fun performAttach() { val lifecycle = owner.lifecycle check(lifecycle.currentState == Lifecycle.State.INITIALIZED) { ("Restarter must be created only during owner's initialization stage") } lifecycle.addObserver(Recreator(owner)) savedStateRegistry.performAttach(lifecycle) attached = true }

KaustubhPatange commented 2 years ago

This is a hack, the main question is why your old destination's lifecycle is not destroyed even though the @Composable's onDispose {} is called, so navigator-compose is trying to reuse the same which is why crash!

Are you adding any lifecycle observers to route (mentioned in this doc)?

shakil807g commented 2 years ago

@KaustubhPatange No i'm not using lifecycle observers also not using popupTo as well.

KaustubhPatange commented 2 years ago

Are you changing the navigation destination within a coroutine scope somewhere?