产品想要接入热修复功能、又不想自研进行差分包下发管理加大研发周期。故尝试对buyly提供的热修复功能进行接入、对接入过程中的一丢丢问题进行记录 (虽然不是很建议接入 Google play都禁止了)
应用配置信息一览表
minSdkVersion 21
targetSdkVersion 30
classpath 'com.android.tools.build:gradle:3.4.3'
com.tencent.bugly:tinker-support:1.2.1
'androidx.multidex:multidex:2.0.0',
'com.tencent.tinker:tinker-android-lib:1.9.14.10',
"com.tencent.tinker:tinker-android-anno-support:1.9.14.10"
'com.tencent.bugly:crashreport_upgrade:1.5.0'
'com.tencent.bugly:nativecrashreport:3.9.0'
distributionUrl=https://services.gradle.org/distributions/gradle-5.3-bin.zip
复制代码
查看官方文档
热更新使用指南 - Bugly 文档 (qq.com) 1.0版本的接入文档 挺久没更新了
查看官方Demo
BuglyDevTeam/Bugly-Android-Demo: Bugly Android SDK 使用例子 (github.com) 最近更新时间 2021年6月四日更新
第一步:添加插件依赖
buildscript {
repositories {
google()
jcenter()
maven { url uri('./repo') }
maven { url 'https://developer.huawei.com/repo/'}// 友盟
maven { url 'https://repo1.maven.org/maven2/'}// 友盟
}
dependencies {
classpath ('com.tencent.bugly:tinker-support:1.2.1')
}
}
复制代码
这里把文档里面的tinker - support 版本从1.1.5 提升到了 1.2.1 (gradle检测到有1.2.3 暂未升)Demo是1.2.0
依据更新日志,发现里面有提到。且在1.1.5打patch包时会报以下错误 (为了解决该问题 还需要其他操作 后续再提 )
第二步:集成SDK
在app module的“build.gradle”文件中添加(示例配置)
android {
// recommend
dexOptions {
jumboMode = true
}
kapt {
// recommend
correctErrorTypes true
}
// 默认配置
defaultConfig {
// 开启multidex
multiDexEnabled true
ndk {
// 设置支持的SO库架构
abiFilters 'x86', 'armeabi-v7a', 'x86_64', 'arm64-v8a'//,'armeabi'
}
}
}
dependencies {
// 多dex配置
implementation 'androidx.multidex:multidex:2.0.0'
// 远程仓库集成方式(推荐)
implementation 'com.tencent.bugly:crashreport_upgrade:1.5.0'
implementation 'com.tencent.tinker:tinker-android-lib:1.9.14.10'
implementation 'com.tencent.bugly:nativecrashreport:3.9.0'
// walle(多渠道使用)
// compile 'com.meituan.android.walle:library:1.1.3'
//新增
implementation 'com.tencent.tinker:tinker-android-anno-support:1.9.14.10'
}
复制代码
这里会有一点问题 打包的时候无法找到 tinker.anno 下的文件 。因此 在依赖中新增了anno相关的库 参考 github.com/BuglyDevTea…
在app module的“build.gradle”文件中添加
// 依赖插件脚本
apply from: 'tinker-support.gradle'
复制代码
注:您需要在同级目录下创建tinker-support.gradle这个文件哦。 这里参考的是官方案例
apply plugin: 'com.tencent.bugly.tinker-support'
def bakPath = file("${buildDir}/bakApk/")
/**
* 此处填写每次构建生成的基准包目录
*/
def baseApkDir = "app-0518-14-42-00"
/**
* 对于插件各参数的详细解析请参考,如果没有特殊需求下面的参数都可以不用更改;如果apk需要加固等可以参考具体描述设置参数
*/
tinkerSupport {
// 开启tinker-support插件,默认值true
enable = true
// 指定归档目录,默认值当前module的子目录tinker
autoBackupApkDir = "${bakPath}"
//建议设置true,用户就不用再自己管理tinkerId的命名,插件会为每一次构建的base包自动生成唯一的tinkerId,默认命名规则是versionname.versioncode_时间戳
//具体参考https://github.com/BuglyDevTeam/Bugly-Android-Demo/wiki/Tinker-ID%E8%AF%A5%E6%80%8E%E4%B9%88%E8%AE%BE%E7%BD%AE
autoGenerateTinkerId = true
//tinkerId必须保证唯一性,如果两个base包的tinkerid是一样的,并且都联网激活了,那么后续补丁上传到后台的时候会出现匹配错误
tinkerId = "if autoGenerateTinkerId=true ,no need set here"
// 是否启用覆盖tinkerPatch配置功能,默认值false
// 开启后tinkerPatch配置不生效,即无需添加tinkerPatch
overrideTinkerPatchConfiguration = true
// 编译补丁包时,必需指定基线版本的apk,默认值为空
// 如果为空,则表示不是进行补丁包的编译
// @{link tinkerPatch.oldApk }
baseApk = "${bakPath}/${baseApkDir}/app-release.apk"
// 对应tinker插件applyMapping
baseApkProguardMapping = "${bakPath}/${baseApkDir}/app-release-mapping.txt"
// 对应tinker插件applyResourceMapping
baseApkResourceMapping = "${bakPath}/${baseApkDir}/app-release-R.txt"
// buildAllFlavorsDir = "${bakPath}/${baseApkDir}"
// 是否开启加固模式,默认为false
isProtectedApp = true
enableProxyApplication = false
supportHotplugComponent = true
}
/**
* 一般来说,我们无需对下面的参数做任何的修改
* 对于各参数的详细介绍请参考:
* https://github.com/Tencent/tinker/wiki/Tinker-%E6%8E%A5%E5%85%A5%E6%8C%87%E5%8D%97
*/
tinkerPatch {
//oldApk ="${bakPath}/${appName}/app-debug.apk"
ignoreWarning = false
useSign = true
allowLoaderInAnyDex = true
removeLoaderForAllDex = true
dex {
dexMode = "jar"
pattern = ["classes*.dex"]
loader = []
}
lib {
pattern = ["lib/*/*.so"]
}
res {
pattern = ["res/*", "r/*", "assets/*", "resources.arsc", "AndroidManifest.xml"]
ignoreChange = []
largeModSize = 100
}
packageConfig {
}
sevenZip {
zipArtifact = "com.tencent.mm:SevenZip:1.1.10"
// path = "/usr/local/bin/7za"
}
buildConfig {
keepDexApply = false
//tinkerId = "1.0.1-patch"
//applyMapping = "${bakPath}/${appName}/app-debug-mapping.txt" // 可选,设置mapping文件,建议保持旧apk的proguard混淆方式
//applyResourceMapping = "${bakPath}/${appName}/app-debug-R.txt" // 可选,设置R.txt文件,通过旧apk文件保持ResId的分配
}
}
复制代码
这个文件和官方案例有一点不太一样 在 tinkerPatch{}下 新增了 两行为了解决类不在主dex下问题
allowLoaderInAnyDex = true
removeLoaderForAllDex = true
复制代码
第三步:初始化SDK
enableProxyApplication = false 的情况 这里采用了官方推荐的方式
- 自定义Application
因为之前已经有Application了,因此将原有Application 继承 TinkerApplication
public class BaseApplication extends TinkerApplication {
public BaseApplication() {
super(ShareConstants.TINKER_ENABLE_ALL, "com.example.xxxxxxx.hotfix.BaseTinkerApplicationLike",
"com.tencent.tinker.loader.TinkerLoader", false, true);
}
}
复制代码
注意:这个类集成TinkerApplication类,这里面不做任何操作,所有Application的代码都会放到ApplicationLike继承类当中
参数解析
参数1:tinkerFlags 表示Tinker支持的类型 dex only、library only or all suuport,default: > TINKER_ENABLE_ALL
参数2:delegateClassName Application代理类 这里填写你自定义的ApplicationLike
参数3:loaderClassName Tinker的加载器,使用默认即可
参数4:tinkerLoadVerifyFlag 加载dex或者lib是否验证md5,默认为false
- 将以前的Applicaton配置为继承TinkerApplication的类:
修改AndroidManifest下Application中的
android:name=".app.BaseApplication"
复制代码
- 自定义ApplicationLike
在应用的 com.example.xxxxxxx.hotfix目录下创建 BaseTinkerApplicationLike 。要和 上一步自定义Application下super中的内容对应上
public class BaseTinkerApplicationLike extends DefaultApplicationLike {
public static final String TAG = "Tinker.SampleApplicationLike";
public BaseTinkerApplicationLike(Application application, int tinkerFlags,
boolean tinkerLoadVerifyFlag, long applicationStartElapsedTime,
long applicationStartMillisTime, Intent tinkerResultIntent) {
super(application, tinkerFlags, tinkerLoadVerifyFlag, applicationStartElapsedTime,
applicationStartMillisTime, tinkerResultIntent);
}
@Override
public void onCreate() {
super.onCreate();
// 设置是否开启热更新能力,默认为true
Beta.enableHotfix = true;
// 设置是否自动下载补丁,默认为true
Beta.canAutoDownloadPatch = true;
// 设置是否自动合成补丁,默认为true
Beta.canAutoPatch = true;
// 设置是否提示用户重启,默认为false
Beta.canNotifyUserRestart = true;
+ // 补丁回调接口 里面的内容看你们的交互
Beta.betaPatchListener = new BetaPatchListener() {
@Override
public void onPatchReceived(String patchFile) {
// Toast.makeText(getApplication(), "补丁下载地址" + patchFile, Toast.LENGTH_SHORT).show();
}
@Override
public void onDownloadReceived(long savedLength, long totalLength) {
// Toast.makeText(getApplication(),
// String.format(Locale.getDefault(), "%s %d%%",
// Beta.strNotificationDownloading,
// (int) (totalLength == 0 ? 0 : savedLength * 100 / totalLength)),
// Toast.LENGTH_SHORT).show();
}
@Override
public void onDownloadSuccess(String msg) {
//Toast.makeText(getApplication(), "补丁下载成功", Toast.LENGTH_SHORT).show();
}
@Override
public void onDownloadFailure(String msg) {
//Toast.makeText(getApplication(), "补丁下载失败", Toast.LENGTH_SHORT).show();
}
@Override
public void onApplySuccess(String msg) {
//Toast.makeText(getApplication(), "补丁应用成功", Toast.LENGTH_SHORT).show();
}
@Override
public void onApplyFailure(String msg) {
//Toast.makeText(getApplication(), "补丁应用失败", Toast.LENGTH_SHORT).show();
}
@Override
public void onPatchRollback() {
}
};
// 设置开发设备,默认为false,上传补丁如果下发范围指定为“开发设备”,需要调用此接口来标识开发设备
Bugly.setIsDevelopmentDevice(getApplication(), true);
// 多渠道需求塞入
// String channel = WalleChannelReader.getChannel(getApplication());
// Bugly.setAppChannel(getApplication(), channel);
// 这里实现SDK初始化,appId替换成你的在Bugly平台申请的appId
- Bugly.init(getApplication(), "xxxxxxxxxxx", true);
+ //原来Application下的代码 放在这里 我这里 延后了SDK初始化
+ //XXXXXXXXX.XXXXXXXX.XXXX(getApplication());
}
@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
@Override
public void onBaseContextAttached(Context base) {
super.onBaseContextAttached(base);
// you must install multiDex whatever tinker is installed!
MultiDex.install(base);
// TODO: 安装tinker
Beta.installTinker(this);
}
@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
public void registerActivityLifecycleCallback(
Application.ActivityLifecycleCallbacks callbacks) {
getApplication().registerActivityLifecycleCallbacks(callbacks);
}
@Override
public void onTerminate() {
super.onTerminate();
Beta.unInit();
}
}
复制代码
注意:tinker需要你开启MultiDex,你需要在dependencies中进行配置
compile "com.android.support:multidex:1.0.1"
才可以使用MultiDex.install方法; SampleApplicationLike这个类是Application的代理类,以前所有在Application的实现必须要全部拷贝到这里,在onCreate
方法调用SDK的初始化方法,在onBaseContextAttached
中调用Beta.installTinker(this);
。
第四步:AndroidManifest.xml配置
- 1. 权限配置
<!--Bugly升级SDK权限配置开始-->
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.INTERNET"/>
<!--Bugly升级SDK权限配置结束-->
复制代码
-2. Activity配置
<!-- Bugly升级SDK配置开始 -->
<activity
android:name="com.tencent.bugly.beta.ui.BetaActivity"
android:configChanges="keyboardHidden|orientation|screenSize|locale"
android:theme="@android:style/Theme.Translucent"/>
复制代码
- 3. 配置FileProvider
<!--API 24以上配置-->
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="com.tencent.bugly.hotfix.fileProvider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths"/>
</provider>
复制代码
在res目录新建xml文件夹,创建provider_paths.xml文件如下:
<?xml version="1.0" encoding="utf-8"?>
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<!-- /storage/emulated/0/Download/com.bugly.upgrade.demo/.beta/apk-->
<external-path name="beta_external_path" path="Download/"/>
<!--/storage/emulated/0/Android/data/com.bugly.upgrade.demo/files/apk/-->
<external-path name="beta_external_files_path" path="Android/data/"/>
</paths>
复制代码
这里配置的两个外部存储路径是升级SDK下载的文件可能存在的路径,一定要按照上面格式配置,不然可能会出现错误。
正常配置如上 但是如果Manifest中 发现使用的第三方库也配置同样的FileProvider, 可以通过继承FileProvider类来解决合并冲突的问题,示例如下:
<provider
android:name=".util.XXXXProvider"
android:authorities="${applicationId}.fileProvider"
android:exported="false"
android:grantUriPermissions="true"
tools:replace="name,authorities,exported,grantUriPermissions">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths"
tools:replace="name,resource"/>
</provider>
复制代码
XXXXProvider
class XXXXProvider: FileProvider()
复制代码
第五步:混淆配置
-dontwarn com.tencent.bugly.**
-keep public class com.tencent.bugly.**{*;}
# tinker混淆规则
-dontwarn com.tencent.tinker.**
-keep class com.tencent.tinker.** { *; }
-keep class android.support.**{*;}
# 加了 Annotation 添加一些 Annotation混淆
-keepattributes *Annotation*
-dontwarn com.tencent.tinker.anno.AnnotationProcessor
-keep @com.tencent.tinker.anno.DefaultLifeCycle public class *
-keep public class * extends android.app.Application {
*;
}
-keep public class com.tencent.tinker.entry.ApplicationLifeCycle {
*;
}
-keep public class * implements com.tencent.tinker.entry.ApplicationLifeCycle {
*;
}
-keep public class com.tencent.tinker.loader.TinkerLoader {
*;
}
-keep public class * extends com.tencent.tinker.loader.TinkerLoader {
*;
}
-keep public class com.tencent.tinker.loader.TinkerTestDexLoad {
*;
}
-keep public class com.tencent.tinker.loader.TinkerTestDexLoad {
*;
}
-keep public class com.tencent.tinker.entry.TinkerApplicationInlineFence {
*;
}
#for command line version, we must keep all the loader class to avoid proguard mapping conflict
#your dex.loader pattern here
-keep public class com.tencent.tinker.loader.** {
*;
}
复制代码
# 这里留意一下
-keep class com.xxx.xxxxx.xxxxxx.BaseTinkerApplicationLike {
*;
}
复制代码
如果你使用了support-v4包,你还需要配置以下混淆规则:
-keep class android.support.**{*;}
复制代码
第六步:关闭R8 (推荐)
在gradle.properties 上 关闭R8 即
android.enableR8=false
复制代码
热更修 流程 梳理
- 点击assembleReleas
- 在build 目录下的bakApk 会生成如下目录 里面的内容包含
- release包
- mapping文件
- R文件
-
修复有问题的类 保存
-
修改tinker-support.gradle 文件 并保存
//这理的路径是你有问题的包的目录
def baseApkDir = "app-0518-14-42-00"
复制代码
- 点击tinker-support task 下的 buildTinkerPatchRelease 执行命令
- 会先自动生成以下目录
- 并在以下 目录自动生成 差分包
- 选择patch_signed_7zip.apk这个差分包在bugly官网进行下发
加固包直接对生成的pakApk目录下的release包进行加固就好了
集成相关问题
Tinker Exception:fail to create inline fence instance
这里的话 是 TinkerApplicationInlineFence 没有分到主Dex里 相关可以阅读 这篇文章 (49条消息) Tinker Exception:fail to create inline fence instance及如何把想要的类放到主Dex里_丶下一个天亮的博客-CSDN博客 以及为方法数超过 64K 的应用启用 MultiDex | Android 开发者 | Android Developers (google.cn) Tinker 官方也有对这个有一些注释及文章
解决方法具体操作如下 在android{}中新增以下代码
android {
defaultConfig{
multiDexEnabled true
multiDexKeepProguard file("tinker_multidexkeep.pro")
multiDexKeepFile file("maindexlist.txt")
}
}
复制代码
和 Tinker-support.gradle 同一级目录
tinker_multidexkeep.pro 内容
#tinker multidex keep patterns:
-keep public class * implements com.tencent.tinker.entry.ApplicationLifeCycle {
<init>(...);
void onBaseContextAttached(android.content.Context);
}
-keep public class com.tencent.tinker.entry.ApplicationLifeCycle {
*;
}
-keep public class * extends com.tencent.tinker.loader.TinkerLoader {
<init>(...);
}
-keep public class * extends android.app.Application {
<init>();
void attachBaseContext(android.content.Context);
}
#your dex.loader patterns here
-keep class com.example.gamevoice.app.BaseApplication{
<init>(...);
}
-keep class com.example.gamevoice.hotfix.BaseTinkerApplicationLike {
<init>(...);
}
-keep class com.tencent.tinker.loader.** {
<init>(...);
}
-keep class android.support.test.internal** { *; }
-keep class org.junit.** { *; }
复制代码
maindexlist.txt 内容
com/tencent/tinker/entry/TinkerApplicationInlineFence.class
+//你的Application类
+com/xxxxxxxxxx/xxxxxxxxx/app/BaseApplication.class
+//你的ApplicationLike类
+com/xxxx/xxxxxxxxxxxxxx/hotfix/BaseTinkerApplicationLike.class
com/tencent/tinker/loader/shareutil/ShareResPatchInfo.class
com/tencent/tinker/loader/SystemClassLoaderAdder$V23.class
com/tencent/tinker/loader/hotplug/ActivityStubManager.class
com/tencent/tinker/loader/shareutil/ShareOatUtil$1.class
com/tencent/tinker/loader/shareutil/ShareOatUtil.class
com/tencent/tinker/loader/shareutil/SharePatchFileUtil.class
com/tencent/tinker/loader/shareutil/ShareFileLockHelper.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_04.class
com/tencent/tinker/loader/TinkerDexOptimizer$StreamConsumer$1.class
com/tencent/tinker/loader/TinkerDexLoader.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_06.class
com/tencent/tinker/loader/TinkerDexOptimizer$1.class
com/tencent/tinker/loader/TinkerDexOptimizer$StreamConsumer.class
com/tencent/tinker/loader/hotplug/IncrementComponentManager.class
com/tencent/tinker/loader/AndroidNClassLoader.class
com/tencent/tinker/loader/TinkerResourcesKey.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_09.class
com/tencent/tinker/loader/hotplug/interceptor/ServiceBinderInterceptor.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_07.class
com/tencent/tinker/loader/shareutil/ShareIntentUtil.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_00.class
com/tencent/tinker/loader/TinkerResourcesKey$V24.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_05.class
com/tencent/tinker/loader/TinkerTestAndroidNClassLoader.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_01_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_01_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_01_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_07.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_00_T.class
com/tencent/tinker/loader/hotplug/handler/MHMessageHandler.class
com/tencent/tinker/loader/shareutil/ShareElfFile$SectionHeader.class
com/tencent/tinker/loader/TinkerDexOptimizer$ResultCallback.class
com/tencent/tinker/loader/TinkerResourceLoader.class
com/tencent/tinker/loader/SystemClassLoaderAdder$V19.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_06.class
com/tencent/tinker/loader/hotplug/interceptor/ServiceBinderInterceptor$1.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_08.class
com/tencent/tinker/loader/hotplug/interceptor/ServiceBinderInterceptor$BinderInvocationHandler.class
com/tencent/tinker/loader/shareutil/ShareResPatchInfo$LargeModeInfo.class
com/tencent/tinker/loader/hotplug/ActivityStubs.class
com/tencent/tinker/loader/hotplug/interceptor/TinkerHackInstrumentation.class
com/tencent/tinker/loader/TinkerResourcesKey$V19.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_02.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_09.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_00.class
com/tencent/tinker/loader/shareutil/ShareElfFile$1.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_02_T.class
com/tencent/tinker/loader/TinkerTestDexLoad.class
com/tencent/tinker/loader/shareutil/ShareElfFile$ProgramHeader.class
com/tencent/tinker/loader/TinkerSoLoader.class
com/tencent/tinker/loader/hotplug/interceptor/HandlerMessageInterceptor$CallbackWrapper.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_01_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_08.class
com/tencent/tinker/loader/shareutil/ShareElfFile$ElfHeader.class
com/tencent/tinker/loader/TinkerResourcePatcher.class
com/tencent/tinker/loader/shareutil/ShareTinkerInternals.class
com/tencent/tinker/loader/hotplug/ComponentHotplug.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_07.class
com/tencent/tinker/loader/TinkerDexOptimizer$OptimizeWorker.class
com/tencent/tinker/loader/hotplug/interceptor/InterceptFailedException.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_01.class
com/tencent/tinker/loader/BuildConfig.class
com/tencent/tinker/loader/TinkerLoader.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_03.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_01.class
com/tencent/tinker/loader/SystemClassLoaderAdder$V4.class
com/tencent/tinker/loader/hotplug/interceptor/Interceptor$ITinkerHotplugProxy.class
com/tencent/tinker/loader/shareutil/ShareSecurityCheck.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_09.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_00.class
com/tencent/tinker/loader/hotplug/interceptor/ServiceBinderInterceptor$FakeInterfaceHandler.class
com/tencent/tinker/loader/SystemClassLoaderAdder.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_08.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_06.class
com/tencent/tinker/loader/TinkerResourcesKey$V17.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_00.class
com/tencent/tinker/loader/hotplug/interceptor/HandlerMessageInterceptor.class
com/tencent/tinker/loader/shareutil/ShareBsDiffPatchInfo.class
com/tencent/tinker/loader/shareutil/ShareReflectUtil.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_00_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_00_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_02.class
com/tencent/tinker/loader/TinkerUncaughtHandler.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_02_T.class
com/tencent/tinker/loader/TinkerDexOptimizer.class
com/tencent/tinker/loader/shareutil/ShareConstants.class
com/tencent/tinker/loader/shareutil/SharePatchInfo.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_09.class
com/tencent/tinker/loader/hotplug/handler/PMSInterceptHandler.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_05.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_03.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_01.class
com/tencent/tinker/loader/SystemClassLoaderAdder$V14.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_03.class
com/tencent/tinker/loader/hotplug/IncrementComponentManager$AttrTranslator.class
com/tencent/tinker/loader/shareutil/ShareOatUtil$InstructionSet.class
com/tencent/tinker/loader/app/TinkerApplication.class
com/tencent/tinker/loader/hotplug/interceptor/ServiceBinderInterceptor$FakeClientBinderHandler.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_02.class
com/tencent/tinker/loader/hotplug/UnsupportedEnvironmentException.class
com/tencent/tinker/loader/TinkerRuntimeException.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_04.class
com/tencent/tinker/loader/hotplug/interceptor/HandlerMessageInterceptor$MessageHandler.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_06.class
com/tencent/tinker/loader/TinkerDexLoader$1.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_00_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_02_T.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_04.class
com/tencent/tinker/loader/hotplug/IncrementComponentManager$1.class
com/tencent/tinker/loader/hotplug/EnvConsts.class
com/tencent/tinker/loader/hotplug/handler/AMSInterceptHandler.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_05.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_03.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_02.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_07.class
com/tencent/tinker/loader/hotplug/ActivityStubs$STDStub_05.class
com/tencent/tinker/loader/AbstractTinkerLoader.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_02_T.class
com/tencent/tinker/loader/SystemClassLoaderAdder$1.class
com/tencent/tinker/loader/TinkerResourcesKey$V7.class
com/tencent/tinker/loader/shareutil/ShareDexDiffPatchInfo.class
com/tencent/tinker/loader/shareutil/ShareElfFile.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTKStub_08.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SGTStub_04.class
com/tencent/tinker/loader/hotplug/interceptor/Interceptor.class
com/tencent/tinker/loader/hotplug/ActivityStubs$SIStub_01.class
com/tencent/tinker/build/decoder/ApkDecoder.class
com/tencent/tinker/build/patch/Runner.class
com/tencent/tinker/loader/R.class
复制代码
打差分包的时候会出现 loader classes are found in old secondary dex. Found classes:
ignoreWarning is false, but we found loader classes are found in old secondary dex
复制代码
然后在tinker 和 bugly的 issue 中 找到了 以下相关文章
解决方式
tinker-support.gradle 文件上新增以下代码
tinkerPatch {
+ allowLoaderInAnyDex = true
+ removeLoaderForAllDex = true
}
复制代码
Illegal invoke-super to void androidx.appcompat.widget.AbsActionBarView.onDetachedFromWindow() from class androidx.appcompat.widget.ActionBarContextView
TinkerPatchException:调用了没有加载的类XmlPullParser导致打补丁包失败 · Issue #1580 · Tencent/tinker (github.com)
解决方式
然后在gradle.properties 上 关闭R8 即
android.enableR8=false
复制代码