乐趣区

关于android:技术干货-深度解构-Android-应用面临紧急发版时的救星方案mPaaS-热修复DexPatch

计划介绍

为了解决 Native 模块上线后的问题,mPaaS 提供了热修复性能,实现不公布客户端 apk 场景下的热修复。目前 Android 端热修复次要包含 andfix 和 dexpatch,思考到 andfix 的版本兼容性,目前次要举荐应用 DexPatch

DexPatch 修复原理比较简单,就是在启动后通过 RPC 拉取以后须要下发的 jar 包地址,而后通过独立过程去下载 jar 包文件,下载实现后保留。在二次启动的时候 hook 零碎的 classLoader,批改 DexPathList,在其数组的最后面退出一个有批改过的 class 的 dex 文件,使其拦挡住数组前面的 dex 文件中同名的 class 的加载。

如下图所示,classloader 就会优先加载 Patch.dex 中的 Ding.class,而疏忽 Classes.dex 中的 Ding.class,达到了替换的成果。

基于这样的原理,DexPatch 具备以下特色:

  1. 反对范畴上:是基于类级别的替换,所以只反对 Java 模块的 patch,不反对非 Java 模块的 patch,比方 so 模块;
  2. 兼容性上:因为是代理了零碎的 ClassLoader,应用的黑科技较少,所以整体计划兼容性较好;
  3. 失效时效性上:只能在下载 patch 后重启后能力失效,不反对实时失效;
  4. 成功率上:因为下载是应用的独立过程,缩小了启动阶段主过程闪退对 patch 下载的影响,晋升了下载的胜利比例。

操作阐明

以下是对于在 mPaaS 下应用 DexPatch 模块的次要步骤以及问题排查思路,不便开发者日常开发。

1. 触发 patch 拉取

启动阶段调用 MPHotpatch.init(),次要触发 Patch 信息的 RPC 申请,如果命中公布 Patch 公布规定,RPC 会返回 Patch 的 jar 包下载地址,客户端去触发下载,下载后保留在客户端公有目录 /data/user/0/ 包名 /dexpatch/patch/ 下。

2. 代码操作演示

以组件化模式接入为例,介绍下 Patch 公布的次要流程。

(1)代码改变前

须要保留改变前的构建产物,不便后续做 Patch 生成,地址在:build/intermediates/bundle/xxxx-raw.jar

(2)代码改变后

从新编译,保留构建产物,产物地址:build/intermediates/bundle/xxxx-raw.jar

(3)生成白名单配置

次要用于热修复包时用于指定修复的类,配置文件为 .txt 格局,该配置文件应蕴含并按程序蕴含以下信息:
须要 Patch 的类。以 L 结尾,后跟以混同后实在类名。如果多个类,每行只可写一个。示例:Lxxx.xxx.clazzX设置 Patch 类型为 dexpatch。示例:PatchType: dexpatch

设置是否是动态 Bundle。默认为 false,如果是动态链接的 Bundle,须要显式设置为 true。示例:HostDex: true(* 目前 mPaaS 客户端的模块个别都在动态链接里,个别写 true)

(4)查看签名

生成 patch 须要用到我的项目的打包秘钥,须要提前准备好,能够在打包脚步下找到对应的配置

(5)生成 patch

① 通过 mPaaS 自带的 IDE 工具,点击热修复,进入修复页面。

② 依照页面提醒,填入之前筹备的修复前和修复后的 jar 包地址,还有白名单配置文件,勾选 dexPatch,进入到下一步

③ 下一步次要抉择打包的配置文件,最近点击实现生成 patch 文件

(6)生成 patch 产物

生成 patch 产物如下:

查看产物,能够应用 dex2jar 工具反解 diff.dex 文件,用 jd-gui 文件查看反解产物是否合乎预期

反解后能够看到批改的模块:

(7)上传公布

① 抉择上一步的产物 jar 包进行上传

② 上传后能够通过白名单进行公布,验证 patch 的稳定性

(8)验证下载

白名单公布后,启动客户端,搜寻关键字:DynamicRelease,能够看到在 tool 过程有触发下载的日志打出。
这里须要阐明的是,这里触发 patch 的下载是在 tool 过程,不在主过程的次要起因是怕因为主过程因为启动导致反复闪退,导致 patch 不能下载胜利,独自在 tool 过程实现下载,尽量进步 patch 的下载胜利比例。

而后去下载目录查看,是否下载保留胜利,下载目录在:/data/user/0/包名/dexpatch/patch/20201023110012@20201023110012.jar

(9)杀过程启动

确认下载保留胜利后,杀掉 App,重启查看是否失效,重启能够搜寻关键字:DexPatchManager,查看 patch 失效的日志,日志会打印以后是否存在 patch 以及 patch 是否加载的日志。

同时咱们也能够就理论业务场景进行验证,查看是否失效。

常见问题

  1. aar 模式集成后 patch 没失效

aar 模式集成的时候,须要继承框架的 QuinoxlessApplication,指定 Application 为框架的实现类能力实现 dexpatch 的加载。QuinoxlessApplication 内次要封装了 dexpatch 模块的初始化和加载。

  1. 应用加固后不失效

须要应用加固前的 apk 生成 patch,不能用加固后的包生成 patch。而后还须要验证在不同加固厂商下的兼容体现。

  1. 应用热修复后,和 RPC 无关的调用产生 apache http 相干的 crash。

请应用 Android 官网上的形式引入 apache http client,禁止应用导入 jar 包或者 gradle implementation/compile 的形式导入 http client。否则会引起 classloader 加载类凌乱。

倡议形式:

<uses-library android:name="org.apache.http.legacy" android:required="false"/>
`_* 如有更多疑难,欢送钉钉搜寻“32930171”退出「mPaaS 技术交换群」_`


E · N · D


退出移动版