Gradle入門

隨着Android Studio越來越完善,更多的開發者捨棄掉Eclipse。但是新的IDE與以往的Eclipse有很大區別,這導致部分開發者望而卻步,其中一個大家覺得比較麻煩的是Android Studio採用的新的構建系統,gradle。那麼這篇文章我將對gradle進行一個簡單介紹(主要講gradle配合Android Studio的使用),希望幫助大家熟悉gradle。

一. gradle是什麼?

gradle跟ant/maven一樣,是一種依賴管理/自動化構建工具。但是跟ant/maven不一樣,它並沒有使用xml語言,而是採用了Groovy語言,這使得它更加簡潔、靈活,更加強大的是,gradle完全兼容maven和ivy。更多詳細介紹可以看它的官網:http://www.gradle.org/

二.爲什麼使用gradle?

更容易重用資源和代碼;
可以更容易創建不同的版本的程序,多個類型的apk包;
更容易配置,擴展;
更好的IDE集成;

三.gradle入門需知

1.基本配置:

首先明確gradle跟maven一樣,也有一個配置文件,maven裏面是叫pom.xml,而在gradle中是叫build.gradle。Android Studio中的android項目通常至少包含兩個build.gradle文件,一個是project範圍的,另一個是module範圍的,由於一個project可以有多個module,所以每個module下都會對應一個build.gradle。這麼說有點抽象,看下面這個圖:

這是一個android工程的project視圖,上面那個是module下的build.gradle文件。下面那個是project下的build.gradle文件。這兩個文件是有區別的,project下的build.gradle是基於整個project的配置,而module下的build.gradle是每個模塊自己的配置。下面看下這兩個build.gradle裏面的內容:

project#build.gradle:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
// Top-level build file where you can add configuration options common to all sub-projects/modules.
 
buildscript {
    //構建過程依賴的倉庫
    repositories {
    jcenter()
}
//構建過程需要依賴的庫
dependencies {
     //下面聲明的是gradle插件的版本
     classpath 'com.android.tools.build:gradle:1.1.0'
     // NOTE: Do not place your application dependencies here; they belong
     // in the individual module build.gradle files
}
}
//這裏面配置整個項目依賴的倉庫,這樣每個module就不用配置倉庫了
allprojects {
     repositories {
          jcenter()
     }
}

注:大家可能很奇怪,爲什麼倉庫repositories需要聲明兩次,這其實是由於它們作用不同,buildscript中的倉庫是gradle腳本自身需要的資源,而allprojects下的倉庫是項目所有模塊需要的資源。所以大家千萬不要配錯了。

module#build.gradle:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
//聲明插件,這是一個android程序,如果是android庫,應該是com.android.library
apply plugin: 'com.android.application'
android {
     //安卓構建過程需要配置的參數
     compileSdkVersion 21//編譯版本
     buildToolsVersion "21.1.2"//buildtool版本
     defaultConfig {//默認配置,會同時應用到debug和release版本上
     applicationId "com.taobao.startupanim"//包名
     minSdkVersion 15
     targetSdkVersion 21
     versionCode 1
     versionName "1.0"
}
 buildTypes {
     //這裏面可以配置debug和release版本的一些參數,比如混淆、簽名配置等
     release {
         //release版本
         minifyEnabled false//是否開啓混淆
         proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'//混淆文件位置
     }
}
}
dependencies {
     //模塊依賴
     compile fileTree(dir: 'libs', include: ['*.jar'])//依賴libs目錄下所有jar包
     compile 'com.android.support:appcompat-v7:21.0.3'//依賴appcompat庫
}

defaultConfig中是一些基本配置,它會同時應用到debug/release版本上,下面列舉了所有可配項及對應的值:

buildTypes結點很重要,這裏可以配置構建的版本的一些參數,默認有兩個構建版本release/debug,當然你可以自定義一個構建版本,比如叫foo,然後通過gradlew assembleFoo就可以生成對應的apk了。

buildTypes裏還有很多可配置項,下面列舉了所有可配項以及debug/release版本的默認值:

