Gradle学习之增量式构建

简介:
请通过以下方式下载本系列文章的Github示例代码:
git clone https://github.com/davenkin/gradle-learning.git
   
 
如果我们将Gradle的Task看作一个黑盒子,那么我们便可以抽象出输入和输出的概念,一个Task对输入进行操作,然后产生输出。比如,在使用java插件编译源代码时,输入即为Java源文件,输出则为class文件。如果多次执行一个Task时的输入和输出是一样的,那么我们便可以认为这样的Task是没有必要重复执行的。此时,反复执行相同的Task是冗余的,并且是耗时的。
 
为了解决这样的问题,Gradle引入了增量式构建的概念。在增量式构建中,我们为每个Task定义输入(inputs)和输入(outputs),如果在执行一个Task时,如果它的输入和输出与前一次执行时没有发生变化,那么Gradle便会认为该Task是最新的(UP-TO-DATE),因此Gradle将不予执行。一个Task的inputs和outputs可以是一个或多个文件,可以是文件夹,还可以是Project的某个Property,甚至可以是某个闭包所定义的条件。
 
每个Task都拥有inputs和outputs属性,他们的类型分别为TaskInputs和TaskOutputs。在下面的例子中,我们展示了这么一种场景:名为combineFileContent的Task从sourceDir目录中读取所有的文件,然后将每个文件的内容合并到destination.txt文件中。让我们先来看看没有定义Task输入和输出的情况:
 
task combineFileContentNonIncremental {   
  def sources = fileTree('sourceDir')   
  def destination = file('destination.txt')   
  doLast {      
     destination.withPrintWriter { writer ->
           sources.each {source ->
              writer.println source.text         
           }      
        }   
  }
}
 
多次执行“gradle combineFileContentNonIncremental”时,整个Task都会反复执行,即便在第一次执行后我们已经得到了所需的结果。如果该combineFileContentNonIncremental是一个繁重的Task,那么多次重复执行势必造成没必要的时间耗费。
 
这时,我们可以将sources声明为该Task的inputs,而将destination声明为outputs,重新创建一个Task如下:
 
task combineFileContentIncremental {
  def sources = fileTree('sourceDir')
  def destination = file('destination.txt')
  inputs.dir sources
  outputs.file destination
  doLast {
     destination.withPrintWriter { writer ->
        sources.each {source ->
           writer.println source.text         
         }      
      }   
  }
}
 
相比之下,后一个Task只比前一个Task多了两行代码:
 
inputs.dir sources
outputs.file destination
 
当首次执行combineFileContentIncremental时,Gradle会完整地执行该Task。但是紧接着再执行一次,命令行显示:
 
:combineFileContentIncremental UP-TO-DATEBUILD SUCCESSFULTotal time: 2.104 secs
 
我们发现,combineFileContentIncremental被标记为UP-TO-DATE,表示该Task是最新的,Gradle将不予执行。在实际应用中,你将遇到很多这样的情况,因为Gradle的很多插件都引入了增量式构建机制。
 
如果我们修改了inputs(即sourceDir文件夹)中的任何一个文件或删除掉了destination.txt,当调用“gradle combineFileContentIncremental”时,Gradle又会重新执行,因为此时的Task已经不再是最新的了。对于outputs,我们还可以使用upToDateWhen()方法来决定一个Task的outputs是否为最新的,该方法接受一个闭包作为检查条件,感兴趣的读者可以自行了解。
 
相关文章
|
6月前
|
Java 数据库连接 数据库
在Maven或者Gradle构建配置中添加了必要的依赖
在Maven或者Gradle构建配置中添加了必要的依赖
63 1
|
6月前
|
Java API 项目管理
Java一分钟之-Gradle插件开发:自定义构建逻辑
【6月更文挑战第5天】Gradle插件开发详解:从入门到发布。文章介绍如何创建自定义插件,强调依赖管理、任务命名和配置阶段的理解。示例代码展示插件实现及避免常见问题的方法。最后,讨论插件的发布与共享,助你提升构建效率并贡献于开发者社区。动手实践,打造强大Gradle插件!
132 3
|
5月前
|
Java
graphql dgs springboot gradle学习
https://dgraphql dgs springboot gradle学习
|
6月前
Gradle项目加速构建
Gradle项目加速构建
387 0
|
6月前
|
XML Java Maven
深入Gradle:初识构建自动化的魅力
深入Gradle:初识构建自动化的魅力
|
6月前
|
Java API Maven
Gradle 自动化项目构建-Gradle 核心之 Project
Gradle 自动化项目构建-Gradle 核心之 Project
63 0
|
7月前
|
缓存 IDE Java
Java一分钟之-Gradle:构建自动化工具
【5月更文挑战第16天】本文介绍了Gradle,一个基于Groovy的灵活构建工具,强调其优于Maven的灵活性和性能。文中通过示例展示了基本的`build.gradle`文件结构,并讨论了常见问题:版本冲突、缓存问题和构建速度慢,提供了相应的解决策略。此外,还提醒开发者注意插件ID、语法错误和源代码目录等易错点。掌握这些知识能提升开发效率,使构建过程更顺畅。
122 2
|
7月前
|
XML 缓存 Java
Gradle 构建自动化工具入门
Gradle 构建自动化工具入门
|
人工智能 移动开发 Java
Android Studio插件版本与Gradle 版本对应关系
Android Studio插件版本与Gradle 版本对应关系
2474 0
Android Studio插件版本与Gradle 版本对应关系
|
存储 Java Android开发
Android 开发 - 充分利用Gradle
Android 开发 - 充分利用Gradle
174 2