Android热更新初探,Bugly热更新的集成和使用

来源:互联网 发布:nodejs配合什么数据库 编辑:程序博客网 时间:2024/05/16 11:34


今日科技快讯


美国今日传出媒体并购案,默多克旗下的21世纪福克斯电影及电视部分资产出售给迪斯尼,并购资金额高达524亿美元,略低于之前传闻的600亿美元。此次收购福克斯的竞争对手有亚马逊,索尼,Verizon,康卡斯特等,随着价格抬高,只有迪士尼坚持到了最后。


作者简介


本篇文章来自 chaychan 的投稿。简单介绍了腾讯 Bugly 服务,分享了如何集成热更新SDK,希望对大家有所帮助! 

chaychan  的博客地址:

http://www.jianshu.com/u/275ef936c427


介绍


在介绍 Bugly 之前,需要先向大家简单介绍下一些热更新的相关内容。当前市面的热补丁方案有很多,其中比较出名的有阿里的 AndFix、美团的 Robust 以及QZone的超级补丁方案。但它们都存在无法解决的问题,这也是 Tinker 面世的原因。Tinker 目前已运行在微信的数亿Android设备上,相对于其它热更新方案,Tinker 相对比较优秀。


什么是Tinker


Tinker 是微信官方的 Android热补丁 解决方案,它支持动态下发代码、So库以及资源,让应用能够在不需要重新安装的情况下实现更新。当然,你也可以使用 Tinker 来更新你的插件。

总的来说:

1. AndFix 作为 native 解决方案,首先面临的是稳定性与兼容性问题,更重要的是它无法实现类替换,它是需要大量额外的开发成本的;

2. Robust 兼容性与成功率较高,但是它与 AndFix 一样,无法新增变量与类只能用做的 bugFix 方案;

3. Qzone方案 可以做到发布产品功能,但是它主要问题是插桩带来 Dalvik 的性能问题,以及为了解决Art下内存地址问题而导致补丁包急速增大的。


Tinker的已知问题


1. Tinker 不支持修改 AndroidManifest.xml,Tinker 不支持新增四大组件(1.9.0支持新增非 export 的 Activity);

2. 由于 Google Play 的开发者条款限制,不建议在GP渠道动态更新代码。在Android N上,补丁对应用启动时间有轻微的影响;

3. 不支持部分三星 android-21 机型,加载补丁时会主动抛出"TinkerRuntimeException:checkDexInstall failed";

4. 对于资源替换,不支持修改 remoteView。例如 transition 动画,notification icon 以及桌面图标。


Tinker更多介绍


对于tinker的详细介绍,感兴趣的可以前往查看,地址:

https://github.com/Tencent/tinker/wiki


Bugly的介绍


腾讯 Bugly,是腾讯公司为移动开发者开放的服务之一,面向移动开发者提供专业的 Crash 监控、崩溃分析等质量跟踪服务。Bugly 能帮助移动互联网开发者更及时地发现掌控异常,更全面的了解定位异常,更高效的修复解决异常。

Bugly 目前包括三大服务:

1. 异常上报;

2. 运营统计; 

3. 应用升级(包括全量升级和热更新)。


Bugly的热更新


热更新能力是 Bugly 为解决开发者紧急修复线上bug,而无需重新发版让用户无感知就能把问题修复的一项能力。Bugly 目前采用微信 Tinker 的开源方案,开发者只需要集成我们提供的SDK就可以实现自动下载补丁包、合成、并应用补丁的功能,我们也提供了热更新管理后台让开发者对每个版本补丁进行管理。


为什么使用Bugly热更新


  • 无需关注Tinker是如何合成补丁的

  • 无需自己搭建补丁管理后台

  • 无需考虑后台下发补丁策略的任何事情

  • 无需考虑补丁下载合成的时机,处理后台下发的策略

  • Bugly提供了更加方便集成Tinker的方式

  • Bugly通过HTTPS及签名校验等机制保障补丁下发的安全性

  • 丰富的下发维度控制,有效控制补丁影响范围

  • Bugly提供了应用升级一站式解决方案


Bugly热更新SDK的集成


集成 Bugly 热更新的详细操作可以参考官网的文档:

https://bugly.qq.com/docs/user-guide/instruction-manual-android-hotfix/?v=20171109131920

在这里就不一步一步地结合如何集成SDK,总的来说有一下几个步骤:

1. 工程根目录 build.gradle 添加 tinker-support 插件依赖;

2. app module 的 build.gradle 添加SDK依赖;

3. 在app目录下新建 tinker-support.gradle 文件,文件的内容文档有提供;

4. 初始化 SDK,改造 application,虽然也可以不改造 application,但是兼容性可能会出现问题,官方推荐改造 application;

