在我们的其中一个发行版中,我们使用ProGuard来帮助混淆和最小化代码。这个问题在我的设备或仿真器上无法重现,但是通过Crashlytics从某些用户那里我们得到了一个异常,指出系统找不到类。该异常来自各种设备以及Android Lollipop以上版本。 (API 21)
异常跟踪:
Caused by java.lang.ClassNotFoundException: Did not find class "com.example.android.views.CustomImageView" on path: DexPathList[[zip file "/data/app/com.example.android-1/base.apk"],nativeLibraryDirectories=[/data/app/com.example.android-1/lib/arm, /vendor/lib, /system/lib]]
at dalvik.system.BaseDexClassLoader.findClass + 56(BaseDexClassLoader.java:56)
at java.lang.ClassLoader.loadClass + 511(ClassLoader.java:511)
at java.lang.ClassLoader.loadClass + 469(ClassLoader.java:469)
at android.view.LayoutInflater.createView + 583(LayoutInflater.java:583)
at android.view.LayoutInflater.createViewFromTag + 764(LayoutInflater.java:764)
at android.view.LayoutInflater.createViewFromTag + 704(LayoutInflater.java:704)
at android.view.LayoutInflater.rInflate + 835(LayoutInflater.java:835)
at android.view.LayoutInflater.rInflateChildren + 798(LayoutInflater.java:798)
at android.view.LayoutInflater.rInflate + 838(LayoutInflater.java:838)
at android.view.LayoutInflater.rInflateChildren + 798(LayoutInflater.java:798)
at android.view.LayoutInflater.rInflate + 838(LayoutInflater.java:838)
at android.view.LayoutInflater.rInflateChildren + 798(LayoutInflater.java:798)
at android.view.LayoutInflater.inflate + 515(LayoutInflater.java:515)
at android.view.LayoutInflater.inflate + 423(LayoutInflater.java:423)
at com.example.android.fragments.MyFragment.onCreateView + 160(AdPopupFragmentVertical.java:160)
at androidx.fragment.app.Fragment.performCreateView + 2600(Fragment.java:2600)
at androidx.fragment.app.FragmentManagerImpl.moveToState + 881(FragmentManagerImpl.java:881)
at androidx.fragment.app.FragmentManagerImpl.moveFragmentToExpectedState + 1238(FragmentManagerImpl.java:1238)
at androidx.fragment.app.FragmentManagerImpl.moveToState + 1303(FragmentManagerImpl.java:1303)
at androidx.fragment.app.FragmentManagerImpl.dispatchStateChange + 2659(FragmentManagerImpl.java:2659)
at androidx.fragment.app.FragmentManagerImpl.dispatchActivityCreated + 2613(FragmentManagerImpl.java:2613)
at androidx.fragment.app.FragmentController.dispatchActivityCreated + 246(FragmentController.java:246)
at androidx.fragment.app.FragmentActivity.onStart + 542(FragmentActivity.java:542)
at androidx.appcompat.app.AppCompatActivity.onStart + 201(AppCompatActivity.java:201)
相关的ProGuard规则:
-keep class com.example.android.views.** { *; }
而且,为了更加安全,我也将@Keep
注释也添加到类的顶部,如下所示:
package com.example.android.views;
import androidx.annotation.Keep;
@Keep
public class CustomImageView extends AppCompatImageView {
// rest of the code
}
[为确保安全,我构建了一个发行版APK并通过APK分析器进行了检查。现在,该应用程序使用MultiDex(因为它必须包含广告),并且classes.dex
文件似乎包含具有正确名称,路径(即包装)和方法的视图。因此,我不明白为什么某些设备无法找到此视图。
可以解决此问题的其他方法?感谢您的任何帮助,谢谢。
编辑:如果有帮助,此视图是一个特殊视图,该视图根据在Android Lollipop上方使用Renderscript发送到的位图来创建投影。 (API 21)
编辑2:这是我的应用程序级别的build.gradle文件。 (跳过不必要的部分)
android {
compileSdkVersion 29
buildToolsVersion '28.0.3' // this is ignored already
defaultConfig {
applicationId "com.example.android"
minSdkVersion 16
targetSdkVersion 29
versionCode 1000
versionName "1000"
multiDexEnabled true
lintOptions {
checkReleaseBuilds false
}
vectorDrawables.useSupportLibrary = true
}
dexOptions {
preDexLibraries = false
javaMaxHeapSize "4g"
}
buildTypes {
release {
minifyEnabled true
shrinkResources true
proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
signingConfig signingConfigs.release
}
debug {
signingConfig signingConfigs.release
}
}
compileOptions {
sourceCompatibility = '1.8'
targetCompatibility = '1.8'
}
applicationVariants.all { variant ->
def flavor = variant.mergedFlavor
def name = flavor.getVersionName()
if (variant.buildType.isDebuggable())
name += 'd'
else
name += 'r'
variant.outputs.each { output ->
output.versionNameOverride = name
}
variant.outputs.all {
def versionName = variant.versionName
versionName += variant.buildType.isDebuggable() ? 'd' : 'r'
outputFileName = "example-${versionName}.apk"
}
}
useLibrary 'org.apache.http.legacy'
}
更改您的minsdk和目标sdk,在app.gradle中将其编译为sdk
compileSdkVersion 29
minSdkVersion 15
targetSdkVersion 29