Gradle 入门
Gradle 入門
轉載請標明出處:
http://blog.csdn.net/lisdye2/article/details/52173213
本文出自:【Alex_MaHao的博客】
項目中的源碼已經共享到github,有需要者請移步【Alex_MaHao的github】
什么是Gradle
公司最近要進行版本迭代。最終決定將IDE 從Eclipse轉到了Android Studio。 以前自己的一些demo也是通過android Studio 來實現。但畢竟真正的轉到AS ,一些必要的東西還是需要去掌握的。
轉到AS,第一個問題便是多渠道打包,分包架構怎么辦。看我之前的博客關于熱修復等的,需要用到Ant,那么在Android Studio中能夠使用Ant 呢。關于這個我也不清楚。。。。。
AS 中引入了Gradle工具,完成App的編譯工作。那么什么是Gradle呢。
Gradle和Ant類似,也是一種自動化腳本編譯語言。能夠實現Android app從源碼到打包生成最終apk 的過程。
通過Gradle 我們能實現多渠道打包,自動簽名,MultiDex等方便我們開發的一些自動腳本。
在研究這個東西時,走了很多彎路,網上的教程大部分都是從原理說起。
比如:Gradle是一個由Groovy編寫的腳本語言。介紹Groovy語言是什么,哦,Groovy是基于Java的擴展性動態語言。開始學Groovy,然后學了半天,還是一知半解。本篇博客不介紹原理,只介紹如何使用它。先學會用,在慢慢的分析,最后到精通。
AS工程目錄結構
通過AS 創建工程時,系統會自動創建一些文件,下面一張圖介紹了這些文件的作用。
漏了一點,補上。。。
從工程目錄可以看到,涉及到Gradle編譯腳本有很多,但我們只需要修改關注的有以下幾個文件
工程根目錄下的:
- settings.gradle
- build.gradle
每一個module下:
- build.gradle
自動生成的Gradle腳本解析
settings.gradle
配置哪些module需要加入編譯,例如我新創建的工程,存在一個基礎的app module和一個lib(依賴庫),那么它的內容為
include ':app', ':lib'build.gradle
在創建工程時,會默認在工程的根目錄下創建一個build.gradle,該build.gradle向所有的module提供默認的Gradle 編譯配置,作為公有的配置向每一個module下的build.gradle提供默認配置。
// buildscript 屬于一個script block 。 他的目的是為了配置Gradle編譯所需要的依賴, // 此依賴指的不是我們apk運行所需要的依賴、 buildscript {// 添加遠程倉庫repositories {// // 聲明遠程倉庫的源// 之前版本則是mavenCentral(), jcenter可以理解成是一個新的中央遠程倉庫,兼容maven中心倉庫,而且性能更優jcenter()}// 添加依賴,此依賴從遠程倉庫中查找dependencies {classpath 'com.android.tools.build:gradle:2.1.0'} }// 面向所有工程提供的依賴,在此只聲明了遠程倉庫的地址 allprojects {// 添加遠程倉庫repositories {jcenter()} }// 刪除本地的gradle,重新下載 task clean(type: Delete) {delete rootProject.buildDir }從代碼格式上可以看出:xxx{}的形式,學名script block。我們把它當做代碼塊就可以了,不過每個代碼塊有固定的意義。
根目錄下的build.gradle自上向下可以分為三個部分:
- 針對Gradle編譯所提供的依賴支持。
- 使用buildscript作為聲明:該中的配置是為了編譯時期為我們的gradle提供相關的庫支持
- 針對我們的apk所提供的依賴支持。
- 從代碼可以看出,只是提供了遠程倉庫的聲明,是因為針對于每一個module,他們依賴的jar包都不相同,所以由他們module下的build.gradle聲明相應的依賴。
- 重新下載gradle插件。此方法不會調用,當然可以鼠標放在代碼處,右鍵run。我試了一下。把我的gradle刪除了又重新下載了。沒有翻墻的不要run。。。
module下的build.gradle
直接上代碼
/*** /*** The first line in the build configuration applies the Android plugin for* Gradle to this build and makes the android {} block available to specify* Android-specific build options.** 應用一個用于構建當前工程的插件,** apply plugin: 'com.android.application'* 提供了一個android標簽 block,能夠解析android 中的一些屬性*/ apply plugin: 'com.android.application'android {// 編譯時期使用的sdk版本compileSdkVersion 23// 編譯工具版本buildToolsVersion "23.0.3"// 默認的配置defaultConfig {// pplicationId 是一個為了發布而定義獨特的標識符,一般和包名一致。當然可以不一致applicationId "com.alex.gradleproject"// 最小sdkminSdkVersion 15// 此標示和compileSdkVersion,他指定的是運行時的sdktargetSdkVersion 23// 代碼版本versionCode 1// app版本versionName "1.0"}/*** 配置多樣的構建類型,構建系統默認的有兩種類型:debug 和 relsase* debug 類型不會顯示的展示在buildType 中但是他已經包含了debug 工具和完成相應的簽名** release 默認顯示,且添加了混淆的配置,但是簽名相關的并沒有被默認配置**/buildTypes {// 是否運行混淆release {// 改為true ,表示開啟混淆minifyEnabled false// 混淆的文件地址proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'}} }// 依賴 dependencies {// module下的libs 文件夾下的jar文件compile fileTree(dir: 'libs', include: ['*.jar'])// 測試需要用的jar,不會打包到apk中testCompile 'junit:junit:4.12'// 打包到apk中的jarcompile 'com.android.support:appcompat-v7:23.4.0'// lib依賴工程compile project(':lib') }這么詳細的注釋,真心良心啊。
此版本中需要注意兩點
compileSdkVersion和targetSdkVersion兩個定義的區別:
- compileSdkVersion:編譯時依賴的sdk,例如我指定為23,那么編譯時將以此sdk作為參考,那些類沒有,或者過時不可用等。
- targetSdkVersion:該版本指定的是運行時,使用哪個版本的sdk。23版本android加入了運行時權限,但我們的app沒有做相關的處理,則可以指定sdk為23以下,那么就不會有運行時權限的相關東西了。
dependencies{}:在工程根目錄下的build.gradle中,只是聲明了工程的遠程倉庫。而此處便是聲明該module下所依賴的相關jar。此時的相關jar會從jcenter()中進行查找下載。
自動簽名
1,生成簽名文件,并將文件放入到module根目錄下,創建key文件夾,放入其中
2,添加簽名信息的配置,在module下的build.gradle文件中
android {// ....signingConfigs{config_release{keyAlias 'alex'keyPassword '111111'storePassword '123456'storeFile file('key/key.jks')}}//.....}3,將簽名的信息添加到buildTypes的release的block中
buildTypes {// 是否運行混淆release {// 改為true ,表示開啟混淆minifyEnabled false// 混淆的文件地址proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'// 添加簽名信息signingConfig signingConfigs.config_release}}如果我們修改了gradle文件,會提示sync Now 的提示。必須刷新
4,通過gradle工具編譯apk
在AS 的右側邊欄中存在一個Gradle,點擊里面就是對應的Gradle對象。這個不能細說。。。找到:app/tasks/build/assembleRelease,雙擊運行。
5,獲取簽過名的apk文件
具體目錄在GradleProject\app\build\outputs\apk中
Gradle 多渠道打包
多渠道打包,一些大公司可能會自己進行統計,而大部分的可能使用的是友盟統計,那么就按照友盟統計的例子進行實現。
1,清單文件中添加友盟的聲明
<!--這里可以添加更多的配置,gradle構建時動態變量${CHANNEL_VALUE}為渠道信息--><meta-data android:name="UMENG_CHANNEL" android:value="${CHANNEL_VALUE}" />${}標示中添一個變量,獲取這個變量的值 。${CHANNEL_VALUE} == CHANNEL_VALUE
Gradle在編譯時,會將.gradle和清單文件進行合并編譯,那么在.gradle中定義一個CHANNEL_VALUE就實現了不同值得替換。
2,編寫渠道列表的配置文件,在app的根目錄下 channel.properties
#默認渠道 channel.default=paojiao #全部渠道列表 channel.list=baidu,360,hiapk#號代表注釋。
3,編寫多渠道打包的腳本channel.gradle
apply plugin: 'com.android.application'/*** gradle 的基礎是Groovy,Groovy是基于Java的,所以java代碼在這里都可以使用** 該文件可以通過一定的方式和app下的build.gradle進行合并*/ // 生成配置對象 Properties properties = new Properties(); // 加載配置文件 properties.load(new FileInputStream(project.rootDir.getAbsolutePath()+"/app/channel.properties")) // 獲取默認的配置渠道包 String defau = properties.getProperty('channel.default') // 獲取渠道列表 String channel = properties.get('channel.list') // 將渠道列表進行分割成數組,獲取相應的渠道包 String[] channelList = channel.split(',')// 下面的代碼會默認加入到app 下的build.gradle中 android{/*** 為了獲得不同的App 版本 ,能夠設置一些信息,覆蓋defaultConfig{}的一些配置信息** 該block 不是可選項,系統不會默認創建他** 打不通包時,如果有重復的,優先級如下 ,相同名字下* build variant > build type > product flavor > main source set > library dependencies*/productFlavors{// 循環遍歷渠道包for(String c : channelList){// 引用變量 此時 ${c} = c的具體字符串"${c}"{// 聲明了一個變量 類似于鍵值對 key = CHANNEL_VALUE value = channel的值manifestPlaceholders = [CHANNEL_VALUE: c]}}}}4,將編寫的渠道腳本加入到app下的build.gradle中
apply plugin: 'com.android.application'// 引入channel.gradle apply from:'channel.gradle'5,在右側的Gradle工具欄中運行gradle腳本
具體運行為app/tasks/build/assembleRelease,雙擊運行。
6,獲取渠道包
生成的apk的具體目錄GradleProject\app\build\outputs\apk中
總結
- 上一篇: (送书)《美好企业》导读:企业家需要超越
- 下一篇: HTML 限制文本框只能输入特定字符(比