5. AndroidManifest.xml 配置相关权限,如果仅仅只是使用热更新而不需要使用到全量升级功能,不需要配置 BetaActivity 和 FileProvider。

6. 混淆配置,在 proguard-rules.pro 文件中添加Bugly的混淆规则。

集成热更新所遇到的相关问题:

  • 文档中提及使用插件的最新版本可以通过使用 lastest.release 拉取,如图:

但我添加依赖的时候,如下:

buildscript {     repositories {         jcenter()     }     dependencies {         // tinkersupport插件, 其中lastest.release指拉取最新版本,也可以指定明确版本号,例如1.0.4         classpath "com.tencent.bugly:tinker-support:lastest.release"     } }

报了找不到该依赖的错误,原来是文档写错了,lastest 应改成 latest 才对。

  • tinker-support.gradle 中缺少 supportHotplugComponent 这项配置导致打补丁包的时候出现错误

视频介绍和文档中都没有提及到 tinker-support.gradle 文件 tinkerSupport { } 中需要添加多 supportHotplugComponent 这项配置,按照文档来打补丁的时候,会出现如下错误:

看了错误提示,老是提示我说 manifest was changed,可是我根本没有改动到 manifest,一直很纳闷,直到看了 demo 后,才发现需要在 tinkerSupport { } 中,添加 supportHotplugComponent 这项配置,代码如下:

tinkerSupport {      ...     supportHotplugComponent = true
}
  • thinkerId 的指定

thinkerId 需要是唯一的,在生成基准包和补丁包时都需要改动,官方推荐时间用git版本号或版本名生成,这里我自己使用的是 versionName_MM-dd-HH-mm-ss 这种格式,版本名+时间戳,比如1.0.5-1121-11-33-20,这和 bakApk 下生成基准包目录的时间戳类似,它是app-1121-11-33-20,这样查看起来一路了然,查看补丁包的YAPATCH文件也很清晰:

Created-Time: 2017-11-21 11:37:15.673
Created-By: YaFix(1.1) YaPatchType: 2
VersionName: 1.0.5
VersionCode: 5
From: 1.0.5-1121-11-36-06
To: 1.0.5-1121-11-37-15

From 是基准包的tinkerId;To 是当前补丁包的 tinkerId

生成上述格式 tinkerId 的代码如下:

tinkerSupport {      ...     tinkerId = "${verName()}-${buildTime()}"     ... } //获取版本名
def verName() {    def versionPropsFile = file("../version.properties")    if (versionPropsFile.canRead()) {        Properties versionProps = new Properties()        versionProps.load(new FileInputStream(versionPropsFile))        return versionProps['VERSION_NAME']    } else {        throw new GradleException("Could not read gradle.properties")    } } //获取构建时间
def buildTime()
{    return new Date().format("MMdd-HH-mm-ss", TimeZone.getTimeZone("GMT+8")) }

需要在工程根目录下,和 gradle.properties 文件同目录下,新建 version.properties 文件,用于保存当前 app 的 versionCode 和 versionName,文件的内容:

VERSION_NAME=1.0.5
VERSION_CODE=4

既然将 versionCode 和 versionName 配置在 properties 文件中,那么 app module 的 gradle 文件中,defaultConfig{} 中指定版本名和版本号直接使用该配置

android {     ...     defaultConfig {         ...         versionCode verCode()         versionName verName()        ...     } }

获取版本号的方法 verCode(),代码如下:

//获取版本号
def verCode() {    def versionPropsFile = file("../version.properties")    if (versionPropsFile.canRead()) {        Properties versionProps = new Properties()        versionProps.load(new FileInputStream(versionPropsFile))        def int verCode = versionProps['VERSION_CODE'].toInteger()        return verCode;    } else {        throw new GradleException("Could not read gradle.properties")    } }


Bugly Q&A


到这里 Bugly 热更新的相关介绍就到此为止了,在这里向大家简单介绍了 Bugly 集成是使用中遇到的问题和相关的建议,官方也提供了常见问题解决的介绍:

Bugly Android 热更新常见问题

https://link.jianshu.com/?t=https://bugly.qq.com/docs/user-guide/faq-android-hotfix/?v=20171109131920

如果里面找不到你想要的,可以联系他们的客服的QQ,但是客服几乎不回答,有点无奈,客服QQ自动回复推荐去他们的论坛留言,可是发现该论坛禁止注册了,有点悲催。几番波折后,终于在他们的新浪微博上找到了希望:

发现了他们提供技术支持的QQ讨论群,群号为: 130979883,现在已经加入了群里,向 Bugly 的技术人员询问了自己的相关疑问。

Demo源码

https://github.com/chaychan/BuglyHotFixDemo


欢迎长按下图 -> 识别图中二维码

或者 扫一扫 关注我的公众号

原创粉丝点击