Android Studio Instant Run的工作原理

首先说明一下,本文算不上严格意义的翻译,因此没有归档到译文类别。本文的主要内容及插图均来自《Instant Run: How Does it Work?!》一文,文末会附上此文地址。

Instant Run是Android Studio2.0以上版本引入的一个新特性,它可以显著地减少应用编译及部署的时间。

Instant Run是一个神奇的功能,为什么这么说呢?当第一次你点击run或debug按钮的时候,跟正常的编译部署流程是一样的;当你对代码做了一些修改,然后再次点击run或debug按钮(这时旁边会出现一个⚡标志),接下来就是见证奇迹的时候了,你甚至还没来得及将注意力从Android Studio转移到手机上来,应用已经编译部署好了,这就是它的神奇之处。

接下来就是了解Instant Run的工作原理了,这里有一个官方视频连接:Instant Run:An Android Tool Time Deep Dive,有兴趣的朋友可以直接点开看。

Instant Run的特点

这里写图片描述

上图为应用程序一般的编译和部署过程:

  1. 编译
  2. 部署安装
  3. App启动
  4. Activity启动

经过以上几个步骤之后才能看到代码修改的效果。

对比通用的编译部署过程,Instant Run的目标就很清晰了:

  1. 尽可能去掉上述过程中不必要的步骤
  2. 让剩下的必要步骤越快越好

上述两点在实际中表现为:

  • 仅对增量和变化做编译和部署
  • 尽量不要重新安装App
  • 尽量不要重启App
  • 甚至不要重启Activity
Instant Run = Incremental build + Hot, Warm, or Cold swap

这里写图片描述

由上图可知,Instant Run可以理解为增量编译和部署(分为Hot Swap、Warm Swap和Cold Swap三种方式)。

Hot Swap:此种方式不需要重启App,甚至不需要重启Activity就能看到代码修改引起的变化,一般适用于某个方法实现中的微小改动,如Toast或某个String字串的内容修改。

Warm Swap:此种方式需要重启Activity才能看到修改导致的变化,经常用于资源相关的代码改变。

Cold Swap:此种方式需要App重启,但并不需要App重新安装,适用于结构性的代码修改如继承关系或方法签名改变。

正常的构建流程

这里写图片描述

Manifest文件会被合并,然后与资源文件一起被AAPT工具打包;同时java文件也被编译为字节码,然后转成dex文件,最终上述文件一起打包成APK。

使用Instant Run的构建流程

这里写图片描述

字节码被添加到.class文件中,同时一个appserver类被注入到APK中。

另外还会添加一个新的Application类定义,它用来注入自定义的类加载器用来调起App Server,因此Manifest也会被修改以便可以使用它。如果你已创建了自己的Application类,Instant Run将会使用新的来代理你的Application。

现在Instant Run就跑起来了,所以当你修改了部分代码,然后再次点击run或者debug时,Instant Run将会使用Hot Swap、Warm Swap或者Cold Swap尽可能地缩短原来的构建过程。

Hot Swapping

这里写图片描述

在开发过程中,Android Studio会监控哪些文件发生了变化,并使用Gradle工具为那些变化的class文件生成dex文件。

这些新的dex文件被Android Studio挑选出来然后部署到我们应用上的App Server上。

由于原始版本的class文件已经存在于运行的App中,Gradle可以高效地将更新的文件替换掉以前的旧文件,这些新文件可以被App Server使用自定义的类加载器加载。

这里写图片描述

随后,每次当应用中的一个方法被调用时,App Server会跟原始文件通信来检查他们是否被更新了。如果是的话,更新文件中的修改过的新方法会被委托来执行。

这里写图片描述

如上图,如果你设了断点你将会看到被覆盖的方法的调用栈情况。

对于方法实现的微小改变,使用重定向方法的方式可以很好地工作,但是某些需要Activity重启才能加载的情况又如何呢?

Warm Swapping

Warm Swap会重启Activity,资源会在Activity启动时加载,因此对资源的修改会要求重启Activity来实现资源的重新加载。

目前,对资源的任何修改将会导致资源重新打包与部署到App,Android Studio的技术人员也在研究资源的增量打包与部署技术。

需要注意的是当Manifest中引用的资源被修改时,或者Manifest文件本身被修改了,Warm Swap并不能工作,因为Manifest中的配置信息是在APK被安装时读取的。对Manifest的修改或其引用到的资源的修改将会触发完整的编译和部署流程。

不幸的是,重启Activity并不能应用于结构变化。添加、删除或者修改注记、静态或实例方法签名,或者修改父类、静态初始化逻辑都将需要Cold Swap方式。

Cold Swapping

应用被部署时会被分割为多个部分,每一部分都有自己的dex文件,class文件根据它们的包名被分配到不同的部分。当使用Cold Swap部署时,一个修改过的类必须与其在同一dex中的其他类一起重新生成dex,然后才能部署到目标设备。

这种方式依赖于multidex机制,仅在Android5.0(API level 21)或更高设备上才支持。

对于低于API level 20的设备而言,使用的是Dalvik模式,因此不支持Instant Run,则会执行完整的APK安装过程。

Instant Run很聪明,但它不能回退

由于Hot Swap和Warm Swap不会重启应用,因此修改某些在应用启动时才会初始化的代码时,必须重启App才能看到对应的效果。

这里写图片描述

其他

Instant Run是由Android Studio控制的,因此要从IDE中启动run或debug,而不是从手机设备中启动或重启应用。

Instant Run目前仅在主线程上支持的最好,因此如果应用使用了多线程,在其他线程上使用Hot Swap与Warm Swap将会降级为Cold Swap,如果API level小于21的话直接转为完整构建与部署。

Instant Run也在不断改进,Android Studio团队也在开发新技术让更多的情况可以支持Hot Swap,减少Cold Swap甚至完整构建,相信Android Studio后面的版本越来越好用。

来源英文文章《Instant Run: How Does it Work?!》

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值