我目前正在尝试解决一个问题,根据 Gradle 文档,这个问题不应该发生。
我正在开发一些 Spring Boot 项目,并创建了一个单独的 git 存储库,其中包含许多具有共享构建逻辑的 Gradle 插件。
为了简单起见,假设我有一个插件
my-api
,它声明了对 Spring Cloud OpenFeign 的依赖:
plugins {
`java-library`
// ...
}
dependencies {
implementation("org.springframework.cloud", "spring-cloud-starter-openfeign", "4.1.0")
// ...
}
和一个不同的插件
my-application
,它使用 Spring Boot:
plugins {
// Version is declared in build.gradle.kts of the plugin project, and is currently "3.2.2"
id("org.springframework.boot")
// ...
}
dependencies {
implementation("org.springframework.boot", "spring-boot-starter")
// ...
}
这些插件发布到内部存储库以及 mavenLocal。
然后,在另一个存储库中,我正在将 Spring 应用程序开发为具有两个模块的多模块项目:
foo-application
和 foo-api
。前者依赖于后者,并且它们都应用各自的插件。内部存储库和 mavenLocal 都被标记为插件存储库。
问题是 OpenFeign 4.1.0 提供了对 Spring Boot 3.2.0 的传递依赖。 Gradle 足够聪明,可以将版本强制为声明的最新版本,如
dependencies
任务的输出所示:
+--- org.springframework.cloud:spring-cloud-starter-openfeign:4.1.0
| +--- org.springframework.cloud:spring-cloud-starter:4.1.0
| | +--- org.springframework.boot:spring-boot-starter:3.2.0 -> 3.2.2
但是,另一个仍然挂在那里并污染我的类路径: 这真的很烦人,因为现在我有 2 组源,并且“搜索无处不在”窗口中的所有 Spring 内容都是重复的。
这与 Gradle 文档直接相反:
我确保插件确实是罪魁祸首,并且删除依赖项“修复”了问题。不过,我很想找到一个更可行的解决方案。
api
配置中出现的依赖关系将传递给库的使用者,因此将出现在使用者的编译类路径中。另一方面,在implementation
配置中找到的依赖项不会暴露给消费者,因此不会泄漏到消费者的编译类路径中。
implementation
依赖项应用。在 api 端,它实际上被正确隐藏,但在应用程序端,即
dependencies
输出的实际来源,它仍然作为常规依赖项挂在那里。现在找出仅在应用程序端排除这些传递依赖项的最佳方法。