Android热修复(一):Tinker的使用(一)命令行接入

介绍

    Tinker是微信官方的Android热补丁解决方案,它支持动态下发代码、So库以及资源,让应用能够在不需要重新安装的情况下实现更新。当然,你也可以使用Tinker来更新你的插件。
    它主要包括以下几个部分:
        gradle编译插件(主要是为了帮助我们在Android Studio直接生成patch文件): tinker-patch-gradle-plugin
        核心sdk库(tinker为用户提供的所有的api): tinker-android-lib
        非gradle编译用户的命令行版本(主要是为了使用命令行来生成patch文件): tinker-patch-cli.jar
    现在有许多热修复方案,比如说我上次介绍的阿里的AndFix,美团的Robust,QQ空间的超级补丁方案,那么我们为什么还要去学习Tinker呢?Tinker的优势在哪里呢?

这里写图片描述
总的来说:
1、AndFix作为native解决方案,首先面临的是稳定性与兼容性问题,更重要的是它无法实现类替换,它是需要大量额外的开发成本的;
2、Robust兼容性与成功率较高,但是它与AndFix一样,无法新增变量与类只能用做的bugFix方案;
3、Qzone方案可以做到发布产品功能,但是它主要问题是插桩带来Dalvik的性能问题,以及为了解决Art下内存地址问题而导致补丁包急速增大的。

Tinker的集成

添加依赖

    //自定义注解库  生成application时使用
    provided 'com.tencent.tinker:tinker-android-anno:1.7.7'
    //tinker核心库
    compile 'com.tencent.tinker:tinker-android-lib:1.7.7'
    //支持分包,不需要分包可以不导入
    compile 'com.android.support:multidex:1.0.1'

Tinker初始化

    //判断是否安装(初始化)tinker
    private static boolean isInstalled = false;
    private static ApplicationLike mAppLike;
    ......
        //初始化tinker
    public static void installTinker(ApplicationLike applicationLike){
        mAppLike = applicationLike;
        if(isInstalled){
            return;
        }else {
            TinkerInstaller.install(applicationLike);
            isInstalled = true;
        }
    }
    Tinker不能直接调用它的初始化方法,而是需要在ApplicationLike中去使用。先创建一个ApplicationLike的类,然后在onBaseContextAttached()方法中去调用它的初始化方法。
@DefaultLifeCycle(application = ".MyApplication", flags = ShareConstants.TINKER_ENABLE_ALL,
        loadVerifyFlag = false)
public class CustomTinkerLike extends ApplicationLike {
    public CustomTinkerLike(Application application, int tinkerFlags, boolean tinkerLoadVerifyFlag,
                            long applicationStartElapsedTime, long applicationStartMillisTime,
                            Intent tinkerResultIntent) {
        super(application, tinkerFlags, tinkerLoadVerifyFlag, applicationStartElapsedTime,
                applicationStartMillisTime, tinkerResultIntent);
    }

    @Override
    public void onBaseContextAttached(Context base) {
        super.onBaseContextAttached(base);

        //使用multidex,使应用支持分包
        MultiDex.install(base);

        //初始化tinker
        TinkerPatchManager.installTinker(this);
    }
}
    然后rebuild一下项目,然后就会生成MyApplication.

这里写图片描述
可以在manifest来使用这个application

Patch文件的加载

    //加载patch
    public static void loadPatch(String path){
        if(Tinker.isTinkerInstalled()){
            TinkerInstaller.onReceiveUpgradePatch(getApplicationContext(),path);
        }
    }

    //通过ApplicationLink获取Context
    private static Context getApplicationContext(){
        if(mAppLike != null){
            return mAppLike.getApplication().getApplicationContext();
        }

        return null;
    }

Tinker的使用

    首先和上篇AndFix的使用一样,我们首先构建出存放patch文件的路径,即我们要加载的patch文件的路径。
    //patch文件后缀名
    private static final String FILE_END = ".apk";
    //patch文件的路径
    private String mPatchDir;
    ......
    mPatchDir = getExternalCacheDir().getAbsolutePath() + "/tpatch/";
    Log.v("xq_msg", "path: " + mPatchDir);
    //创建文件夹
    File file = new File(mPatchDir);
    if (file == null || !file.exists()) {
        file.mkdir();
    }
    ......
    //构造patch文件名
    private String getPatchName() {
        return mPatchDir.concat("xq_sq").concat(FILE_END);
    }
    然后写一个按钮来调用我们加载patch文件的方法
    //加载patch
    public void loadPatch(View view) {
        TinkerPatchManager.loadPatch(getPatchName());
    }
    再在我们的Manifest文件中添加
    //用来判断这个patch文件是否能加载到我们的手机当中,只有当patch文件的id和我们手机中的apk的id一致才能加载
     <meta-data
            android:name="TINKER_ID"
            android:value="tinker_id_1"/>
    接着打出老的apk(签名版),先保存一份(我们后面还需要用它来生成patch文件),再安装到手机中。我们再修改一下代码(例如我们修改一下布局,增加一个按钮,然后打包,打出新的apk)

生成patch文件(使用命令行)

    首先我们需要先下载命令行工具(链接在文章末尾),它主要包括下图圈出来的几个部分,其他是我们生成命令行需要的一些文件

这里写图片描述

    然后我们需要去修改tinker_config.xml文件的2个地方,如下图所示,一个是loader,我们需要改成我们的application的全路径,一个是最下面的签名文件的一个配置

这里写图片描述

     然后我们就可以使用我们的命令来生成我们的patch文件了。
    java -jar tinker-patch-cli.jar -old old.apk -new new.apk -config tinker_config.xml -out output_path
    我们对应修改一些来执行我们的命令
java -jar tinker-patch-cli-1.7.7.jar -old tinker_old.apk -new tinker_new.apk -config tinker_config.xml -out output/

这里写图片描述

    然后我们可以在我们的output文件夹中去找到我们的生成的patche文件

这里写图片描述

    我们需要的就是这签名了patch文件,然后我们使用adb命令来将这个文件push到我们代码中对应的目录下,然后点击loadPatch按钮,应用自动重启,再次打开我们会发现,我们新增的按钮已经出现了。这个使用命令行来接入Tinker与我们上次讲到的AndFix的使用是没有太大的区别。但是我们在实际项目中都是使用配置gradle文件来使用我们的Tinker的,这个我们在后续的文章中也会讲到具体的是怎么使用配置gradle文件使用Tinker的。

源码下载地址和命令行工具的下载地址

源码及下载工具

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值