Gradle 深入解析

FreeGuideOnline 最新 2026-07-15

kotlin plugins { id("java") }

group = "com.example" version = "1.0.0"

repositories { mavenCentral() }

dependencies { testImplementation("org.junit.jupiter:junit-jupiter:5.9.3") }


- `plugins{}` 块:应用官方或社区插件。
- `repositories{}`:指定依赖查找的仓库。
- `dependencies{}`:声明项目的依赖。

Groovy DSL 语法类似,但字符串和函数调用略有差异。

### 3. 任务(Task)详解

任务是 Gradle 的核心执行单位。下面深入介绍如何创建和定制任务。

#### 3.1 创建任务

可以在构建脚本中通过任务容器注册任务:

```kotlin
// 使用register方式(推荐,延迟配置)
tasks.register("hello") {
    doLast {
        println("Hello Gradle!")
    }
}

// 使用create方式(立即配置)
tasks.create("greet") {
    doFirst {
        println("Greet executed first")
    }
    doLast {
        println("Greet executed last")
    }
}
  • doLast:添加一个在任务执行最后执行的动作(Action)。
  • doFirst:添加在最前的动作。
  • 推荐使用 register,因为它延迟配置,仅在需要时才创建任务,能提升构建性能。

3.2 任务依赖

通过 dependsOn 设置任务间的依赖关系:

tasks.register("prepare") {
    doLast { println("Preparing...") }
}

tasks.register("assemble") {
    dependsOn("prepare")
    doLast { println("Assembling...") }
}

可以通过命令行执行 gradle assemble,Gradle 会先执行 prepare 再执行 assemble。也可以为依赖指定数组,实现多重依赖。

3.3 任务输入与输出

声明任务的输入和输出是实现增量构建的关键。Gradle 可以根据输入输出的变化决定是否跳过任务。

tasks.register<Copy>("copyConfig") {
    from("src/config")
    into("build/config")
}

对于自定义任务,可以使用 inputsoutputs 属性:

abstract class MyTask : DefaultTask() {
    @InputFile
    lateinit var inputFile: File

    @OutputFile
    lateinit var outputFile: File

    @TaskAction
    fun process() {
        // 处理逻辑
    }
}

仅为有输入输出变化的任务重新执行,大幅加快构建速度。

3.4 任务类型

Gradle 内置了丰富的任务类型,如 CopyDeleteExecJavaCompile 等。你可以直接使用或继承它们。

tasks.register<Zip>("bundle") {
    from("src/main/resources")
    archiveFileName.set("bundle.zip")
    destinationDirectory.set(layout.buildDirectory.dir("dist"))
}

4. 依赖管理

Gradle 提供了强大的依赖管理功能,能够声明、解析和使用来自不同仓库的依赖。

4.1 依赖配置

声明依赖时需要指定配置(Configuration),表示依赖使用的范围。常见配置包括:

  • implementation:依赖仅在模块内部使用,不会泄露给编译时消费者。推荐使用。
  • api:依赖会暴露给消费者(即如果其他项目依赖本项目,能传递性获得本依赖)。
  • compileOnly:编译时需要,但不会打包,运行时由环境提供。
  • runtimeOnly:运行时需要,编译时不暴露。
  • testImplementationtestCompileOnly等:测试相关的配置。

示例:

dependencies {
    implementation("com.google.guava:guava:32.1.2-jre")
    testImplementation("org.junit.jupiter:junit-jupiter:5.9.3")
    compileOnly("org.projectlombok:lombok:1.18.28")
    runtimeOnly("org.postgresql:postgresql:42.6.0")
}

4.2 外部依赖与版本

依赖的声明格式为 group:artifact:version。也可以使用动态版本:

implementation("org.springframework:spring-core:5.+")   // 使用5.x的最新版本
implementation("com.google.guava:guava:[10.0,11.0)")     // 版本范围

但为了构建可重现性,生产环境建议采用固定版本。

4.3 依赖冲突与传递性依赖

当一个依赖被多条路径引入且版本不同时,Gradle 会自动选择一个最高版本(默认策略)。可以用 resolutionStrategy 强制指定:

configurations.all {
    resolutionStrategy {
        force("com.google.guava:guava:31.1-jre")
    }
}

也可以排除传递性依赖:

implementation("some:lib:1.0") {
    exclude(group = "log4j", module = "log4j")
}

5. Gradle 插件体系

插件是 Gradle 扩展功能的单元。它们可以添加任务、配置、约定以及新的 DSL。

5.1 应用插件

plugins{} 块中声明插件:

plugins {
    id("java")                     // 内置插件
    id("org.springframework.boot") version "3.1.2" // 第三方插件
}

对于旧版的 apply plugin 方式,依然可用,但新项目建议采用 plugins DSL。

5.2 常用官方插件

  • java / java-library:添加 Java 编译、测试、Jar 打包等任务。
  • application:生成可执行 JVM 应用,提供 run 任务和打包分发包的功能。
  • maven-publish:用于发布构件到 Maven 仓库。
  • checkstyle / pmd / spotbugs:静态代码分析。
  • war:适用于 Web 应用,构建 WAR 包。

5.3 自定义插件

自定义插件可以打包在 buildSrc 目录或独立项目中。最简单的自定义插件方式:

buildSrc/src/main/kotlin/MyPlugin.kt 中:

class MyPlugin : Plugin<Project> {
    override fun apply(project: Project) {
        project.tasks.register("myTask") {
            doLast { println("Hello from custom plugin") }
        }
    }
}

然后于主项目的 build.gradle.kts 中应用:

plugins {
    id("my-plugin")
}

6. 多项目构建

大型项目通常由多个子模块构成,Gradle 提供了方便的多项目构建支持。

6.1 项目结构

在根目录创建 settings.gradle.kts 文件,包含所有子项目:

rootProject.name = "my-root"
include("core", "web", "data")

子项目分别位于 core/web/data/ 目录下,并各自拥有自己的 build.gradle.kts

6.2 通用配置

根项目的构建脚本可以集中定义子项目共用的配置:

subprojects {
    apply(plugin = "java")
    group = "com.example"
    version = "1.0"
    repositories {
        mavenCentral()
    }
}

也可以通过 allprojects 应用于所有项目(包括根项目)。

6.3 跨项目依赖

在子项目之间声明依赖,使用项目路径:

// web/build.gradle.kts
dependencies {
    implementation(project(":core"))
    implementation(project(":data"))
}

这样 web 就能使用 coredata 模块中的类。

7. Gradle Wrapper:确保一致的构建环境

Wrapper 是 Gradle 推荐使用的执行方式。它是一套脚本和 Jar 包,允许在没有预装 Gradle 的机器上,自动下载指定版本的 Gradle 并执行构建。

7.1 使用方式

在项目根目录执行 gradle wrapper 生成 wrapper 文件。之后使用 ./gradlew(Unix)或 gradlew.bat(Windows)代替直接调用 gradle

Wrapper 的关键文件:

  • gradlew / gradlew.bat:执行脚本。
  • gradle/wrapper/gradle-wrapper.jar:负责下载 Gradle 的引导 Jar。
  • gradle/wrapper/gradle-wrapper.properties:配置 Gradle 版本和存放路径。

7.2 配置版本

gradle-wrapper.properties 中指定:

distributionUrl=https\://services.gradle.org/distributions/gradle-8.2.1-bin.zip

通过 ./gradlew wrapper --gradle-version 8.3 可以快速升级或降级。

8. 常用的构建优化技巧

Gradle 自身具备很高的性能,但仍有一些优化手段值得掌握。

8.1 开启并行与按需配置

gradle.properties 中设置:

org.gradle.parallel=true
org.gradle.configureondemand=true
  • parallel 使得多模块项目中的独立任务可以并行执行。
  • configureondemand 仅配置当前执行任务所需的项目,减少配置阶段耗时。

8.2 使用构建缓存

org.gradle.caching=true 启用本地构建缓存,使得任何任务的输出只要输入不变都能被重用,而不仅仅依赖任务的增量构建。

8.3 守护进程调优

Gradle 默认会启动守护进程。可以通过 gradle.properties 调整 JVM 参数:

org.gradle.jvmargs=-Xmx2048m -XX:MaxMetaspaceSize=512m