##騰訊Bugly
功能:
1.異常上報(上線后的APP 在用戶手中發(fā)送的bug看不到憎夷,這就用到Bugly丁眼,可以吧bug上傳到后臺供開發(fā)人員觀察并及時修復(fù)bug)
????2.運營統(tǒng)計,可以統(tǒng)計日活躍赴捞,月活躍量,還有使用客戶數(shù)诗力,安裝客戶數(shù)
????3.應(yīng)用升級弟塞,升級功能是轉(zhuǎn)為APP的灰度升級而開發(fā)的組件凭峡,在Bugly內(nèi)側(cè)頁面配置好APP的更新策略,策略指定的老版本APP在啟動時會自動檢測更新并提示升級决记,為團(tuán)隊的應(yīng)用分發(fā)摧冀,灰度內(nèi)側(cè)提供一站式解決方案
????4.熱更新,熱更新能力是Bugly為解決開發(fā)者緊急修復(fù)線上bug系宫,而無需重新發(fā)布新版本索昂,讓用戶無感知就能把問題修復(fù)的一項能力。bugly目前采用微信Tinker的開源方案扩借,開發(fā)者主需要繼承我們提供的SDK就開源實現(xiàn)自動下載補(bǔ)丁包楼镐、合成、并應(yīng)用補(bǔ)丁的功能往枷,我們也提供了熱更新管理后臺框产,讓開發(fā)者對每個版本補(bǔ)丁進(jìn)行管理?
##Bugly集成熱更新
1.申請賬號:HTTPS://bugly.qq.com/
2.完善開發(fā)者信息+創(chuàng)建應(yīng)用(直接提交,不審核错洁,可直接使用)
##參照文檔集成
首先去申請賬號:https://bugly.qq.com/
創(chuàng)建應(yīng)用秉宿,拿到appid后續(xù)會用到
在工程跟目錄下
????????buildscript {
????repositories {
????????google()
????????jcenter()
????}
????dependencies {
????????// tinkersupport插件, 其中l(wèi)astest.release指拉取最新版本,也可以指定明確版本號屯碴,例如1.0.4
???????classpath "com.tencent.bugly:tinker-support:1.1.5"
????}
}
##在導(dǎo)入依賴的Gradle中
defaultConfig {
????????applicationId "com.example.dell.demohotbuglys"
????????minSdkVersion 17
????????targetSdkVersion 27
????????versionCode 1
????????versionName "1.0"
????????testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
????????ndk {
????????????//設(shè)置支持的SO庫架構(gòu)
????????????abiFilters 'armeabi', 'x86' // 'armeabi-v7a', 'x86_64', 'arm64-v8a'
????????}
????????// 開啟multidex
????????multiDexEnabled true
}
// 簽名配置,官方文檔上面沒說,但我們得配置,因為官網(wǎng)不負(fù)責(zé)教你????配置這個,
????signingConfigs {
????????release {
????????????try {
????????????????storeFile file('buglys.jks')
????????????????storePassword "123456"
????????????????keyAlias "key0"
????????????????keyPassword "123456"
????????????} catch (ex) {
????????????????throw new InvalidUserDataException(ex.toString())
????????????}
????????}
????}
????buildTypes {
????????release {
????????????signingConfig signingConfigs.release
????????????minifyEnabled true
????????????proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
????????}
????????debug {
????????????signingConfig signingConfigs.release
????????????minifyEnabled true
????????????proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
????????}
????}
?????在dependencies 中導(dǎo)入下面幾個依賴
????dependencies {
compile "com.android.support:multidex:1.0.1" // 多dex配置
????//其中l(wèi)atest.release指代最新版本號描睦,也可以指定明確的版本號,例如1.3.4
????//包含了crash上報功能
????compile 'com.tencent.bugly:crashreport_upgrade:1.4.0'
????// 指定tinker依賴版本(注:應(yīng)用升級1.3.5版本起导而,不再內(nèi)置tinker)
????compile 'com.tencent.tinker:tinker-android-lib:1.9.9'
????//其中l(wèi)atest.release指代最新版本號忱叭,這里我們指定某個版本
????//compile 'com.tencent.bugly:nativecrashreport:latest.release'
????compile 'com.tencent.bugly:nativecrashreport:3.7.1'
}
在最頂端依賴插件腳本
????// 依賴插件腳本
????apply from: 'tinker-support.gradle'
##在APP下創(chuàng)建tinker-support.gradle這個文件哦(和app module 的 build.gradle同級別)。
apply plugin: 'com.tencent.bugly.tinker-support'
????def bakPath = file("${buildDir}/bakApk/")
????/**
?????6
?????*?此處填寫每次構(gòu)建生成的基準(zhǔn)包目錄,注意每次打補(bǔ)丁包都需要修????改
?????7
?????*/
????def baseApkDir = "app-0611-20-44-04"
????/**
?????11
?????*?對于插件各參數(shù)的詳細(xì)解析請參考
12
*/
????tinkerSupport {
????// 開啟tinker-support插件今艺,默認(rèn)值true
????enable = true
????// 指定歸檔目錄韵丑,默認(rèn)值當(dāng)前module的子目錄tinker
????autoBackupApkDir = "${bakPath}"
????// 是否啟用覆蓋tinkerPatch配置功能,默認(rèn)值false
????// 開啟后tinkerPatch配置不生效虚缎,即無需添加tinkerPatch
????overrideTinkerPatchConfiguration = true
????// 編譯補(bǔ)丁包時撵彻,必需指定基線版本的apk,默認(rèn)值為空
????// 如果為空实牡,則表示不是進(jìn)行補(bǔ)丁包的編譯
????// @{link tinkerPatch.oldApk }
????baseApk = "${bakPath}/${baseApkDir}/app-release.apk"
????// 對應(yīng)tinker插件applyMapping
????baseApkProguardMapping = "${bakPath}/${baseApkDir}/app-release-mapping.txt"
????// 對應(yīng)tinker插件applyResourceMapping
????baseApkResourceMapping = "${bakPath}/${baseApkDir}/app-release-R.txt"
????//建議設(shè)置true,用戶就不用再自己管理tinkerId的命名,插件會為每一次構(gòu)建的base包自動生成唯一的tinkerId陌僵,默認(rèn)命名規(guī)則是versionname.versioncode_時間戳
????//具體參考https://github.com/BuglyDevTeam/Bugly-Android-Demo/wiki/Tinker-ID%E8%AF%A5%E6%80%8E%E4%B9%88%E8%AE%BE%E7%BD%AE
????//autoGenerateTinkerId = true
????// 構(gòu)建基準(zhǔn)包和補(bǔ)丁包都要指定不同的tinkerId,并且必須保證唯一性
????tinkerId = "patch-1.0.1-0611-2030"
????// 構(gòu)建多渠道補(bǔ)丁時使用
????// buildAllFlavorsDir = "${bakPath}/${baseApkDir}"
????// 是否啟用加固模式创坞,默認(rèn)為false.(tinker-spport 1.0.7起支持)
????// isProtectedApp = true
????// 是否開啟反射Application模式
????enableProxyApplication = false
????// 是否支持新增非export的Activity(注意:設(shè)置為true才能修改AndroidManifest文件)
????supportHotplugComponent = true
????}
????/**
57
?????*?一般來說,我們無需對下面的參數(shù)做任何的修改
?????58
?????*?對于各參數(shù)的詳細(xì)介紹請參考:
59
?????*?https://github.com/Tencent/tinker/wiki/Tinker-%E6%8E%A5%E5%85%A5%E6%8C%87%E5%8D%97
60
?????*/
????tinkerPatch {
????//oldApk ="${bakPath}/${appName}/app-release.apk"
????ignoreWarning = false
????useSign = true
????dex {
????????dexMode = "jar"
????????pattern = ["classes*.dex"]
????????loader = []
????}
????lib {
????????pattern = ["lib/*/*.so"]
????}
????res {
????????pattern = ["res/*", "r/*", "assets/*", "resources.arsc", "AndroidManifest.xml"]
????????ignoreChange = []
????????largeModSize = 100
????}
????packageConfig {
????}
????sevenZip {
????????zipArtifact = "com.tencent.mm:SevenZip:1.1.10"
????//????????path = "/usr/local/bin/7za"
????}
????buildConfig {
????????keepDexApply = false
????????//tinkerId = "1.0.1-base"
????????//applyMapping = "${bakPath}/${appName}/app-release-mapping.txt" //??可選碗短,設(shè)置mapping文件,建議保持舊apk的proguard混淆方式
????????//applyResourceMapping = "${bakPath}/${appName}/app-release-R.txt" // 可選题涨,設(shè)置R.txt文件偎谁,通過舊apk文件保持ResId的分配
????}
}
##去初始化applacation
????public class SampleApplication extends TinkerApplication {
????public SampleApplication() {
????????super(ShareConstants.TINKER_ENABLE_ALL, "com.example.dell.demohotbuglys.SampleApplicationLike",
????????????????"com.tencent.tinker.loader.TinkerLoader", false);
????}
}
##使用applacation的代理類來完成所有的工作
注意在初始化時候要換成自己的appid
?????public class SampleApplicationLike extends DefaultApplicationLike {
????public static final String TAG = "Tinker.SampleApplicationLike";
????public SampleApplicationLike(Application application, int tinkerFlags,
?????????????????????????????????boolean tinkerLoadVerifyFlag, long applicationStartElapsedTime,
?????????????????????????????????long applicationStartMillisTime, Intent tinkerResultIntent) {
????????super(application, tinkerFlags, tinkerLoadVerifyFlag, applicationStartElapsedTime, applicationStartMillisTime, tinkerResultIntent);
????}
????@Override
????public void onCreate() {
????????super.onCreate();
????????// 這里實現(xiàn)SDK初始化奔坟,appId替換成你的在Bugly平臺申請的appId
????????// 調(diào)試時,將第三個參數(shù)改為true
????????Bugly.init(getApplication(), "a55ecdce55", true);
????}
????@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
????@Override
????public void onBaseContextAttached(Context base) {
????????super.onBaseContextAttached(base);
????????// you must install multiDex whatever tinker is installed!
????????MultiDex.install(base);
????????// 安裝tinker
????????// TinkerManager.installTinker(this); 替換成下面Bugly提供的方法
????????Beta.installTinker(this);
????}
????@TargetApi(Build.VERSION_CODES.ICE_CREAM_SANDWICH)
????public void registerActivityLifecycleCallback(Application.ActivityLifecycleCallbacks callbacks) {
????????getApplication().registerActivityLifecycleCallbacks(callbacks);
????}
????@Override
????public void onTerminate() {
????????super.onTerminate();
????????Beta.unInit();
}
????}
##清單文件中注冊權(quán)限 及配置一些文件
????<uses-permission android:name="android.permission.INTERNET" />
????<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
????<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" />
????<uses-permission android:name="android.permission.READ_LOGS" />
????<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
????????<!--bugly-->
????????<activity
????????android:name="com.tencent.bugly.beta.ui.BetaActivity"
????????android:configChanges="keyboardHidden|orientation|screenSize|locale"
????????android:theme="@android:style/Theme.Translucent" />
>
????注意:如果您想兼容Android N(7.0/M(8.0))或者以上的設(shè)備搭盾,必須要在AndroidManifest.xml文件中配置FileProvider來訪問共享路徑的文件
????????<provider
????????android:name="android.support.v4.content.FileProvider"
????????android:authorities="${applicationId}.fileProvider"
????????android:exported="false"
????????android:grantUriPermissions="true">
????????<meta-data
????????android:name="android.support.FILE_PROVIDER_PATHS"
????????android:resource="@xml/provider_paths"/>
????</provider>
如果你使用的第三方庫也配置了同樣的FileProvider, 可以通過繼承FileProvider類來解決合并沖突的問題,示例如下:
????<provider
android:name=".utils.BuglyFileProvider"
android:authorities="${applicationId}.fileProvider"
android:exported="false"
android:grantUriPermissions="true"
????????tools:replace="name,authorities,exported,grantUriPermi????ssions">
????<meta-data
????????android:name="android.support.FILE_PROVIDER_PATHS"
????????android:resource="@xml/provider_paths"
????????tools:replace="name,resource"/>
????</provider>
>這里要注意一下婉支,F(xiàn)ileProvider類是在support-v4包中的鸯隅,檢查你的工程是否引入該類庫。
在res目錄新建xml文件夾向挖,創(chuàng)建provider_paths.xml(庫里已經(jīng)有了,不用創(chuàng)建了)文件如下:
????<?xml version="1.0" encoding="utf-8"?>
????<paths xmlns:android="http://schemas.android.com/apk/res/android">
????<!-- /storage/emulated/0/Download/${applicationId}/.beta/apk-->
????<external-path name="beta_external_path" path="Download/"/>
????<!--/storage/emulated/0/Android/data/${applicationId}/files/apk/-->
????<external-path name="beta_external_files_path" path="Android/data/"/>
????</paths>
>混淆配置
-dontwarn com.tencent.bugly.**
????-keep public class com.tencent.bugly.**{*;}
????# tinker混淆規(guī)則
????-dontwarn com.tencent.tinker.**
????-keep class com.tencent.tinker.** { *; }
????#如果你使用了support-v4包蝌以,你還需要配置以下混淆規(guī)則:
????-keep class android.support.**{*;}
##自己去手寫一個bug
private void bug() {
????????String str = null;
????????Log.d(TAG, "bug: "+str.length());
????????Toast.makeText(this,"bug 不見了", Toast.LENGTH_SHORT).show();
????}
找到我們studio右上角的Gradle,點開會看到當(dāng)前APP的構(gòu)建文件app-->build-->assembleRelesease,雙擊此目錄會自動打包生成apk(在build目錄下生成bakapk文件夾何之,內(nèi)部才是我們打包的apk跟畅,有三個文件,實際應(yīng)用中溶推,請注意保存線上發(fā)布版本的基準(zhǔn)apk包徊件、mapping文件、R.txt文件蒜危,如果線上版本有bug虱痕,就可以借助我們tinker-support插件進(jìn)行補(bǔ)丁包的生成),也就是我們有bug的一個版本辐赞,然后運行到手機(jī)去測試部翘,點擊崩掉。
>第二步
>
????修改bug响委,并去我們的tinker-support.gradle這個文件中新思,把生成的bug版本的文件夾名字復(fù)制,修改def baseApkDir = "app-0611-20-44-04"這個值赘风,把賦值的內(nèi)容放在這個變量中
????第二個修改的就是我們的tinkerId = "patch-1.0.1-0611-2030"
????只用把patch隨便改個自己記住的名字夹囚,把后邊版本號增加就行,比如2030--》到2060 2045 2080 只要大于之前那個就行
>第三步
????同樣找到我們studio右上角的Gradle邀窃,點開會看到tinker-support這個文件夾崔兴,點開,找到buildTinkerPatchRelease蛔翅,雙擊生成補(bǔ)丁包敲茄,等待生成后,會在我們的build下的outputs目錄下的patch文件夾中山析,同樣會生成三個文件堰燎,我們保存,并把7zip笋轨。apk名字的去上傳到我們的騰訊Bugly中秆剪,找到應(yīng)用升級模塊赊淑,點擊熱更新,上傳補(bǔ)丁仅讽,把此文件上傳上去陶缺,會自動匹配目標(biāo)版本,并在下發(fā)中選擇全量設(shè)備洁灵,點擊立即下發(fā)即可饱岸,等待10分鐘左右再去看應(yīng)用(有可能時間更長,不固定)徽千,已經(jīng)修復(fù)苫费。