Gradle知识点整理(1)
文章目录
常见的项目构建工具
- Ant:
- 优点: 使用灵活,速度快(快于 gradle 和 maven)
- 缺点:Ant没有强加任何编码约定的项目目录结构,开发人员需编写繁杂 XML 文件构建指令,对开发人员是一个挑战
- Maven
- 优点: 遵循一套约定大于配置的项目目录结构,使用统一的 GAV 坐标进行依赖管理,侧重于包管理
- 缺点: 项目构建过程僵化,配置文件编写不够灵活、不方便自定义组件,构建速度慢于 gradle
- Gradle
- 优点:集 Ant 脚本的灵活性+Maven 约定大于配置的项目目录优势,支持多种远程仓库和插件,侧重于大项目构建
- 缺点: 学习成本高、资料少、脚本灵活、版本兼容性差等
Gradle安装
SpringBoot 官方文档明确指出,目前 SpringBoot 的 Gradle 插件需要 gradle6.8 版本及以上,所以我们这里选择 7x 版本
其中SpringBoot与Gradle存在版本兼容问题,Gradle与Idea也存在兼容问题,所以要选择Gradle6.8版本以及高于6.8版本的Gradle
Important Tips:
- 打开Idea安装目录下的\plugins\gradle\lib,能查看Idea与Gradle相对应的Gradle版本号
- 选择Spring Boot时一定要注意Spinrg Boot 和JDK 的版本
具体安装步骤参考以下文档:
Gradle和Maven项目结构
修改Maven下载源
我们可以在gradle的init.d目录下创建以.gradle结尾的文件,.gradle文件可以实现在build开始之前执行,所以可以在这个文件配置一些你要预先加载的操作
将以下内容复制到init.d目录下的init.gradle文件中:
- 项目所需要的架包会前往repositories中区下载
- 而buildscript是给build.gradle使用的
- mavenLocal() 即为maven本地仓库
- mavenCentral() 即为maven重要仓库
allprojects {
repositories {
mavenLocal()
maven { name "Alibaba"; url "https://maven.aliyun.com/repository/public"}
maven { name "Bstek"; url "https://nexus.bsdn.org/content/groups/public"}
mavenCentral()
}
buildscript {
repositories {
maven { name "Alibaba"; url "https://maven.aliyun.com/repository/public"}
maven { name "Bstek"; url "https://nexus.bsdn.org/content/groups/public"}
maven { name "M2"; url "https://plugins.gradle.org/m2/"}
}
}
}
启用init.gradle文件的方法:
- 在命令行指定文件,例如:
gradle -init-script yourdir/init,gradle -q taskName
。你可以多输入此命令来指定多个init文件 - 把init.gradle文件放到 USER_HOME/.gradle/ 目录下(即放到C盘下的当前用户目录下的.gradle文件夹下)
- 把以.gradle结尾的文件放到 USER_HOME/.gradle/init.d/ 目录下(即放到C盘下的当前用户目录下的.gradle文件夹下的init.d文件夹下)
- 把以.gradle结尾的文件放到 GRADLE_HOME/init.d/ 目录下(即gradle安装目录下的init.d文件夹下)
如果以上四种方式,存在两种,那么gradle会按照上面的顺序从1到4依次执行,如果给定目录下存在多个init脚本,会按拼音a-z顺序执行这些脚本,每个init脚本都存在一个对应的gradle实例,你在这个文件中调用的所有方法和属性,都会委托给这个gradle实例,每个init脚本都实现了Script接口。
其他类型的Maven的Aliyun地址
插件类的仓库地址,最好放到 buildscript
下
Gradle.properties
# 开启守护进程,下一次构建的时候,会连接这个守护进程进行构建,而不是重新fork一个进程进行构建
org.gradle.daemon=true
# 设置JVM堆内存大小
org.gradle.jvmargs=-Xmx4096m -XX:MaxPermSize=1024m -XX:+HeapDumpOnOutOfMemoryError -Dfile.encoding=UTF-8
# 并行编译
org.gradle.parallel=true
# 按需加载
org.gradle.configureondemand=true
# 开启gradle缓存
org.gradle.caching=true
Gradle Wrapper
Gradle Wrapper 实际上就是对Gradle的一层包装,用于解决实际开发中可能会遇到的不同项目需要不同版本的Gradle问题,例如:把自己代码共享给别人,发现别人的没有安装Gradle、或者别人的Gradle版本太老旧。
如何使用Gradle Wrapper
![在这里插入图片描述](/i/ll/?i=direct/70fd1595a59440d999ec566894caa17f.png) Gradle指令和Gradlew指令是不一样的,并且版本也有可能不一样。原因是因为Gradle指令使用的是本地安装的Gradle,Gradlew使用的是Gradle Wrapper中的Gradle,不过最终指令的使用方式是一样的。 对于Gradlew指令时,我们也可以用一些参数来控制Wrapper的生产,比如依赖的版本等:
参数名称 | 参数说明 | 参数示例 |
---|---|---|
–gradle-version | 用于指定使用的Gradle版本 | gradle wrapper --gradle-version=7.4.2 |
–gradle-distribution-url | 用于指定下载的Gradle发行版的url | gradle wrapper --gradle-version 7.4.2 --distribution-type all |
GradleWrapper执行流程
1.当我们第一次执行 ./gradlew build 命令的时候,gradlew 会读取 gradle-wrapper.properties 文件的配置信息
2.准确的将指定版本的 gradle 下载并解压到指定的位置GRADLE_USER HOME目录下的wrapper/dists目录中
3.并构建本地缓存(GRADLE_USER HOME目录下的caches目录中),下载再使用相同版本的gradle就不用下载了
4.之后执行的 ./gradlew 所有命令都是使用指定的 gradle 版本
何时使用Gradle Wrapper
下载别人的项目或者使用操作以前自己写的不同版本的gradle项目时:用Gradle wrapper,也即:gradlew,什么时候使用本地gradle?新建一个项目时:使用gradle指令即可。
Groovy学习
Groovy 是 用于Java虚拟机的一种敏捷的动态语言,它是一种成熟的面向对象编程语言,既可以用于面向对象编程,又可以用作纯粹的脚本语言。使用该种语言不必编写过多的代码,同时又具有闭包和动态语言中的其他特性。
Groovy是JVM的一个替代语言(替代是指可以用 Groovy 在Java平台上进行 Java 编程),使用方式基本与使用 Java代码的方式相同,该语言特别适合与Spring的动态语言支持一起使用,设计时充分考虑了Java集成,这使 Groovy 与 Java 代码的互操作很容易。(注意:不是指Groovy替代java,而是指Groovy和java很好的结合编程。)
Groovy与Java的主要区别
- 没有可见性修饰符的类或方法自动是公共的(可以使用一个特殊的注释来实现包的私有可见性)
- 没有可见性修饰符的字段将自动转换为属性,不需要显式的 getter 和 setter 方法
- 如果属性声明为 fnal,则不会生成 setter
- 一个源文件可能包含一个或多个类(但是如果一个文件不包含类定义的代码,则将其视为脚本)。脚本只是具有一些特殊约定的类,它们的名称与源文件相同(所以不要在脚本中包含与脚本源文件名相同的类定义)。
安装配置
Groovy概要
![在这里插入图片描述](/i/ll/?i=direct/f91b3fbc8e374797b7c2474121bde675.png) **类型转换**:当需要时,类型之间会自动发生类型转换:字符串(String)、基本类型如 (int)和类型的包装类(如 nteger)类说明: 如果在一个 groovy 文件中没有任何类定义,它将被当做 script 来处理,也就意味着这个文件将被透明的转换为一个Script 类型的类,这个自动转换得到的类将使用原始的 groovy 文件名作为类的名字。groovy 文件的内容被打包进run 方法,另外在新产生的类中被加入一个 main 方法以进行外部执行该脚本。
Groovy字符串操作
Groovy使用字符串时,单引号、双引号使用起来有不同的效果
- 单引号:不支持变量引用,不支持换行操作
- 双引号:支持变量引用,不支持换行操作
- 单引号模板字符串:不支持变量引用,支持换行操作
- 双引号模板字符串:支持变量引用,支持换行操作
Groovy三大语句结构
Groovy类型以及权限修饰符
- 原生数据类型
原生 | 包装 |
---|---|
boolean | Boolean |
char | Character |
short | Short |
int | Integer |
long | Long |
float | Float |
double | Double |
- 类、内部类、抽象类、接口
- 注解
- Trait:带有方法实现的接口
- 权限修饰符:private、public、protected
Groovy集合操作
Groovy支持List、Map集合操作,并且拓展了Java中的API,具体参考官方文档
Groovy类导入
Groovy异常处理
Groovy闭包
定义:是一个开放的、匿名的代码块,它可以接受参数、也可以有返回值。闭包可以引用其周围作用域中声明的变量。
语法:
{ [closureParameters -> ] statemets }
调用:
- 将闭包赋值给一个变量
- 变量名()、变量名.call()
示例:
def running = { who ->
println("$who start")
}
running("code")
running().call("code")
//____________分割_______________
def running(Closure closure) {
println("running start")
println("running end")
}
running({println("running")})
//____________分割_______________
def caculate(num1,num2,Closure closure){
closure(num1,num2)
}
caculate(10,15,{k,v -> println("$k + $v = ${k+v}")})
// 闭包作为方法的最后一个参数,那么闭包可以写在方法外边
caculate(10,15){k,v -> println("$k + $v = ${k+v}")}
//____________分割_______________
def caculate(Closure closure){
def num1 = 10
def num2 = 15
closure(num1,num2)
}
caculate(){k,v -> println("$k + $v = ${k+v}")}
caculate{k,v -> println("$k + $v = ${k+v}")}
Gretty项目部署
Tips:Gradle 6.x版本以前对Gretty支持比较友好
Gretty核心功能:
- 底层支持jerry,tomcat等Servlet容器
- 支持热部署、Https、调试
具体使用
- 项目引入Gretty
plugins {
id 'war'
id 'org.gretty' version '2.2.0'
}
- 指定maven仓库
repositories {
jcenter()
mavenCentral()
}
- Gretty 插件设置
gretty {
httpPort = 8888
contextPath = "/web"
debugPort = 5005
debugSuspend = true
httpsEnabled = true
// 热部署
manageClassReload = true
// 如果不指定默认容器,则默认使用Jetty
// servletContainer = 'tomcat'
httpsPort = 4431
}
- 执行命令:gradle appRun
Gradle项目生命周期
Gradle项目的生命周期分为三大阶段:Initialization -> Configuration -> Execution
Gradle中的setting文件
作用:主要作用是在项目初始化阶段确定要引入那些工程,需要加入到项目构建中,为构建项目工程树做准备。
工程树:Gradle中有工程树的概念,类似于Maven中的Project和Module
内容:里面主要定义了当前Gradle项目以及子Project的项目名称
位置:必须放在根工程下
名字:为setting.gradle文件,不能发生变化
对应实例:与org.gradle.api.initialization.Settings 实例是一一对应的关系。每个项目只有一个settings文件。
关注:只需关注文件中的 include 方法。
一个子工程只有再settings文件中配置了才会被gradle识别,构建时才会被包含
// 根项目名称
rootProject.name = 'gradle_tree'
// 子模块名称
include 'sub_01'
include 'sub_02'
include 'sub_03'
// 包含的子工程下的子工程名称
include 'sub_01:subProject01'
include 'sub_02:subProject02'
Gradle的Task
tasks.named('test') {
// 任务配置段,在配置阶段执行
println "this is task example"
// 任务的行为:在执行阶段执行
doFirst {
println "task first task"
}
doLast {
println "task last task"
}
}
运行任务
gradle -i test
任务的doFirst、doLast都可以在任务的外部定义
tasks.named('test') {
// 任务配置段,在配置阶段执行
println "this is task example"
}
test.doFirst {
println "task first task"
}
test.doLast {
println "task last task"
}
底层原理解析:无论是定义任务自身的 action,还是添加的 doLast、doFirst 方法,其实底层都被放入到一个 Action 的 List中了,最初这个action List 是空的,当我们设置了 ation[任务自身的行为],它先将 actin 添加到列表中,此时列表中只有一个action,后续执行doFirst的时候 doFirst在 action 前面添加,执行 doLast 的时候 doLast 在 action 后面添加。doFirst永远添加在 actions List 的第一位,保证添加的 Action 在现有的 action List 元素的最前面;doLast 永远都是在 action List末尾添加,保证其添加的 Action 在现有的 ction List 元素的最后面。一个往前面添加一个往后面添加,最后这个 actionList 就按顺序形成了 doFirst、 doSelf、 doLast 三部分的 Actions,就达到 doFirst、 doSelf、doLast 二部分的 Actions 顺序执行的目的。
Tips:其中<<代表dolast,在Gradle5.x版本之后就废弃了。
任务的依赖方式
- 参数方式依赖
taks 'A' {
doLast {
println "task A"
}
}
taks 'B' {
doLast {
println "task B"
}
}
taks 'C'(dependsOn: ['A','B']) {
doLast {
println "task C"
}
}
- 内部依赖
taks 'C' {
dependsOn = ['A','B']
doLast {
println "task C"
}
}
// ==================
taks 'C' {
doLast {
println "task C"
}
}
c.dependsOn = ['A','B']
- 外部依赖
// subproject01 工程
taks 'A' {
doLast {
println "task A"
}
}
// subproject02 工程
taks 'B' {
dependsOn(":subproject01:A")
doLast {
println "task B"
}
}
Tips1:当一个Task依赖多个Task的时候,被依赖的Task之间如果没有依赖关系,那么它们的执行顺序是随机的。
Tips2:重复依赖的任务只会执行一次,比如:
任务的执行
语法:gradle [taskanme] [–option-name]
# 常见任务
gradle build:构建项目:编译、测试、打包等操作
gradle run:运行一个服务,需要 application 插件支持,并且指定了主启动类才能运行
gradle clean:请求当前项目的 build 目录
gradle init:初始化 gradle 项目使用
gradle wrapper:生成 wrapper 文件夹的
gradle wrapper 升级 wrapper 版本号:gradle wrapper -gradle-version=4.4
gradle wrapper -gradle-version 5.2.1 --distribution-type all:关联源码用
# 项目报告
gradle projects:列出所选项目及子项目列表,以层次结构的形式显示
gradle tasks:列出所选项目[当前 project,不包含父、子]的已分配给任务组的那些任务
gradle tasks -all:列出所选项目的所有任务
gradle tasks -group="build setup":列出所选项目中指定分组中的任务
gradle help -task someTask:显示某个任务的详细信息
gradle dependencies:查看整个项目的依赖信息,以依赖树的方式显示
gradle properties:列出所选项目的属性列表
# 调试选项
-h,--help:查看帮助信息
-v,--version:打]印Gradle、Groovy、 AntJVM 和操作系统版本信息
-S,-full-stacktrace:打印出所有异常的完整(非常详细)堆栈跟踪信息
-s,-stacktrace:打印出用户异常的堆栈跟踪(例如编译错误)
-Dorg.gradle,daemon.debug=true:调试 Gradle 守护进程
-Dorg.gradle.debug=true:调试 Gradle 客户端(非 daemon)进程
-Dorg.gradle.debug.port=(port number):指定启用调试时要侦听的端口号。默认值为 5005
# 性能选项
-build-cache,--no-build-cache:尝试重用先前版本的输出。默认关闭(off)。
-max-workers:设置 Gradle 可以使用的 woker数。默认值是处理器数
-parallel,-no-parallel:并行执行项目。有关此选项的限制,请参阅并行项目执行默认设置为关闭(off)
# 守护进程
-daemon,--no-daemon:使用守护进程运行构建。默认是 onGradle
-foreground:在前台进程中启动 Gradle 守护进程
-Dorg.gradle.daemon.idletimeout=(number of milliseconds):Gradle Daemon 将在这个空闲时间的毫秒数之后停止自己。默认值为 1000000(3 小时)
# 日志选项
-Dorg.gradle.logging.level=(quiet,warn,lifecycle,info,debug):通过 Gradle 属性设置日志记录级别。
-q,-quiet:只能记录错误信息
-w,--warn:设置日志级别为 warn
-i,--info:将日志级别设置为 info
-d,-debug:登录调试模式(包括正常的堆栈跟踪)
# 其他
-x:-x 等价于:-exclude-task:常见 gradle -x test clean build
-rerun-tasks:强制执行任务,忽略up-to-date ,常见 gradle build -rerun-tasks
-continue:忽略前面失败的任务.继续执行,而不是在遇到第一个失败时立即停止执行。每个遇到的故障都将在构建结束时报告,常见: gradle build -continue。
gradle init -type pom:将 maven 项目转换为 gradle 项目(根目录执行)
gradle [taskName]:执行自定义任务
Gradle默认各指令之间相互的依赖关系
任务的定义方式
任务定义方式,总体分为两大类,一种是通过Project中的task方法,另一种是通过tasks对象的create或者register方法。
task('A',{ // 任务名称,闭包都作为参数
println "task a"
})
task('B'){ // 闭包作为最后一个参数可以直接从中括号中拿出来
println "task b"
}
task C { // groovy语法支持省略方法括号
println "taks c"
}
// 以上三种方法本质上是一种方法
def map = new HashMap<String,Object>();
map.put("aciton",{println "task d"})// action属性可以设置为闭包
taks(map,"D");
task.create("E"){ // 使用 task 的create方法
println "task e"
}
task.register("F"){ // register执行是延迟创建,即只有当task被需要的时候才会创建
println "task f"
}
任务的属性
配置项 | 描述 | 默认值 |
---|---|---|
type | 基于一个存在的task来创建,和java中的类继承相似 | DefaultTask |
overwrite | 是否替换一个存在的task,这个和type配合使用 | false |
dependsOn | 用于配置任务的依赖 | [] |
action | 添加到任务中的一个Action或者一个闭包 | null |
description | 任务的描述 | null |
group | 任务的分组 | null |
// 1.F是任务名,以参数的方式指定任务的属性信息
task(grou: "alan", description: "this is task F","F")
// 2.H是任务名,任务定义的同时,直接在内部指定属性信息
task("H"){
group("alan")
description("this is task H")
}
// 3.Y是任务名,给已有的任务 在外部指定属性信息
task("Y"){}
y.group = "alan"
y.description = "this is task Y"
标签:Groovy,知识点,task,gradle,println,init,整理,Gradle
From: https://blog.csdn.net/weixin_43795587/article/details/136674464