如何配置ProGuard不移除Kotlin Lambda函数参数?
解决Release模式下ProGuard移除Lambda回调的问题
问题原因
Release模式中ProGuard会对未明确保护的类和方法进行混淆或移除,你传递给JNI的Kotlin Lambda本质是kotlin.jvm.functions.Function1接口的实现类,其invoke(int)方法被ProGuard处理后,JNI调用GetMethodID时无法找到该方法,导致mid == null错误。之前定义的@Keep全局变量和实际传递的Lambda不是同一个对象,因此无法解决问题。
正确的ProGuard配置方案
添加以下规则到你的ProGuard配置文件(通常是proguard-rules.pro):
- 保护GitManager相关类与外部方法
确保JNI调用的外部方法及其参数类型不被混淆:
# 保护GitManager类及其方法 -keep class com.example.gitnote.manager.GitManager { *; } # 保护顶层函数所在的GitManagerKt类及cloneRepoLib方法 -keep class com.example.gitnote.manager.GitManagerKt { private external fun cloneRepoLib(java.lang.String, java.lang.String, java.lang.String, java.lang.String, kotlin.jvm.functions.Function1); }
- 保护Function1接口的invoke方法
直接保护Lambda对应的接口方法,确保JNI能找到invoke(int):
# 保护Function1接口的int参数版本invoke方法 -keep class kotlin.jvm.functions.Function1 { public abstract void invoke(int); } # 或者更通用的:保护所有实现Function1的类的invoke方法 -keepclassmembers class * implements kotlin.jvm.functions.Function1 { public void invoke(int); }
额外说明
如果你的回调涉及更多参数类型的Lambda(比如其他FunctionN接口),可以扩展对应的规则。另外,确保@Keep注解只作用于需要保留的关键对象,避免不必要的内存占用。
内容的提问来源于stack exchange,提问作者wiiznokes3
相关产品推荐
相关产品推荐

