启用minify后Compose Android测试失败:类/方法未找到
问题描述
启用minify后,Compose单元测试运行失败,报错如下:
java.lang.NoSuchMethodError: No interface method complete()Z in class Lkotlinx/coroutines/CompletableJob; or its super classes (declaration of 'kotlinx.coroutines.CompletableJob' appears in /data/app/com.clover.engine-7ap2fJvfCgX89H0L0ytLZg==/base.apk!classes3.dex) at androidx.compose.ui.test.junit4.IdlingResourceRegistry.<init>(IdlingResourceRegistry.jvm.kt:46) at androidx.compose.ui.test.junit4.IdlingResourceRegistry.<init>(IdlingResourceRegistry.jvm.kt:37) at androidx.compose.ui.test.AndroidComposeUiTestEnvironment.<init>(ComposeUiTest.android.kt:220) ... at androidx.compose.ui.test.junit4.AndroidComposeTestRule_androidKt.createComposeRule(AndroidComposeTestRule.android.kt:212) at com.mytest.MyTest.<init>(...)
尝试添加ProGuard规则绕过当前问题,但不断出现新的缺失项,显然这不是正确方向。
当前minify配置:
buildTypes.all { minifyEnabled true // ... }
其他androidTest测试运行正常,启用minify后应用中的Compose页面也能正常工作。
Compose相关依赖配置:
def composeBom = platform('androidx.compose:compose-bom:2023.1.00') implementation composeBom androidTestImplementation composeBom implementation 'androidx.compose.material3:material3' implementation 'androidx.compose.ui:ui-tooling-preview' debugImplementation 'androidx.compose.ui:ui-tooling' implementation 'androidx.compose.runtime:runtime-livedata' implementation 'androidx.activity:activity-compose:1.6.1' implementation 'androidx.lifecycle:lifecycle-viewmodel-compose:2.5.1' androidTestImplementation 'androidx.compose.ui:ui-test-junit4'
补充:参考Compose最佳实践应用Now in Android,发现其在测试时并未启用minify。
解决方案
1. 针对测试构建类型禁用minify
将全局启用minify的配置改为仅针对非测试构建类型生效,或者单独为测试依赖的构建类型(通常是debug)关闭minify:
buildTypes { release { minifyEnabled true // 其他release相关配置 } debug { minifyEnabled false // 其他debug相关配置 } }
如果需要保留debug构建的minify但测试时跳过混淆,可指定测试使用的构建类型并单独配置:
android { testBuildType "debug" buildTypes { debug { minifyEnabled false } } }
2. 为测试配置专属混淆规则(不推荐)
如果坚持要在测试时启用minify,需为androidTest添加专门的ProGuard规则,确保Compose测试相关类和依赖不被混淆。创建proguard-rules-test.pro文件并添加以下规则:
# 保留Compose测试核心类 -keep class androidx.compose.ui.test.** { *; } # 保留kotlinx.coroutines相关类与接口 -keep class kotlinx.coroutines.** { *; } -keep interface kotlinx.coroutines.CompletableJob { *; } # 保留JUnit测试相关注解与方法 -keep @org.junit.** class * -keepclassmembers class * { @org.junit.Test *; @org.junit.Before *; @org.junit.After *; }
然后在build.gradle中指定测试的混淆规则文件:
buildTypes.all { minifyEnabled true testProguardFiles getDefaultProguardFile('proguard-android-test.txt'), 'proguard-rules-test.pro' }
注:这种方式需要持续维护规则,可能不断出现新的缺失项,维护成本较高。
3. 检查依赖版本一致性
确认implementation与androidTestImplementation的Compose BOM版本一致(当前已满足),同时通过./gradlew dependencies查看依赖树,排查kotlinx.coroutines是否存在版本冲突,确保测试依赖的协程版本与应用依赖的版本匹配。
内容的提问来源于stack exchange,提问作者Jeffrey Blattman
相关产品推荐
相关产品推荐

