前言
先说下我们公司的目前kotlin和gradle版本
kotlin版本 | gradle插件版本 | gradle版本 | minSdkVersion | targetSdkVersion |
---|---|---|---|---|
1.3.72 | 4.0.2 | 6.7.1 | 21 | 33 |
我们升级后的目标是
kotlin版本 | gradle插件版本 | gradle版本 | minSdkVersion | targetSdkVersion |
---|---|---|---|---|
1.6.10 | 4.1.1 | 6.7.1 | 21 | 33 |
为什么升级和升级理由就不阐述了,直接上正餐。
gradle插件版本与gradle版本
- 首先我们需要知道gradle插件版本和gradle版本的关系
- 官网地址:developer.android.google.cn/studio/rele…
插件版本 | 所需的最低Gradle 版本 |
---|---|
8.1 | 8.0 |
8.0 | 8.0 |
7.4 | 7.5 |
7.3 | 7.4 |
7.2 | 7.3.3 |
7.1 | 7.2 |
7.0 | 7.0 |
4.2.0+ | 6.7.1 |
4.0.0+ | 6.1.1+ |
实践
首先我们直接上手,对gradle插件和kotlin进行升级
ext.kotlin_version = '1.6.10'
dependencies {
classpath 'com.android.tools.build:gradle:4.1.1'
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
}
直接点击同步我们遇到了第一个问题
异常一:Unable to get provider androidx.startup.InitializationProvider: androidx.startup.StartupException: java. lang.ClassNotFoundException:androidx.emoji2.text.EmojiCompatInitializer
第一反应有点懵,我都没添加过androidx.emobji2,这是啥玩意?多亏我在看过的寥寥无几的文章中,恰巧瞟了一眼关于emobji2的文章,这玩意添加依赖应该就可以嘞
def emojiVersion = "1.3.0"
implementation "androidx.emoji2:emoji2:$emojiVersion"
implementation "androidx.emoji2:emoji2-views:$emojiVersion"
同步一下,不报这个错了(不愧是我😏),然后就报了第二个错误
异常二:Unable to get provider androidx.startup.InitializationProvider: androidx.startup.StartupException: java. lang.ClassNotFoundException:com.huawei.agconnect.core.provider.AGConnectInitializeProvider
- 看了源码,这是华为自带的AGConnectInitializeProvider,然后打包的时候找不到,上网查大部分都是说要开启multixDex分包
- 但是我的minSdkVersion是21(Android 5.0)默认是开启分包的,完全不需要配置multiDex相关配置
- 我看到androidx.startup.InitializationProvider,就感觉这个玩意有鬼,于是就找了官方网址:developer.android.google.cn/jetpack/and…
使用
- app->build.gradle中添加相关依赖
implementation "androidx.startup:startup-runtime:1.2.0-alpha02"
- app->build.gradle中添加androidx.startup.InitializationProvider
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
android:exported="false"
tools:node="merge">
</provider>
- app->build.gradle中移除报错的AGConnectInitializeProvider,直接拷贝源码,然后添加tools:node="remove"即可。此方法会停用AGConnectInitializeProvider的自动初始化功能
<provider
android:name="com.huawei.agconnect.core.provider.AGConnectInitializeProvider"
android:authorities="${applicationId}.AGCInitializeProvider"
android:exported="false"
tools:node="remove" />
- 之后创建一个类AGConnectInitializeProviderInitializer继承
- onCreate中进行初始化
- dependencies:表示你需要的依赖库,不依赖其他库,可直接返回空列表
class AGConnectInitializeProviderInitializer:Initializer<Unit> {
override fun create(context: Context) {
AGConnectInstance.initialize(context)
}
override fun dependencies(): MutableList<Class<out Initializer<*>>> {
return mutableListOf()
}
}
- 调用组件初始化程序,Application中进行初始化
AppInitializer.getInstance(this).initializeComponent(InitProviderInitializer.class);
重新运行项目,我们会发现AutoSize这个库也会报上面的错误,我们继续按上面步骤走就好,只是第五步的时候,我们添加一个统一管理类InitProviderInitializer 修改后的代码如下
class InitProviderInitializer : Initializer<Unit> {
override fun create(context: Context) {
}
override fun dependencies(): MutableList<Class<out Initializer<*>>> {
return mutableListOf(
AutoSizeInitProviderInitializer::class.java,
AGConnectInitializeProviderInitializer::class.java
)
}
}
AutoSizeInitProviderInitializer的代码如下
class AutoSizeInitProviderInitializer: Initializer<Unit> {
override fun create(context: Context) {
AutoSize.checkAndInit(context.applicationContext as Application)
}
override fun dependencies(): MutableList<Class<out Initializer<*>>> {
return mutableListOf()
}
}
继续运行,我们发现它又报下面的错 阿哈?我明明没用到呀,他为什么报错呢?我总感觉Google在给我挖坑(嗯,一定是),既然还是androidx.startup错误,那就继续
class InitProviderInitializer : Initializer<Unit> {
override fun create(context: Context) {
}
override fun dependencies(): MutableList<Class<out Initializer<*>>> {
return mutableListOf(
AutoSizeInitProviderInitializer::class.java,
AGConnectInitializeProviderInitializer::class.java,
EmojiCompatInitializer::class.java
)
}
}
终于呀,不报androidx.startup相关错误,但是,他还是报错😭。
异常三:com.mob.MobProvider: iava.lang.ClassNotFoundException: Didn’t find class “com.mob.MobProvider”
- 我对了好几遍shareSDK官方文档,确定了好几遍,得到一个结论:我写的就是复制粘贴的,没毛病,但是就是报错。
- 我看到有的文章说是因为你项目中有多个版本,移除某个依赖,gradle.clean下重启一下(实测无效,浪费大把时间)
- 我盲测既然以前没问题,现在有问题,那就是gradle配置某项有问题,于是我找到了gradle.properties,撬开了它的天灵盖
android.useDeprecatedNdk=true
android.enableD8=true
android.useDexArchive=true
android.enableD8.desugaring=false
android.enableAapt2=true
android.enableD8=true
- 启用D8 Dex编译器,这是Android Gradle插件3.0及更高版本的默认选项,用于更高效地处理Dex编译
android.useDexArchive=true
- 启用Dex归档,以提高构建和应用启动性能。这是一个有助于加快应用加载速度的优化
android.enableAapt2=tru
- 启用AAPT2资源打包工具,它提供更快的资源处理速度和更好的错误报告。AAPT2是默认启用的
android.enableD8.desugaring=false
- 用于控制是否启用D8编译器的Desugaring功能。
- Desugaring是一种处理Java 8+语言特性的技术,使其能够在Android版本低于8.0的设备上运行。Android 8.0(API级别26)引入了对Java 8语言特性的原生支持,但在此之前的Android版本中,某些新的语言特性需要通过Desugaring来实现兼容性。
一句话就是:建议保留此配置设置(android.enableD8.desugaring=true
)。删掉此配置之后,重新运行,发现正常运行了。
总结
在kotlin和gradle升级过程中,我们会发现有引入一些新的东西和对gradle依赖的更新,以后大家还是要有机会经常去更新自己公司项目的库,防止一下子更新差距太大,网上呢又没有合适的资源和文章,导致步履维艰。
有人肯定会问,既然升级为什么不直接一步到位呢?你可以猜猜哦😏