在这里先给大家拜个晚年,虽然说新已经过了。本文是今天第一篇文章,已经有好长时间没总结了,算了给2017开个好头吧。之前一直搞不懂什么是热修复?其实热修复就是在应用不用重新安装的情况下更新应用。最多的应用场景就是用来修复bug。因为重新发包的代价太大了,所以我们可以选择用热修复来修复bug!需要注意的一点是Tinker在1.7.6版本以及之后的版本不支持加固后的动态更新,所以用了这个就不用用其他厂商的加固服务,只能使用so文件等更安全的方式来使应用更安全!在这里附上官网指南:https://github.com/Tencent/tinker/wiki
一、添加gradle依懒
在项目build.gradle中添加以下代码
dependencies { classpath 'com.android.tools.build:gradle:2.2.0' //tinker依懒 classpath "com.tencent.tinker:tinker-patch-gradle-plugin:${TINKER_VERSION}" // NOTE: Do not place your application dependencies here; they belong // in the individual module build.gradle files }别忘了还要在项目的gradle.PRoperties中添加以下变量TINKER_VERSION=1.7.7然后在app/build.gradle中添加从Tinker模板(点击去复制代码)中拷贝代码到里面去
当配置完成,点击Sync Now,bug就出来了,这是大部分人会遇到的问题!如下图
出现这个问题的原因是没有正确的配置ide的git路径(官方解释),不过我配置了还是不行!这里最简单的办法就是给它设置一个值,如下图
二,编写生成Application的类,因为SimpleTinkerInApplicationLike会在编译期生成SimpleTinkerInApplication。
@DefaultLifeCycle(application = ".SimpleTinkerInApplication", flags = ShareConstants.TINKER_ENABLE_ALL, loadVerifyFlag = false)public class SimpleTinkerInApplicationLike extends ApplicationLike { public SimpleTinkerInApplicationLike(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); } @Override public void onCreate() { super.onCreate(); TinkerInstaller.install(this); }}别忘了添加到清单文件里去
<application android:name=".SimpleTinkerInApplication" android:allowBackup="true" android:icon="@mipmap/ic_launcher" android:label="@string/app_name" android:supportsRtl="true" android:theme="@style/APPTheme"> <activity android:name=".MainActivity"> <intent-filter> <action android:name="android.intent.action.MAIN"/> <category android:name="android.intent.category.LAUNCHER"/> </intent-filter> </activity> </application>三、编写MainActivity,很简单,就一行代码public class MainActivity extends AppCompatActivity { private TextView mTextView; private Button mButton; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); mTextView = (TextView) findViewById(R.id.tv); mButton = (Button) findViewById(R.id.btn);// mTextView.setText("这不是bug"); mButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { TinkerInstaller.onReceiveUpgradePatch(getApplicationContext(), Environment.getExternalStorageDirectory().getAbsolutePath() + "/patch_signed_7zip.apk");//等下要push到SD卡里面去apk,以达到更新的目的 } }); }}xml文件如下<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/activity_main" android:layout_width="match_parent" android:layout_height="match_parent" android:paddingBottom="@dimen/activity_vertical_margin" android:paddingLeft="@dimen/activity_horizontal_margin" android:paddingRight="@dimen/activity_horizontal_margin" android:paddingTop="@dimen/activity_vertical_margin" tools:context="com.kuyue.tinkertest.MainActivity" android:orientation="vertical" android:gravity="center"> <TextView android:id="@+id/tv" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="这是个bug"/> <Button android:id="@+id/btn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="点我修复bug"/></LinearLayout>四,安装“有bug”的应用
这里不能直接点运行,要选择assembleDebug。这时会在app/build/bakApk下生成编译好的安装包(编译时会报错,需要把debug时的签名文件放到相应路径里面,一般我们debug不需要签名文件,所以只需要把与debug签名相关的代码注释即可),然后将该安装包安装到手机上。可以使用adb命令将安装包安装到手机。如果应用已经在手机上已经安装了,那么就要使用这个命令。(如果提示不是内部命令则需要将adb.exe所在的文件地址添加到电脑的系统变量Path里面去)
没有在手机上安装过的则使用这个命令:adb install app/build/bakApk/app-debug-0207-10-35-25.apk。
安装成功之后,打开应用,出现如下的界面,很简单的界面!
五、生成补丁包及修复“bug”
将MainActivity里面注释掉的代码放出来,没错,就是“这不是bug”那一句!
然后需要将上一步生成的安装包的路径拷到oldApk参数里面去
双击tinkerPatchDebug任务
任务完成后,会在/build/outputs/tinkerPatch/生成补丁包,然后我们需要将patch_signed_7zip.apk推送到sd卡的中。
adb push ./app/build/outputs/tinkerPatch/debug/patch_signed_7zip.apk /storage/sdcard0/有可能会报Permission denied错误,目前没有解决,可以选择直接复制到手机sdcard的主目录。推送完成之后,则点击“点我修复BUG”按钮,应用自动退出,观察log,log会打印提示更新成功,再次启动应用,见证奇迹的时候到了,这时候bug已经不见了!
到这里,接入的流程基本完成了。不知道大家发现一个问题没有,那我怎么知道应用更新补丁成功?并且也不能让应用自动退出啊!这样的用户体验太差了。所以我们需要解更新完补丁后应用自动退出和监听补丁更新完的问题!需要解决这样的问题,可以参考Tinker官网的demo,添加一个service:SampleResultService。
六、打release包
步骤类似上面的四,不过这里要将里面的keystore配置更改成自己的,然后再双击assembleRelease任务,编译成功之后会在bakApk里面生成相应的文件,然后再将这三个文件的路径添加到grale里面,如下图
然后再双击tinkerPatchRelease任务,和上面的debug一样,会生成patch_signed_7zip.apk补丁包!剩下的就和debug的一样了!
最后放上github地址:https://github.com/kuyue/TinkerTest/tree/master
新闻热点
疑难解答