首页 > 解决方案 > 如何在 Gradle 中创建可传递的分层多项目?

问题描述

我使用 Gradle 已经有一段时间了,但从未深入研究过它的许多特性和功能,但前几天我决定将我的 Java 项目拆分为两个模块,以便于测试和维护。完成后,我开始阅读有关Authoring Multi-projects和名为Composite builds的较新 Gradle 概念之一。然后我开始花费一天的大部分时间尝试应用(我认为我理解的)这些知识来使我的项目模块化。可以肯定地假设我没有成功,现在我在这里寻求帮助以理解这些概念及其应用。

理论工作区

让我们假设我们有以下目录结构:

toolbox
|
├── first-tool
|   └── build.gradle
|
├── second-tool
|   └── build.gradle
|
├── build.gradle
└── settings.gradle

这些是根目录中的项目:

Root project 'toolbox'
+--- Project ':first-tool'
\--- Project ':second-tool'

让我们让项目first-tool引入一个外部依赖org.master-toolbox:some.other.tool项,第二个工具箱依赖于该外部依赖项,但不实现自身:

default - Configuration for default artifacts.
+--- org.master-toolbox:some.other.tool:1.0
|    +--- ...
\--- io.toolbox:first-tool

这些是相关的 Gradle 文件:

设置.gradle

rootProject.name = 'toolbox'

include 'first-tool', 'second-tool'

工具箱.build.gradle

allprojects {

    apply plugin: 'java-library'

    group = "io.toolbox"

    repositories {
        jcenter()
    }
} 

第一个工具.build.gradle

dependencies {
    // This is an external dependency that is resolved through jcentral
    implements 'org.master-toolbox:some.other.tool:1.0'
}

第二个工具.build.gradle

dependencies {
    // Try to implement first-tool build to inherit dependencies
    implementation 'io.toolbox:first-tool'
}

如上所示,上面生成了一个不错的项目结构,但由于second-tool找不到,因此无法完全工作,first-tool并且我们的控制台中会出现类似于以下错误的内容:

> Could not resolve all files for configuration ':second-tool:compileClasspath'.
   > Could not find io.toolbox:first-tool:.
     Required by:
         project :second-tool

现在据我了解,这是假设复合构建突入并通过允许我们包含整个构建来节省时间的地方。听起来不错,让我们更新一下settings.gradle

rootProject.name = 'toolbox'

includeBuild `first-tool`
include 'second-tool'

现在项目构建和编译正常,一切都很好,对吧?不完全是,因为includeBuild在 our 中使用关键字settings.gradle first-tool不再从继承属性,toolbox并且基本上不再是toolbox.

项目目标

我很可能误解了复合构建的整个概念,或者只是犯了愚蠢的错误。无论哪种方式,我想知道的是,是否有任何方法可以使具有相互依赖的子项目的分层多项目结构?

就目前而言,我必须在以下选项之间进行选择:

如果有可能有一个build.gradle位于顶层项目根目录的 main 并为整个层次结构定义通用插件、存储库、组等,那就太好了。然后其他项目将拥有自己的build.gradle文件,这些文件将赋予它们独特的属性,但会从顶级项目执行它们的任务。

我已经阅读了有关此主题的官方文档,因此我正在寻找有关如何实现此特定目标的更具体的解释和指导。

标签: gradlebuild.gradle

解决方案


通过多模块构建,一个模块可以依赖于另一个模块。要让第二个项目依赖于第一个项目,请编辑second-tool/build.gradle为:

dependencies {
    implementation project(':first-tool')
}

此外,第一个模块可能应该是:

dependencies {
    api 'org.master-toolbox:some.other.tool:1.0'
}

您可以使用多模块构建来执行您描述的操作;allprojects { ... }您可以拥有模块间依赖关系,并且可以使用或来从顶层构建中配置模块subprojects{ ... }

很少使用复合构建 - 如果您对“单一”构建感到满意,并且不需要将代码拆分到不同的存储库中。等等,然后使用(普通)多模块构建。


推荐阅读