現在大家對build.gradle已經初步瞭解了,我們再看下其他一些與gradle相關的文件:
1.gradle.properties:
從名字上就知道它是一個配置文件,沒錯,這裏面可以定義一些常量供build.gradle使用,比如可以配置簽名相關信息如keystore位置,密碼,keyalias等。
2.settings.gradle:
這個文件是用來配置多模塊的,比如你的項目有兩個模塊module-a,module-b,那麼你就需要在這個文件中進行配置,格式如下:
1
include ':module-a',':module-b'
3.gradle文件夾:
這裏面有兩個文件,gradle-wrapper.jar和gradle-wrapper.properties,它們就是gradle wrapper。gradle項目都會有,你可以通過命令gradle init來創建它們(前提是本地安裝了gradle並且配置到了環境變量中)。
4.gradlew和gradlew.bat:
這分別是linux下的shell腳本和windows下的批處理文件,它們的作用是根據gradle-wrapper.properties文件中的distributionUrl下載對應的gradle版本。這樣就可以保證在不同的環境下構建時都是使用的統一版本的gradle,即使該環境沒有安裝gradle也可以,因爲gradle wrapper會自動下載對應的gradle版本。
gradlew的用法跟gradle一模一樣,比如執行構建gradle build命令,你可以用gradlew build。gradlew即gradle wrapper的縮寫。
2.gradle倉庫:
gradle有三種倉庫,maven倉庫,ivy倉庫以及flat本地倉庫。聲明方式如下:
1
2
3
4
5
6
7
8
9
maven{
      url "..."
}
ivy{
      url "..."
}
flatDir{
      dirs 'xxx'
}

有一些倉庫提供了別名,可直接使用:

1
2
3
4
5
repositories{
     mavenCentral()
     jcenter()
     mavenLocal()
}
3.gradle任務:
gradle中有一個核心概念叫任務,跟maven中的插件目標類似。
gradle的android插件提供了四個頂級任務
1
2
3
4
assemble 構建項目輸出
check 運行檢測和測試任務
build 運行assemble和check
clean 清理輸出任務

執行任務可以通過gradle/gradlew+任務名稱的方式執,執行一個頂級任務會同時執行與其依賴的任務,比如你執行

1
gradlew assemble

它通常會執行:

1
2
gradlew assembleDebug
gradlew assembleRelease
這時會在你項目的build/outputs/apk或者build/outputs/aar目錄生成輸出文件
注:linux下執行構建任務需要首先更改gradlew腳本的權限,然後才能執行該腳本:
1
2
chmod +x gradlew
./gradlew assemble

可以通過:

1
gradlew tasks

列出所有可用的任務。在Android Studio中可以打開右側gradle視圖查看所有任務。

四.常見問題

1.導入本地jar包:
跟eclipse不太一樣,android studio導入本地jar除了將jar包放到模塊的libs目錄中以外,還得在該模塊的build.gradle中進行配置,配置方式是在dependencies結點下進行如下聲明:
1
compile files('libs/xxx.jar')

如果libs下有多個jar文件,可以這樣聲明:

1
compile fileTree(dir: 'libs', include: ['*.jar'])

2.導入maven庫:

1
compile 'com.android.support:appcompat-v7:21.0.3'

可見,格式爲

1
compile 'groupId:artifactId:version'
3.導入某個project:
你的app是多模塊的,假設有兩個模塊app和module-A,並且app模塊是依賴module-A的,這時候我們就需要在app模塊的build.gradle中的dependencies結點下配置依賴:
1
compile project(':module-A')

並且你需要在settings.gradle中把module-A模塊包含進來:

1
include ':module-A',':app'

此外,這種情況下module-A模塊是作爲庫存在的,因而它的build.gradle中的插件聲明通常應該是這樣的:

1
apply plugin: 'com.android.library'

而且,作爲library的模塊module-A的build.gradle文件的defaultConfig中是不允許聲明applicationId的,這點需要注意。

4.聲明三方maven倉庫:
可能你項目需要的一些庫文件是在你們公司的私服上,這時候repositories中僅有jcenter就不行了,你還需要把私服地址配到裏面來,注意,應該配到project的build.gradle中的allprojects結點下或者直接配到某個模塊中如果僅有這個模塊用到。
配置方式:
1
2
3
4
5
repositories{
     maven{
          url="http://mvnrepo.xxx.com"
     }
}

5.依賴三方aar文件:

1
compile 'com.aaa.xxx:core:1.0.1@aar'

6.將庫項目導出爲aar:
首先你的項目必須是一個庫項目,build.gradle中進行配置:

1
apply plugin : 'com.android.library'

然後你可以在命令行中進到項目目錄,執行如下gradle任務:

1
gradlew assembleRelease//確保該目錄下有gradlew文件

