本篇博客 主要为本人学习过程总结,有不对的地方麻烦指出,一起学习进步
前言
最近也是搞到了一个 电子书 《Android+Gradle权威指南》,学习一波Gradle 知识,尝试配置签名设置和配置Walle实现多渠道打包。阅读时间:15分钟
我们便可以通过点击左上角的Build->Generate Signed APK->Next,如果没有jks 文件,则需要自己创建,然后选择对应的Build Type进行打包。
对于部分不用上架的App来说,这波操作还可以接受,但是如果需要上传到国内的各个平台则需要多次重复这个操作,能把人搞死…,通过这篇文章可以学到 Gradle 签名配置 及 Walle 配置实习 多渠道打包。
我们先来看一下新建的项目 默认的 app gradle文件默认主要配置如下,
首先将我们生成好的 jks文件放到project 目录下
defaultConfig { .... } signingConfigs { release { storeFile file(../ymcandroid.jks)//签名文件路径 storePassword ymc****** keyAlias key0 keyPassword ymc******//签名密码 println("====== signingConfigs.release ======") } }
上述代码中的部分变量分别对应于 视图打包中的 我们需要添加的 jks 文件相关信息。
- 坑: signingConfigs代码块一定要写在buildTypes前面,否则会报下面这种错: Could not find property ‘debugConfig’ on SigningConfig container.
我们在项目路径下的app/build/outputs可以看到我们打包的apk。
这里也上下我的 buildTypes 配置
buildTypes { release { minifyEnabled false //是否移除无用资源 zipAlignEnabled true signingConfig signingConfigs.release proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } }
上述已经是简单的 签名了,但是我这个wanAndroid 项目需要上传到Github上,所以我们这里先说一下 忽略文件,在上传git 的时候,我们将忽略部分文件,以下是我项目中的忽略文件配置
# Built application files // *.apk *.ap_ # Files for the ART/Dalvik VM *.dex # Java class files *.class # Generated files bin/ gen/ out/ # Gradle files .gradle/ build/ # Local configuration file (sdk path, etc) local.properties /local.properties # Proguard folder generated by Eclipse proguard/ # Log Files *.log # Android Studio Navigation editor temp files .navigation/ # Android Studio captures folder captures/ # Intellij *.iml .idea/workspace.xml # Keystore files *.jks *.iws .idea/
我们可以在其中找到我们将要配置 jks密码信息的 local.properties 文件。
ndk.dir=E\:\\AndroidSDK\\ndk-bundle sdk.dir=E\:\\AndroidSDK keystore.path=../ymcandroid.jks keystore.password=ymc****** keystore.alias=key0 keystore.alias_password=ymc******
我们这里就需要修改 app build.gradle 文件,将明文的地方替换掉
def keystoreFilepath = '' def keystorePSW = '' def keystoreAlias = '' def keystoreAliasPSW = '' // default keystore file, PLZ config file path in local.properties def keyfile = file('s.keystore.temp') Properties properties = new Properties() // local.properties file in the root director properties.load(project.rootProject.file('local.properties').newDataInputStream()) keystoreFilepath = properties.getProperty("keystore.path") if (keystoreFilepath) { keystorePSW = properties.getProperty("keystore.password") keystoreAlias = properties.getProperty("keystore.alias") keystoreAliasPSW = properties.getProperty("keystore.alias_password") keyfile = file(keystoreFilepath) } android { compileSdkVersion 27 defaultConfig { applicationId "cn.white.ymc.wanandroidmaster" minSdkVersion 19 targetSdkVersion 27 versionCode 1 versionName "1.0" testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner" vectorDrawables.useSupportLibrary = true } signingConfigs { release { storeFile keyfile//签名文件路径 storePassword keystorePSW keyAlias keystoreAlias keyPassword keystoreAliasPSW //签名密码 println("====== signingConfigs.release ======") } } buildTypes { release { minifyEnabled false //是否移除无用资源 zipAlignEnabled true signingConfig signingConfigs.release proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' //签名文件存在,则签名 if (keyfile.exists()) { println("WITH -> buildTypes -> release: using jks key") signingConfig signingConfigs.release }else { println("WITH -> buildTypes -> release: using default key") } } } } dependencies { ... }
上述代码 主要修改地方 就是使用 gradle 语法读取 local.properties文件,获取其中信息,如果有就 签名打包。这样我们就可以保证 key文件的安全性了。
讲完 签名,我们就需要来看 Walle 的配置和部分Gradle 相关操作。
打包更加快速传统的通过productFlavors渠道包的方式,渠道10个以内还可以接受,如果100个渠道包,要死人,而采用美团Walle多渠道打包的方式只需要打一个包的时间。
配置更加灵活可以在APK渠道包中通过配置config文件,针对于不同渠道包配置各个渠道定制化额外信息。
整个APK(ZIP文件格式)会被分为以下四个区块:
Contents of ZIP entries(from offset 0 until the start of APK Signing Block)
APK Signing Block
ZIP Central Directory
ZIP End of Central Directory
这个是V2签名包的APK包格式,新的应用签名方案有着良好的向后兼容性,能完全兼容低于Android 7.0(Nougat)的版本。区块1、3、4都是受保护区块,不允许修改保护区块。美团打包的方式,是在2区块内写入ID-value的扩展信息(渠道信息),并保存到APK中。这样,每打一个渠道包只需复制一个APK,然后在APK中添加一个ID-value即可。
项目的根目录 build.gradle 文件中添加Walle Gradle插件的依赖
classpath 'com.meituan.android.walle:plugin:1.1.6'
App的 build.gradle 文件中apply这个插件,并添加上用于读取渠道号的AAR
apply plugin: 'walle' dependencies { compile 'com.meituan.android.walle:library:1.1.6' }
我们单独新建一个 gradle 用来保存配置插件 multlple-channel.gradle,内容如下
apply plugin: 'walle' walle { // 指定渠道包的输出路径 apkOutputFolder = new File("${project.buildDir}/outputs/channels") // 定制渠道包的APK的文件名称 apkFileNameFormat = '${appName}-${channel}-${buildType}-v${versionName}-${versionCode}-${buildTime}.apk'; // 渠道配置文件 channelFile = new File("${project.getProjectDir()}/channel") }
部分配置解析
apkOutputFolder:指定渠道包的输出路径, 默认值为new File("${project.buildDir}/outputs/apk")
apkFileNameFormat:定制渠道包的APK的文件名称, 默认值为 {buildType}-${channel}.apk
变量含义
projectName - 项目名字
appName - App模块名字
packageName - applicationId (App包名packageName)
buildType - buildType (release/debug等)
channel - channel名称 (对应渠道打包中的渠道名字)
versionName - versionName (显示用的版本号)
versionCode - versionCode (内部版本号)
buildTime - buildTime (编译构建日期时间)
fileSHA1 - fileSHA1 (最终APK文件的SHA1哈希值)
flavorName - 编译构建 productFlavors 名
记得在添加完成后 一定要在app build.gradle 文件中引入
apply from: 'multlple-channel.gradle'
接下来配置 channelFile
meituan # 美团 samsungapps #三星 hiapk anzhi xiaomi # 小米 91com gfan appchina nduoa 3gcn mumayi 10086com wostore 189store lenovomm hicloud meizu wandou # Google Play # googleplay # 百度 baidu # # 360 360cn # # 应用宝 myapp
上述 市场平台,读者可以自行删减留下需要的,接下来我们使用 Android Studio 进行打包
打包会经历一段时间,等成功后,我们打开 配置输出地址
就可以看到我们需要的 各个渠道的安装包了。