带有多项目Gradle的SpringBoot->主类名称尚未配置,无法解析

Ill*_*dan 1 gradle spring-boot

我有以下项目结构:

RootProject
??? lib
     ??? src
          ??? main
               ??? java
                    ??? ...
??? test-project
     ??? src
          ??? main
               ??? java
                    ??? ...

??? build.gradle
Run Code Online (Sandbox Code Playgroud)

我试图遵循Gradle 最佳实践进行多项目构建,因此我在单个build.gradle文件中描述了整个构建过程。

“ RootProject”只是一个没有任何代码的根项目,其唯一目的是为其子项目“ lib”和“ test-project”提供一个build.gradle。

“ test-project”是一个使用“ lib”作为编译依赖项的SpringBoot项目(微服务)。

我常见的build.gradle如下所示:

plugins{
    id 'java'
    id 'org.springframework.boot' version '2.1.1.RELEASE'
    id 'io.spring.dependency-management' version '1.0.6.RELEASE'
}


allprojects {
    repositories {
        jcenter()
    }
}


subprojects {

    apply plugin: 'io.spring.dependency-management'
    apply plugin: 'org.springframework.boot'

    group = 'com.xxx.yyy'
    version = '1.0'

    sourceCompatibility = 1.8
    targetCompatibility = 1.8
}


project(":lib"){

    apply plugin: 'java-library'

    dependencies {

        implementation group: 'org.springframework.boot', name: 'spring-boot-starter-web'
        implementation group: 'org.springframework.boot', name: 'spring-boot-starter-data-jpa'
        testImplementation group: 'org.springframework.boot', name: 'spring-boot-starter-test'
    }

    bootJar { enabled = false }
    jar { enabled = true }
}

project(":test-project"){

    apply plugin: 'java'

    dependencies {
        implementation group: 'org.springframework.boot', name: 'spring-boot-starter-web'
        implementation group: 'org.springframework.boot', name: 'spring-boot-starter-data-jpa'
        implementation project(":lib")
        implementation ('mysql:mysql-connector-java')
    }
}
Run Code Online (Sandbox Code Playgroud)

成功构建了“ lib”和“ test-project”。但是,当我尝试在根项目上执行“ bootJar”任务(应该在所有子项目上触发“ build”任务)时,出现以下错误:

Main class name has not been configured and it could not be resolved
Run Code Online (Sandbox Code Playgroud)

有任何想法吗?

M.R*_*uti 5

多项目构建最佳实践简介

当你说:

我试图遵循Gradle最佳实践进行多项目构建,因此我在单个build.gradle文件中描述了整个构建过程。

我认为这实际上不是一个好习惯,但这并不是您提到的指南中真正建议

在指南介绍中:

虽然每个子项目都可以完全隔离其他子项目进行配置,但是子项目具有共同的特征是很常见的。因此,通常最好在项目之间共享配置,因此相同的配置会影响多个子项目。

=>实际上,应该在根项目构建的中央位置配置子项目之间共享的共同特征。

在指南的后面(在本节中),有一个示例,该示例在根项目脚本中定义了特定于子项目的配置,但示例说明中有一个注释:

所有构建逻辑都在根项目的构建脚本中。(2)

(2):我们在这里这样做,因为它使布局更加容易。我们通常将项目特定的内容放入各个项目的构建脚本中。

关于你的问题

我假设您的lib项目是一个普通的“简单” java lib项目(没有Spring或SpringBoot依赖项),并且test-project是包含SpringBoot应用程序类(特别是@SpringBootApplication主应用程序类)的项目。按照上述最佳实践,您应该具有三个不同的项目构建脚本:

  • root project:用于在子项目中定义通用配置共享(Java插件配置,存储库,共享依赖项等)
  • lib project:此lib项目的特定配置(java库插件,特定的依赖项,...)
    • 没有理由将spring-boot插件应用于此子项目,这实际上是导致您的错误“找不到主类”的原因
    • 如果该项目依赖于Spring核心模块,则可以简单地应用io.spring.dependency-management插件(在这种情况下,在根项目构建中应用此Dependecy插件是有意义的,以便在两个子项目中使用相同的Spring版本)
  • test-project项目:与Spring Boot应用程序相关的配置(SpringBoot插件和依赖项)

根项目构建

ext{
    slf4jVersion = "1.7.25"
}

subprojects {
    apply plugin: "java"
    // if both subprojects share some Spring related dependencies, apply the Spring `io.spring.dependency-management` here.

    group = 'com.xxx.yyy'
    version = '1.0'

    sourceCompatibility = 1.8
    targetCompatibility = 1.8

    repositories {
        jcenter()
    }
}
Run Code Online (Sandbox Code Playgroud)

'lib'项目构建

plugins{
    id 'java-library'
}

dependencies {
    implementation group: 'org.slf4j', name: 'slf4j-api', version: slf4jVersion
    // lib dependencies
}
Run Code Online (Sandbox Code Playgroud)

“测试项目”构建

plugins {     
    id "org.springframework.boot"  version "2.1.1.RELEASE"
}
apply plugin: 'io.spring.dependency-management'

dependencies {
    implementation project(":lib")
    implementation('org.springframework.boot:spring-boot-starter-web')
    testImplementation('org.springframework.boot:spring-boot-starter-test')
    implementation ('mysql:mysql-connector-java')
    // ...
}
Run Code Online (Sandbox Code Playgroud)

根据您的评论进行编辑:如果lib项目需要与Spring Data相关的内容,请应用io.spring.dependency-management以下内容(请参阅Spring参考指南中的更多详细信息)

plugins{
    id 'java-library'
    id "org.springframework.boot"  version "2.1.1.RELEASE" apply false
}
apply plugin: 'io.spring.dependency-management'

dependencyManagement {
    imports {
        mavenBom org.springframework.boot.gradle.plugin.SpringBootPlugin.BOM_COORDINATES
    }
}

dependencies {
    implementation group: 'org.slf4j', name: 'slf4j-api', version: slf4jVersion
    implementation 'org.springframework.boot:spring-boot-starter-data-jpa' 
    // lib dependencies
}
Run Code Online (Sandbox Code Playgroud)

  • 正如我在回答中所说的那样,如果您需要在lib中使用一些与Spring相关的deps,则只需应用io.spring.dependency-management插件,而不是spring-boot插件即可。我更新了答案。 (3认同)
  • “lib”是一个具有处理 JPA 的“通用”(例如可重用)代码的库。因此,“lib”需要在 Spring 中具有依赖性,但它不打算执行。第二个项目(“test-project”)引用(“lib”)作为编译依赖项,并打算执行(spring boot) (2认同)