【发布时间】:2019-12-19 18:05:31
【问题描述】:
我想创建一个项目,其构建过程包括一些代码生成。生成的代码在编译时依赖于主代码(它扩展了一个公共基类)和来自 JCenter 的模块。主代码实际上对生成的代码具有运行时依赖性;也许更正确的说法是应用程序对主代码和生成代码以及两者的模块依赖项都有运行时依赖。
编辑:为了使依赖关系更清晰,这是一个伪劣的图表,其中箭头从配置指向它所依赖的东西。如您所见,依赖图中没有循环。
main compile ← generated compile → generated module
↑ ↑
main runtime → generated runtime
我真的很想将生成的代码放在主代码的单独源集中。我也很想用应用插件,提供gradle run和gradle installDist。
我使用的是最新的 Gradle 3.3。
我创建了一个project to try this。其中,源集是:
sourceSets {
generated {
java {
srcDirs = ["$buildDir/src/generated/java"]
compileClasspath += sourceSets.main.output
}
}
main {
java {
runtimeClasspath += sourceSets.generated.output + sourceSets.generated.runtimeClasspath
}
}
}
还有一个任务是生成代码:
task generateSource {
doLast {
// generate the code into sourceSets.generated.java.srcDirs[0] here
}
}
compileGeneratedJava.dependsOn generateSource
生成的代码的生成和编译工作正常。如果我说gradle generatedClasses,它会编译主代码,生成源代码,然后编译生成的代码。
但是,运行和分发都不能正常工作。如果我说gradle run,它不会尝试生成或编译生成的代码。如果我说gradle generatedClasses run,那么生成的代码会生成并编译,但不会添加到已执行 Java 进程的类路径中。如果我说gradle installDist,那么它不会尝试生成或编译生成的代码,同样,如果我说gradle generatedClasses installDist,生成的代码会生成并编译,但不包含在分发中。
生成的源集的模块依赖也不包含在类路径或分发中。
真正奇怪的是,如果我用自己的运行任务版本定义:
task runProperly(type: JavaExec) {
classpath = sourceSets.main.runtimeClasspath
main = mainClassName
}
效果很好!
那么,为什么编译的类和生成的源集的模块依赖项都没有包含在运行或分发类路径中?
【问题讨论】: