java - 将 multidex apk 部署到 Fabric Beta 时出现 android ART NoClassDefFoundError

标签 java android kotlin compilation android-runtime

我有一个奇怪的问题。

我的 multidix 混合 java-kotlin 应用程序中有一段对字典进行排序的 kotlin 代码。 (代码如下)

在开发手机(SAMSUNG s9)上运行应用程序时,一切运行正常。 当将该应用程序部署到 Fabric 的“测试版”时,很大一部分 (50%) 的用户遇到 NoClassDefFoundError 类型的崩溃。 。 受影响的手机包括小米的小米5s和红米手机以及多款一加手机

我尝试查看输出的 apk(通过构建 -> 分析 APK)并确保该类确实存在。从this image可以看出- 该类实际上位于主“classes.dex”文件中。

任何帮助将不胜感激!

日志文件:

... (custom logging from the app on initiation level)

09-09 13:04:31.667 17365-17365/com.example.orcam.basic_recognition_app I/art: Rejecting re-init on previously-failed class java.lang.Class<com.example.orcam.logic_myme.ComputedData.ComputedPersonData$calculateMeetingsForPerson$2>

... (custom logging from the app on normal run level)

09-09 13:04:31.762 17365-17365/com.example.orcam.basic_recognition_app E/AndroidRuntime: FATAL EXCEPTION: main Process: com.example.orcam.basic_recognition_app, PID: 17365 java.lang.NoClassDefFoundError: com.example.orcam.logic_myme.ComputedData.ComputedPersonData$calculateMeetingsForPerson$2 at com.example.orcam.logic_myme.ComputedData.ComputedPersonData.calculateMeetingsForPerson(ComputedPersonData.kt:45) at com.example.orcam.logic_myme.ComputedData.ComputedData.calculate(ComputedData.kt:7) at com.example.orcam.logic_myme.db.DBManager$init$2.onDbInitAndReady(DBManager.kt:79) at com.example.lib_sync.sync.SyncManager2.(SyncManager2.java:63) at com.example.orcam.logic_myme.db.DBManager.init(DBManager.kt:76) at com.example.orcam.basic_recognition_app.LogicManager.init(LogicManager.java:58) at com.example.orcam.basic_recognition_app.MyMeApplication.initManagers(MyMeApplication.kt:31) at com.example.orcam.basic_recognition_app.MyMeApplication.onCreate(MyMeApplication.kt:13) at android.app.Instrumentation.callApplicationOnCreate(Instrumentation.java:1014) at android.app.ActivityThread.handleBindApplication(ActivityThread.java:4782) at android.app.ActivityThread.access$1700(ActivityThread.java:153) at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1445) at android.os.Handler.dispatchMessage(Handler.java:102) at android.os.Looper.loop(Looper.java:154) at android.app.ActivityThread.main(ActivityThread.java:5544) at java.lang.reflect.Method.invoke(Native Method) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:739) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:629) 09-09 13:04:31.763 17365-17365/com.example.orcam.basic_recognition_app E/MQSEventManagerDelegate: failed to get MQSService.

build.gradle 文件:

buildscript {
    repositories {
        maven { url 'https://maven.fabric.io/public' }
        google()
    }

    dependencies {
        classpath 'io.fabric.tools:gradle:1.+'
    }
}
apply plugin: 'com.android.application'
apply plugin: 'io.fabric'
apply plugin: 'kotlin-android'
apply plugin: 'kotlin-android-extensions'
apply plugin: 'kotlin-kapt'

repositories {
    maven { url 'https://maven.fabric.io/public' }
    google()
}


android {
    compileSdkVersion 27
    buildToolsVersion "27.0.3"

    defaultConfig {
        applicationId "com.example.orcam.basic_recognition_app"
        minSdkVersion 21
        targetSdkVersion 27
        versionCode 29
        versionName "5.0.9"

    }
    buildTypes {
        debug {
            applicationIdSuffix ".debug"
        }

        beta {
            initWith debug
            applicationIdSuffix ""
        }



        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
    packagingOptions {
        pickFirst 'META-INF/LICENSE'
        pickFirst 'META-INF/DEPENDENCIES'
        pickFirst 'META-INF/ASL-2.0.txt'
        pickFirst 'META-INF/LGPL-3.0.txt'
        exclude 'META-INF/main.kotlin_module'
    }
    dexOptions {
        preDexLibraries = false
    }
}

ext {
    supportLibVersion = '27.1.1'
}

dependencies {
    /* ... a lot of dependencies ... */

    // multi dex
    implementation 'com.android.support:multidex:1.0.3'

    // kotlin
    compile "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"

}
kapt {
    generateStubs = true
}

CompulatedPersonData.kt 文件(仅具有“坏”功能的简化版本):

class ComputedPersonData() {
    var meetingsByPerson = mapOf<String, ArrayList<String>>()

    fun calculateMeetingsForPerson() {
        val faces: Map<String: Face?> = getFaces()
        val faceToContact: Map<String: String?> = getMapping()
        val peopleWithFaces = mutableMapOf<String, ArrayList<Face>>()


        faces.values.forEach {
            if (it != null) {
                val personId = faceToContact[it.imageId] ?: ""

                val list = peopleWithFaces[personId] ?: run {
                    peopleWithFaces[personId] = arrayListOf(it)
                    return@forEach
                }
                list.add(it)
            }
        }

        val dictSorted = mutableMapOf<String, ArrayList<Face>>()
        peopleWithFaces.forEach { id, item ->
            dictSorted[id] = ArrayList(item.sortedBy { it.timestamp })
        }

// the "dictSorted.mapValues{}" generates the "bad" $2 class

        val dictFaceToString: Map<String, ArrayList<String>> = dictSorted.mapValues {
            ArrayList(it.value.map {
                it.id
            }
            )
        }

        this.meetingsByPerson = dictFaceToString
    }
}

应用程序类:

class MyApplication : MultiDexApplication()

最佳答案

好吧,经过几个月的调查,显然坏线是 -

peopleWithFaces.forEach { id, item ->
            dictSorted[id] = ArrayList(item.sortedBy { it.timestamp })
        }

旧的 android-OS(特定于 6.0.0)和 kotlin 的解耦 for-each 存在问题。

一旦发现问题,解决办法就很简单了。我们需要做的就是像这样重写这个有趣的东西:

peopleWithFaces.forEach { 
            val id = it.key
            val item = it.value
            dictSorted[id] = ArrayList(item.sortedBy { it.timestamp })
        }

关于java - 将 multidex apk 部署到 Fabric Beta 时出现 android ART NoClassDefFoundError,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52243627/

相关文章:

android - 如何在 MVVM 架构中使用来自 onActivityResult 的数据?

java - 如何找到 Java 依赖项?

java - 用于投影异常的 Spring Data Rest ResourceProcessor

java - Android(Eclipse)找不到google-play-services_lib.apk尝试了多种解决方案

android - 使用 tess-two 库从 android 中的位图中提取数字

java - 空字段导致错误 "stopped unexpectedly"

kotlin - Spring WebFlux Webclient 作为 Mono 接收应用程序/八位字节流文件

java - 获取 jsp 响应作为 servlet 中的字符串

java - 如果我的数据库中没有任何要上传的图像怎么办?

android - jetpack 内的动画组成绘制范围