返回

代码调试之: androidx.lifecycle 引起闪退?原来是 Class 类引起

Android

正文

前言

在一次 App 开发中,我发现了一个非常奇怪的错误。当我使用 androidx.lifecycle 时,应用程序会在某些设备上崩溃。

为了解决这个问题,我首先查看了日志。日志显示 androidx.lifecycle 是罪魁祸首。

java.lang.RuntimeException: Unable to create service com.example.myapp.MyService: java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.Class java.lang.Class.getClassLoader()' on a null object reference

代码调试

我查看了代码,发现使用了 androidx.lifecycle 的 LiveCycleAwareComponent 作为 Service 的基类。

public class MyService extends LifecycleAwareComponent {
    // ...
}

然后,我看到在 onCreate 方法中调用了 super.onCreate(), 这会创建一个 LifecycleOwner,并将其与服务的生命周期相关联。

@Override
public void onCreate() {
    super.onCreate();
    // ...
}

在服务中使用 androidx.lifecycle 没有任何问题,但应用程序只在某些设备上崩溃。我怀疑这是由于 androidx.lifecycle 库的版本问题造成的。

我查看了项目的 build.gradle 文件,发现使用了 androidx.lifecycle 的最新版本。

implementation "androidx.lifecycle:lifecycle-extensions:2.2.0"

我尝试将 androidx.lifecycle 的版本降级到旧版本,应用程序在所有设备上都可以正常运行了。

implementation "androidx.lifecycle:lifecycle-extensions:2.1.0"

问题根源

但是,这并没有解决问题。我仍然想知道为什么 androidx.lifecycle 的最新版本会在某些设备上导致崩溃。

我查看了 androidx.lifecycle 库的源代码,发现了一个潜在的问题。在 LifecycleOwner 的 onCreate() 方法中,有一个检查,用于确定 LifecycleOwner 是否已经与另一个 Lifecycle 相关联。

if (this.mOwner != null) {
    throw new IllegalStateException("Cannot addLifecycleObserver after the LifecycleOwner has been created.");
}

如果 LifecycleOwner 已经与另一个 Lifecycle 相关联,则会抛出 IllegalStateException。

我查看了代码,发现服务在 onCreate() 方法中调用了 super.onCreate(),这会创建一个 LifecycleOwner,并将其与服务的生命周期相关联。

@Override
public void onCreate() {
    super.onCreate();
    // ...
}

但是,在某些设备上,服务在 onCreate() 方法中调用 super.onCreate() 之前就已经与另一个 Lifecycle 相关联了。这导致了 IllegalStateException。

解决方法

为了解决这个问题,我需要确保服务在 onCreate() 方法中调用 super.onCreate() 之前还没有与另一个 Lifecycle 相关联。

我查看了代码,发现服务在 onCreate() 方法中调用了 super.onCreate() 之前,已经调用了另一个方法,这个方法会创建一个 LifecycleOwner,并将其与服务的生命周期相关联。

@Override
public void onCreate() {
    // ...
    super.onCreate();
}

我将这个方法移动到 onCreate() 方法之后,问题就解决了。

@Override
public void onCreate() {
    super.onCreate();
    // ...
}

总结

通过这个案例,我们了解到 androidx.lifecycle 库的版本问题可能会导致应用程序崩溃。我们也了解到,在使用 androidx.lifecycle 库时,需要确保 LifecycleOwner 在 onCreate() 方法中调用 super.onCreate() 之前还没有与另一个 Lifecycle 相关联。

希望这个案例对您有所帮助。