我有一个Gradle项目,有两个子项目。父级不包含任何代码;所有Kotlin代码都在这两个子项目中。所有Gradle构建文件都是在Kotlin DSL中定义的。
构建后,Gradle生成两个JAR文件,一个在每个子项目的build
子文件夹中。我相信这是Gradle的默认行为。但这不是我想要的。
我想将父项目的JAR文件作为Maven工件发布。因此,我需要将两个子项目都包含在一个JAR文件中。我怎样才能做到这一点?
注意:在这个网页上,作者似乎在这个代码片段中实现了我所需要的东西:
apply plugin: "java"
subprojects.each { subproject -> evaluationDependsOn(subproject.path)}
task allJar(type: Jar, dependsOn: subprojects.jar) {
baseName = 'multiproject-test'
subprojects.each { subproject ->
from subproject.configurations.archives.allArtifacts.files.collect {
zipTree(it)
}
}
}
artifacts {
archives allJar
}
然而,这是在Gradle的原生Groovy DSL中定义的。我发现自己无法将其翻译成Kotlin DSL。我试图在Kotlin构建文件(*.gradle.kts
(之外添加一个Groovy构建文件(*.gradle
(,但这导致了一个奇怪的构建错误。我不确定是否支持混合构建文件语言。此外,我也认为这是不好的做法。最好只用一种语言定义所有生成文件。
此外,上面的例子与Java编程语言有关。但我不认为这会是一个大问题,因为Java和Kotlin都会生成JVM字节码作为编译输出。
更多澄清:
- 我不是在说;胖JAR";。依赖项和Kotlin库而不是应该包含在JAR中
- 我不在乎子项目的JAR文件是否仍在构建中。我只对包含两个子项目的集成JAR感兴趣
- 重点是获得二进制文件的组合JAR。源代码和JavaDoc的组合JAR是一个不错的选择,但不是严格要求的
我会使用Gradle指南创建"uber";或";脂肪;以Gradle文档中的JAR为基础。你想要的基本上是一样的。它也比您发现的Groovy示例好得多,因为它没有使用不鼓励使用的subprojects
util或需要了解其他项目如何配置的"简单共享"。
-
创建用于解析其他项目的配置。
// build.gradle.kts val mergedJar by configurations.creating<Configuration> { // we're going to resolve this config here, in this project isCanBeResolved = true // this configuration will not be consumed by other projects isCanBeConsumed = false // don't make this visible to other projects isVisible = false }
-
使用新配置来添加对我们想要添加到组合Jar 中的项目的依赖项
dependencies { mergedJar(project(":my-subproject-alpha")) mergedJar(project(":my-subproject-beta")) }
-
现在从文档中复制指南,但我们可以使用
mergedJar
配置,而不是使用configurations.runtimeClasspath
,它只会创建我们指定的子项目。然而,我们需要做一些修改。
- 我已经调整了这个例子来编辑现有的Jar任务,而不是创建一个新的"fatJar"任务
- 由于某种原因,设置
isTransitive = false
会导致Gradle无法解析。相反,我添加了一个过滤器(it.path.contains(rootDir.path)
(,以确保我们正在使用的Jars在项目中
tasks.jar { dependsOn(mergedJar) from({ mergedJar .filter { it.name.endsWith("jar") && it.path.contains(rootDir.path) } .map { logger.lifecycle("depending on $it") zipTree(it) } }) }