Gradle學習之一入門介紹
Gradle學習之二Groovy核心語法
Gradle學習之三Groovy高階語法
Gradle學習之四Gradle生命週期
Gradle學習之五Project詳解
Gradle學習之六Task詳解
Gradle學習之七其他重要模組
雖然在專案中 AS有 Project 、 Module Library、Module App之分,但是對於Gradle來說,都是"project": 每一個module能把理解為gradle project的原因是存在build.gradle檔案
Root project 管理子project。子project負責本project的檔案輸出,並且能夠呼叫父project api ,管理其子project
在gradl專案中,每一個build.gradle會被編譯成Project位元組碼,因此在其中書寫內容,就相當於在Project類內部寫內容。
使用build.gradle列印所有的project和所有的子project:
this.getProjects()
//project api 詳解
//注意build.gradle中的方法,都是在設定階段執行的
//要想在執行階段執行, 需要設定task, 後面進行使用。
def getProjects(){
println '---------------'
println 'Root Project'
println '---------------'
this.getAllprojects().eachWithIndex { Project entry, int index ->
if(index == 0){
println "Root project ${entry.name}"
}else {
println "+--- project ${entry.name}"
}
}
}
this.getSubproject()
def getSubproject(){
println '---------------'
println 'Sub Project'
println '---------------'
this.getSubprojects().eachWithIndex { Project entry, int index ->
println "+--- project ${entry.name}"
}
}
使用build.gradle列印根project和父project:
this.getParentPro()
def getParentPro(){
this.getParent().each {println it.name}
}
this.getRootPro()
def getRootPro(){
println "The root is ${this.getRootProject().name}"
}
在Android開發中,我們使用Gradle來設定和構建APP。接下來我們看一下Project的api在android專案中的應用。下述程式碼是寫在專案的根build.gradle下,為子模組提供一些通用設定。
/**
* Project api
*
* 在根工程中管理子project (雖然能夠設定子project但是不建議這麼做)
* 通過傳入模組名稱,獲取指定模組的Gradle Project物件,從而設定它
*/
project('app'){ Project project->
apply plugin: 'com.android.application'
group 'com.zfc'
version '1.0.0'
dependencies {}
android{}
}
//該方法用於設定當前project和子project
allprojects {
group 'com.zfc'
version '1.0.0'
}
//列印驗證,是否子模組已經有上面設定的group屬性了
println project('app').group
println project('baselibrary').group
//不包括當前project,只包含它的子project
//比如將子project上傳的maven的設定,可以在這裡進行設定
subprojects { Project project->
if(project.plugins.hasPlugin("com.android.library")){
apply from: '../publicToMaven.gradle'
}
}
public interface Project extends Comparable<Project>, ExtensionAware, PluginAware {
//gradle預設檔名
String DEFAULT_BUILD_FILE = "build.gradle";
//預設路徑分隔符
String PATH_SEPARATOR = ":";
//輸出的預設路徑
String DEFAULT_BUILD_DIR_NAME = "build";
String GRADLE_PROPERTIES = "gradle.properties";
}
由於Project預設屬性有限。我們需要定義一些擴充套件屬性
//定義擴充套件屬性
ext{
}
subprojects{
//每個project都定義了擴充套件屬性
ext{
}
}
我們可以在優化一下,將ext定義在根gradle中。根屬性,可以被子完全繼承,可以直接使用。
最佳實踐,將擴充套件屬性單獨這是在一個檔案中
然後再在根gradle參照。
還可以在gradle.properties.但是隻能定義key-value的形式
//file: gradle.properties
isNeedLoadTest = false
//file: setting.gradle
include ':app',"lib_base"
//需要注意的是gradle.properties的屬性 key或者value都是Object型別,需要進行一下轉換
if(hasProperty('isNeedLoadTest')?isNeedLoadTest.toBoolean():false){
include ':test'
}
println getRootDir().absoulutePath() //根工程
println getBuildDir().absolutePath() //當前位置下的build資料夾路徑
println getProjectDir().absolutePath() //當前project模組
def getContent(String path){
try{
//file 從當前位置定位檔案
//project 還有 files api ,通過批次定位檔案
def f = file(path)
return f.text
}catch(GradleException e){
e.printStackTrack()
}
return null
}
//將當前檔案的path複製都 根目錄下的build的檔案
copy{
from fiile('path1')
into getRootProject().getBuildDir()
//還可以排除
exclude{
}
//重新命名
rename{
}
}
fileTree('path'){FileTree fileTree ->
fileTree.visit{ FileTreeElement element->
copy{
from element.file
into getRootProject().getBuildDir().path+"/test"
}
}
}
上述的檔案操作,比如copy ,file等,需要在同一工程下進行操作。
buildscript{ ScriptHandler scriptHandler->
//設定工程的倉庫地址
scriptHandler.repositories{ RepositoryHandler handler->
handler.jcenter()
handler.mavenCentral()
handler.mavenLocal()
handler.ivy{
}
handler.maven{
name 'personal'
url 'http://local.....'
credenticals{
username = 'admin'
password = 'admin123'
}
}
}
//設定工程外掛地址
scriptHandler.dependencies{
classpath 'com.android.tools.buid:gradle:2.2.2'
classpath 'com.tencent'
}
}
dependencies{
//資料夾 -> fileTree ,否則file
compile fileTree(include:['*.jar'],dir:'libs')
compile(){
//排除依賴
exclude module:'xxx'
exclude group:'yyyy'
//禁止傳遞依賴
transive false
}
}
儘量不要使用傳遞依賴。因為傳遞依賴是不確定的。
compile 完全把依賴打包進去。
provided:輔助過程,確保不會再執行時起作用才可以。
如果使用外部命令
task(name: 'apkcopy'){
//doLast確保 該方法在gradle執行階段執行
doLast{
def sourcePath = this.buildDir.path + '/outputs/apk'
def destPath = '絕對目的路徑'
def cmd = 'mv -f ${sourcePath} ${destPath}'
exec{
try{
executable 'bash'
args '-c' , cmd
println 'the command is execute success.'
}catch(GradleException e){
e.printStackTrace()
println 'the command is execute failed.'
}
}
}
}
./gradlew apkcopy