拆分Gradle中的所有输出目录

时间:2017-06-15 23:04:34

标签: java gradle build.gradle

Gradle 4.0昨天问世了,我为它更新了我的项目。

现在我收到以下警告:

  

Gradle现在为每种JVM语言使用单独的输出目录,但是   此构建假定来自源的所有类的单个目录   组。此行为已被弃用,并计划删除   在Gradle 5.0中

我想为每种语言使用单独的输出目录。为了实现这一目标,我需要做些什么改变?

我尝试的事情:

  • gradle clean后跟gradle build
  • 删除构建目录,然后运行gradle build
  • 删除gradle并生成目录,然后运行gradle

相关GitHub issue

Gradle插件:

  • 的java
  • 主意
  • org.springframework.boot

4 个答案:

答案 0 :(得分:15)

Gradle 4.0为每种JVM语言引入了多个sourceSet,以便启用远程构建缓存。使用java插件,您的build/classes/main应该变为build/classes/java/mainbuild/classes/test应变为build/classes/java/test等。

您所看到的警告在DefaultSourceSets.java

中定义

因此,如果项目中的任何插件或build.gradle来电DefaultSourceSetOutput.getClassesDir()(或访问classesDir),您都会收到此警告。

解决方案1 ​​

使用

sourceSets.main.output.classesDir = new File(buildDir, "classes/main")

对应于:

@Override
public boolean isLegacyLayout() {
    return classesDir!=null;
}

@Override
public void setClassesDir(File classesDir) {
    setClassesDir((Object)classesDir);
}

@Override
public void setClassesDir(Object classesDir) {
    this.classesDir = classesDir;
    this.classesDirs.setFrom(classesDir);
}

请注意,SourceSetOutput.javagetClassesDir()标记为已弃用。

因此,在项目中的所有插件都获得对Gradle 4.0的支持之前,您应该坚持使用变通方法并忽略弃用警告。

另一个问题是测试文件。 如果您不想使用新版式build/classes/mainbuild/classes/java/test),您也应该调整测试路径:

sourceSets.main.output.classesDir = new File(buildDir, "classes/main")
sourceSets.test.output.classesDir = new File(buildDir, "classes/test")

<强>更新 如果检测到Gradle 4.x,IDEA的用户可能会注意到IDE开始使用单独的out目录进行构建。如果您在IDEA之外运行应用,则无法热门应用重新加载。要修复添加和重新导入:

subprojects {
    apply plugin: 'idea'
    // Due to Gradle 4.x changes (separate output directories per JVM language)
    // Idea developers refuse to reuse Gradle classpath and use own 'out/' directory.
    // Revert to old behavior to allow Spring Devtool to work with using fast Idea compiler.
    // https://youtrack.jetbrains.com/issue/IDEA-175172
    // Alternatively use native Gradle builds or bootRun.addResources = true
    // To use this feature push Ctrl+Shift+F9 to recompile!
    // Be aware that Idea put resources into classes/ directory!!
    idea.module.inheritOutputDirs = false
    idea.module.outputDir = sourceSets.main.output.classesDir
    idea.module.testOutputDir = sourceSets.test.output.classesDir
}

请注意,IDEA会将资源放入与.class文件相同的目录中,因此您的Gradle类路径可能已损坏。对于使用IDEA内置构建命令的模块(Ctrl + Shift + F10等),只需执行gradle clean

答案 1 :(得分:5)

这是由于Gradle 4.0中引入的更改:如果有多个语言源,它现在使用单独的输出目录。

要返回旧行为并删除警告,请将其插入build.gradle:

// Change the output directory for the main source set back to the old path sourceSets.main.output.classesDir = new File(buildDir, "classes/main")

参考:https://docs.gradle.org/4.0/release-notes.html#multiple-class-directories-for-a-single-source-set

答案 2 :(得分:0)

我的情况有点特定,因为使用输出类目录来构造用于命令行执行的类路径条目。但这也许会帮助某人。

我决定串联所有输出目录。我所做的更改是表格

sourceSets.integrationTest.output.classesDir

ext {
    classpathSeparator = System.properties['os.name'].toLowerCase().contains('windows')?";":":"
}
...
sourceSets.integrationTest.output.classesDirs.join(classpathSeparator)

答案 3 :(得分:-1)

例如,如果混合Java,Kotlin和Groovy项目结构应如下所示:

root/
    src/
       main/
            java/
            kotlin/
            groovy/
       test/
            java/
            kotlin/
            groovy/

build.gradle 中,您必须指定特定语言所需的插件。

apply plugin: 'java'
apply plugin: 'groovy'
apply plugin: 'kotlin'