生成的aar在/build/output/aar文件夾中
7.引用本地aar:
首先將aar文件放到模塊的libs目錄下,然後在該模塊的build.gradle中聲明flat倉庫:

1
2
3
4
5
repositories{
    flatDir{
          dirs 'libs'
    }
}

最後在dependencies結點下依賴該aar模塊:

1
2
3
dependencies{
      compile (name:'xxx',ext:'aar')
}
8.排除依賴:
當出現依賴衝突的時候可以通過排除依賴解決,具體方式如下:
1
2
3
compile (group:'xxx',name:'xxx',version:'xxx'){
      exclude group:'xxx',module:'xxx'//module對應的就是artifactId
}

9.多dex支持(打包65k方法數限制)

 首先在build.gradle的buildConfig中增加如下配置:
1
multiDexEnabled true

接着,在dependencies結點下增加如下依賴:

1
2
3
dependencies{
compile 'com.android.support:multidex:1.0.0'
}

最後,讓你的Application繼承MultiDexApplication,如果你的應用沒有聲明Application,可以在manifest文件的application結點下增加name屬性,值爲android.support.multidex.MultiDexApplication。

詳細內容參見官方文檔。

10.自動移除不用資源

可以在buildTypes結點中增加如下配置:

1
2
3
4
5
6
buildTypes{
     release{
           minifyEnabled true
           shrinkResources true
     }
}

11.忽略lint錯誤:

可以在build.gradle文件中的android結點下增加如下配置:

1
2
3
4
5
android{
     lintOptions{
           abortOnError false
     }
}

12.聲明編譯的java版本

可以在build.gradle文件中的android結點下增加如下配置:

1
2
3
4
compileOptions {
     sourceCompatibility JavaVersion.VERSION_1_7
     targetCompatibility JavaVersion.VERSION_1_7
}

13.應用簽名配置

首先在module的build.gradle中增加這些字段:

1
2
3
4
storeFiles:keystore文件存儲位置,通常是.jks文件
storePassword 密碼
keyAlias keystore別名
keyPassword 密碼

具體配置方式爲:

首先在build.gradle的android結點下增加如下配置:

1
2
3
4
5
6
7
8
9
10
11
signingConfigs {
     //debug版本的簽名配置,通常不用配,因爲有默認的debug簽名
     debug {
     }
     release {
          storeFile file("key.jks")
          storePassword "123456"
          keyAlias "mykey"
          keyPassword "123456"
     }
}

注:debug的默認簽名爲:

1
signingConfig android.signingCongfigs.debug

位置爲

1
${home}\.android\debug.keystore

然後在buildTypes結點下的對應版本中添加上面的配置:

1
2
3
4
5
buildTypes{
     release{
          signingConfig signingConfigs.release
     }
}

當然,release不是固定的名稱,你可以隨便取,比如這樣:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
android {
     signingConfigs {
          debug {
                storeFile file("debug.keystore")
          }
          myConfig {
                storeFile file("other.keystore")
                storePassword "android"
                keyAlias "androiddebugkey"
                keyPassword "android"
          }
     }
     buildTypes {
          foo {
               debuggable true
               jniDebuggable true
               signingConfig signingConfigs.myConfig
         }
    }
}

真實開發中,把密碼配置到build.gradle中不是很好的做法,最好的做法是放在gradle.properties中:

1
2
3
4
RELEASE_STOREFILE=xxx.jks
RELEASE_STORE_PASSWORD=123456
RELEASE_KEY_ALIAS=mykey
RELEASE_KEY_PASSWORD=123456

然後直接引用即可:

1
2
3
4
storeFile file(RELEASE_STOREFILE)
storePassword RELEASE_STORE_PASSWORD
keyAlias RELEASE_KEY_ALIAS
keyPassword RELEASE_KEY_PASSWORD

14.定製buildConfig:

在build.gradle中配置:

1
2
3
4
5
6
7
8
buildTypes{
      release{
            buildConfigField "string","type","\"release\""
      }
      debug{
            buildConfigField "string","type","\"debug\""
      }
}

這樣就會在BuildConfig類中生成type字段:

1
2
3
4
//build/generate/source/buildConfig/release/包名/   路徑下的BuildConfig.java
public static final String type = "release"
//build/generate/source/buildConfig/debug/包名/    路徑下的BuildConfig.java
public static final String type = "debug"



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章