onStop 在 onDestroy 之后被调用?

Ale*_*ock 11 android broadcastreceiver android-lifecycle

我遇到了一个相当奇怪的Activity生命周期问题。

短前传:

我发现的第一个症状是,IllegalArgumentException当我onStoponStart.

转储活动接收器的完整列表(一些反射魔法)后,我发现我的接收器不是列表。它要么被错误地从其他地方删除,要么在onDestroy调用正在清理的Activity位置期间被删除Context(在onDestroy ActivityThread调用期间ContextImpl#performFinalCleanup,然后调用LoadedApk#removeContextRegistrations)。

怎么了?

在向崩溃添加更多分析信息后,我发现当崩溃发生时onStopActivity它处于一种非常奇怪的状态 - 它是isDestroyed()调用返回true,它是isFinishing()返回false,它是getLifecycle().getCurrentState()返回DESTROYED......

检查正常onStop()(没有崩溃)调用表明Activity处于这种状态:

isDestroyed()false,并且getLifecycle().getCurrentState()CREATEDonStop

所以我得出了onStop正在被调用的结论,onDestroy我认为这是不可能的,但它似乎发生了。

并且onStop绝对不会被应用程序中的其他东西手动调用,因为这是调用 的位置的堆栈跟踪onStop

com.myapp.TheActivity.onStop (TheActivity.java:217)
android.app.Instrumentation.callActivityOnStop (Instrumentation.java:1474)
android.app.Activity.performStop (Activity.java:8189)
android.app.ActivityThread.callActivityOnStop (ActivityThread.java:4994)
android.app.ActivityThread.performStopActivityInner (ActivityThread.java:4967)
android.app.ActivityThread.handleStopActivity (ActivityThread.java:5047)
android.app.servertransaction.TransactionExecutor.performLifecycleSequence (TransactionExecutor.java:233)
android.app.servertransaction.TransactionExecutor.cycleToPath (TransactionExecutor.java:201)
android.app.servertransaction.TransactionExecutor.executeLifecycleState (TransactionExecutor.java:173)
android.app.servertransaction.TransactionExecutor.execute (TransactionExecutor.java:97)
android.app.ActivityThread$H.handleMessage (ActivityThread.java:2220)
android.os.Handler.dispatchMessage (Handler.java:107)
android.os.Looper.loop (Looper.java:237)
android.app.ActivityThread.main (ActivityThread.java:8016)
java.lang.reflect.Method.invoke (Method.java)
com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run (RuntimeInit.java:493)
com.android.internal.os.ZygoteInit.main (ZygoteInit.java:1076)
Run Code Online (Sandbox Code Playgroud)

Sin*_*ina 2

原因尚不清楚,但最近越来越受到关注。它发生在 onResume/onPause 和 onStart/onStop 对中调用注册/取消注册。关于这些生命周期检查,请确保您在活动实例上具有 hashCode() 或其他内容。无论如何,要解决此问题,最佳实践是将注册/取消注册调用包装在 try/catch 块中:

private void registerBroadcastReceiver() {
    try {
        appUpdateReceiver = new AppUpdateReceiver();
        registerReceiver(appUpdateReceiver, appUpdateIntentFilter);
    } catch (IllegalArgumentException e) {
        // already registered
    }

}

private void unregisterBroadcastReceiver() {
    try {
        unregisterReceiver(appUpdateReceiver);
    } catch (IllegalArgumentException e) {
        // already unregistered
    }
}
Run Code Online (Sandbox Code Playgroud)