Gradle——构建脚本基础

1、项目(project)和任务(task)

Gradle中的任何事都基于两个基本概念:项目(project)和任务(task)

每一个构建(build)都是由一个或多个项目组成的。一个项目代表什么取决于你使用Gradle做什么。例如,一个项目也许代表一个库或者一个web应用程序,它也许代表一个由其他项目产生的JAR文件组成的ZIP。一个工程不一定代表一件要去构建的事,它也许代表一件要去做的事情,例如将你的应用程序部署到工作台或者生产环境。现在看来,这些概念似乎有一点模糊,不过别担心,Gradle的基于约定的构建会对一个项目是什么有更具体的定义。

每一个项目由一个或多个任务(task)组成,一个任务代表一些执行构建工作的最小工作单元。它也许编译一些类,创建一个JAR,生成Javadoc文档,或者向库发布一些文档。
一个build包含多个project,一个project包含多个task
一个build包含多个project,一个project包含多个task

现在,我们将在一个项目中定义一些简单的任务,后面的章节将会使用多个项目,并且还有更多关于使用项目和任务的知识。

2、Hello World

你可以使用gradle命令运行Gradle的构建。gradle命令在当前目录下查找一个名为build.gradle的文件,我们称build.gradle文件是一个“构建脚本”,严格的说它是一个构建配置脚本。构建脚本定义了一个项目及其任务。

试一试:创建如下构建脚本,并命名为“build.gradle”

task hello{
    doLast{
        println 'Hello World!'
    }
}

在控制台中移动到此文件所在目录,并输入“gradle -q hello”执行该文件,可看到控制台中输出Hello World。
这里写图片描述
(关于 -q :用户手册中的大多数例子都使用了 -q 命令行选项,它会抑制Gradle的日志信息,所以会只显示task的输出。这会使手册中例子的输出更简洁,你完全可以不使用它。)

对build.gradle的说明:构建脚本定义了一个名为“hello”的task,并为其添加了一个操作。当你运行“gradle hello”的时候,Gradle执行这个名为“hello”的task时,会去执行你提供的操作。这个操作是一个闭包,包含了Groovy代码去执行。

3、使用更简单/快捷的定义方式定义task

task hello << {
    println 'Hello World!'
}

如上,这使用了 [一个简单的闭包(翻译不恰当)] 定义了一个名为“hello”的task,我们将在用户手册中使用这种风格定义task

4、构建脚本代码

Gradle的构建脚本给你Groovy的全部权利。

例1:在名为“build.gradle”的文件中输入如下代码:

task upper <<{
    String str = 'aBcD'
    println "original:" + str
    println "Upper case:" + str.toUpperCase()

}

运行结果如下:
这里写图片描述

例2:在名为“build.gradle”的文件中输入如下代码:

task count << {
     4.times { print "$it " }
     println ''
}

结果如下:
这里写图片描述

5、task依赖

也许你已经猜到了,你可以声明依赖于其他tasks的task

例:在名为“build.gradle”的文件中输入如下代码:

task hello << {
    println "hello"
}

task world(dependsOn: hello) <<{
    println "world"
}

结果如下:
这里写图片描述

可见,若先执行名为hello的task,则会只执行该task;若先执行名为world的task,则会先执行该task所依赖的其他task(hello),然后再执行自身那个task。即,被依赖的task会先执行。

懒依赖:被依赖的task不存在(被依赖的task后定义)

task world(dependsOn: "hello") <<{   
    println "world"
}
task hello << {
    println "hello"
}

注意:task world依赖的task的名字要加上引号

结果如下:
这里写图片描述
Task world对task hello的依赖关系声明在task hello定义之前,这对于多项目构建非常重要。

请注意,当引用一个未被定义的task时,你不能使用 shortcut notation (即点运算符 . )

6、动态task
Groovy能不仅能用于指定一个task能做什么,你也能用它去动态创建task。

4.times{ counter -> 
    task "task$counter" <<{
        println "No. $counter task"
    }
}

结果如下:
这里写图片描述

7、操作现有的task
一旦task被创建,他们就能通过API被访问到。

例如,你可以在运行时动态地为task添加依赖关系。

4.times{ counter -> 
    task "task$counter" <<{
        println "No. $counter task"
    }
}
task1.dependsOn task2, task3

为task1添加对task2,task3的依赖。
结果如下:
这里写图片描述

为现有的task添加行为:

task hello <<{
    println "hello"
}

hello.doFirst{
    println "doFirst"
}

hello.doLast{
    println "doLast"
}
hello << {
    println '88888'
}

结果如下:
这里写图片描述

可见,执行的顺序为:doFirst - task本身 - doLast - <<(doLast)
doFirst和doLast可以被多次调用,doFirst在task的操作列表开头,doLast在task的操作列表结尾,当task执行时,操作列表中的操作会按顺序执行。
“<<”操作符只不过是doLast的别名。

8、快捷访问符(. )
也许你已经注意到,可以使用快捷访问符访问现存的task,构建脚本中的每一个task的属性都可以使用快捷访问符访问。

task hello <<{
    println "hello world"
}

hello.doLast{
    println "my name is $hello.name !"
}

结果如下:
这里写图片描述

这使得代码很易读,特别是当使用插件提供的task时,例如编译task(compile task)

9、额外的task属性
你可以为task添加你自己的属性。
添加一个名为“myProperty”的属性,并为其赋初值。从这时起,这个属性就能像一个预定义的task属性一样读、写(设置)

task myTask {
    ext.myProperty = "Xiaming_Chen"
}

task printMyProperty <<{
    println myTask.myProperty
    myTask.myProperty = "Chen_Xiaming"
    println myTask.myProperty
}

结果如下:
这里写图片描述

可见,额外的task属性不局限于task,myProperty属性可以被其他的task读,也能在其他task中为其赋值。

10、使用Ant tasks

11、使用方法
在Gradle中,你可以怎样组织你的构建逻辑是有等级限制的。上面的示例“提取一个方法”只是第一级。

12、默认task
如果你没有指定其他的task,Gradle允许你定义一个或多个默认task执行。

defaultTasks "default1","default2"

task default1<<{
    println "No.1 default task"
}

task default2<<{
    println "No.2 default task"
}

task myTask<<{
    println "my task"
}

结果如下:
这里写图片描述

指定默认task为default1和default2,当执行时若不指定要执行的task,则会执行所有默认的task。

这与运行“gradle default1 default2”等效。
在一个多项目构建中,每个子项目能拥有他们自己特定的默认task,如果一个子项目没有指定默认task,则父项目的默认task会被使用(如果定义了的话)。

13、用DAG配置Gradle有配置阶段和执行阶段,在配置阶段之后,Gradle知道所有需要被执行的task,Gradle为你提供了可以利用这些信息的工具。一个用例将会检查发布的task是否在要被执行的所有task中,由此,你可以为不同的变量分配不同的值。

在下面的例子中,task的执行结果会因变量version的不同而不同。

task distribution <<{
    println "We build the zip with version = $version"
}

task release(dependsOn: distribution) <<{
    println "We release now"
}

gradle.taskGraph.whenReady { taskGraph ->

    if(taskGraph.hasTask(release)){
        version = "1.0"
    }else{
        version = "1.0-SNAPSHOT"
    }

}

执行gradle -q distribution:
这里写图片描述

执行gradle -q release:
这里写图片描述

“whenReady”会在release task执行之前影响release,即使release task不是首要的task这也会起作用。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值