Android Apply Changes 源码 Deployer 解析
Android, Android 编译  ·  
源码链接
一般代码直接看 studio-master-dev 分支就好,此处为了溯源指定了具体 commit。
功能:
IDE 上面的三个按钮对应三个方法
Run -> Deployer::install
Apply Code Changes -> Deployer::codeSwap
Apply Changes and Restart Activity -> Deployer::fullSwap
参数分析:
Deployer::install
/**
* 对应 IDE 中的 Run 按钮。
*
* @param packageName 包名
* @param apks 待安装的 apk 文件列表
* @param options 设置 adb install 的参数
* @param installMode 安装模式,分为三种:发送整个 APK 安装;只发送变化部分进行安装,只发送变化部分进行安装且如果 APK 无变化也不跳过安装
*/
public Result install(String packageName, List<String> apks, InstallOptions options, InstallMode installMode)
Deployer::codeSwap
/**
* 对应 IDE 中的 Apply Code Changes 按钮。
*
* @param apks 待安装的 apk 文件列表
* @param redefiners 类重定义实现类。从源码来看,主要是未 debug attached 时传入 DebuggerRedefiner,其他情况传入empty map
*/
public Result codeSwap(List<String> apks, Map<Integer, ClassRedefiner> redefiners)
Deployer::fullSwap
/**
* 对应 IDE 中的 Apply Changes and Restart Activity 按钮。
* 对比可以发现,fullSwap 和 codeSwap 区别只有两点:
* 1. 是否支持传入 redefiners(codeSwap 支持,fullSwap 不支持)
* 2. 是否重启 Activity(codeSwap 不重启,fullSwap 重启)
*
* @param apks 待安装的 apk 文件列表
*/
public Result fullSwap(List<String> apks)
流程分析
版本区别
- Android 11 以上 supportsNewPipeline = true
- Android 11 支持新的 swap 流程 optimisticSwap
- optimistic 意思是“乐观的”,流程中 optimisticSwap 会假设部署 cache 是正确的,以减少设备通信数据量,从而提高 swap 效率
- optimisticSwap 支持资源更新
Deployer::install
调用 ApkInstaller 安装 apk,如果设备 supportsNewPipeline,则讲 apk 录入到数据库中,用于后续 codeSwap 和 fullSwap
Deployer::codeSwap
如果支持 supportsNewPipeline 且开启 useOptimisticResourceSwap,则调用 optimisticSwap;否则调用 swap
Deployer::fullSwap
如果支持 supportsNewPipeline 且开启 useOptimisticResourceSwap,则调用 optimisticSwap;否则调用 swap
fullSwap 和 codeSwap 区别只有两点:
- 是否支持传入 redefiners
- 是否重启 Activity(codeSwap 不重启,fullSwap 重启)
Deployer::swap
runner.create 会将创建的 Task 加入队列,随后调用 run/runAsync 时会将任务队列拷贝一份然后清空,然后按顺序执行拷贝的任务队列。
Task 命名方式是以 Task 运行完后返回的结果命名
- paths: (参数)Apk 路径
- restart: 重启
- splitter: (参数)拆分 Dex 实现类 CachedDexSplitter
- newFiles: 解析新 apk 的 zip entries
- dumps: 从设备上拉取已安装的同包名 apk 的 zip entries
- diffs: 对以上两个列表做 diff,得出变更文件的列表
- sessionId: 通过 ApkPreInstaller 安装 apk
- dexDiffs: 过滤掉不支持 swap 的文件
- toSwap: 比较本地和设备上的 dex 文件,根据文件列表 dexDiffs 验证是否支持 apply changes(是否改动 dex,资源之外的内容),如果不支持则退出。不支持的情况如:新增了类,改变了方法签名等。
- swapper: 开始 swap dex 和资源
- (如果成功)CACHE, DEPLOY_CACHE_STORE: 异步将变更文件列表存储在数据库
Deployer::optimisticSwap
- paths: (参数)Apk 路径
- restart: 重启任务
- splitter: (参数)拆分 Dex 实现
- newFiles: 解析新 apk 的 zip entries
- packageName,pids,arch,获取包名,进程 id,架构
- speculativeDump: 从设备上拉取已安装的同包名 apk 的 zip entries,假设本地 cache 是正确的
- dumper: (参数)ApplicationDumper
- verifyDump: 校验拉取的 apk 的 zip entries
- diffs: 对以上两个列表做 diff,得出变更文件的列表,并推测本地 cache 是正确性
- extractedFiles: 解压 apk 的res 和 assets 资源
- dexDiffs: 过滤掉不支持 swap 的文件
- changedClasses: 比较本地和设备上的 dex 文件,根据文件列表 dexDiffs 验证是否支持 apply changes(是否改动 dex,资源之外的内容),如果不支持则退出。不支持的情况如:新增了类,改变了方法签名等。
- swapper: 开始 swap dex 和资源
- overlayUpdate: 收集更新资源列表
- nextOverlayId: 更新资源
- (如果成功)CACHE, DEPLOY_CACHE_STORE: 异步将变更文件列表存储在数据库
可以看到 optimisticSwap 和 swap 区别是:
- 从设备拉取变更文件列表的流程不同了
- 支持资源 overlay
附录
参考资料:Android Studio Apply Changes
版权所有,转载请注明出处:
https://sickworm.com/?p=1861