Maven 依赖冲突:快照没有优先级



当依赖树中存在冲突(相同的工件但不同的版本)时,AFAIK,Maven将通过选择最高版本的依赖关系来解决冲突,并将省略"旧"版本。

但是,当较新的版本是快照时,显然它将选择较旧的稳定版本而不是快照。

在我的情况下:一些工件:0.5.0-快照(因与 0.4.0 冲突而省略)=> 版本 0.4.0 被选中而不是想要的 0.5.0-SNAPSHOT。

我假设此功能按设计运行,但我不明白原因。除此之外,是否知道是否有办法告诉 Maven 在稳定版本上获取快照?

你关于Maven总是选择最高版本的假设是不准确的。工件的选择基于许多因素,包括树中依赖项的深度、树中的顺序、依赖项是快照还是发布,以及依赖项管理,这几乎覆盖了其他所有内容。

不幸的是,我不知道任何关于Maven依赖解析算法的明确信息来源。你会发现它的零碎散落在各处。一些方便的参考:

    依赖
  • 关系机制简介概述了该主题,其中有一个很好的(如果简短)部分,介绍了传递依赖关系以及如何从依赖关系树中选择它们。
  • Sonatype Maven 一书有一个更全面的项目依赖关系部分,这将增加你对该主题的了解。
  • 同一本书的前面部分讨论了项目版本,它与这个问题密切相关,并且有一个关于快照版本的很好的部分,尽管没有我希望它们如何在依赖关系解析中发挥作用。
  • 项目
  • 关系讨论坐标系以及项目继承如何影响要包含的依赖项。
  • 最后,POM 参考是几乎所有与 pom 相关的事物的良好起点。每个pom元素至少有一个简短的描述,可以帮助你理解足够的信息,以便能够有效地开始搜索更多信息。

至于一些实用的建议,mvn dependency:tree 的输出对于发现为什么选择特定版本的依赖项非常有用。它甚至经常会告诉你"foo:bar:1.2(was 1.1)"。确定错误版本的来源后,有多种方法可以确保将特定的依赖项版本用于项目:

  • 从导致它们包含在生成中的其他依赖项中排除版本控制错误的依赖项。
  • pom 添加显式顶级依赖项,而不是依赖于传递依赖项。
  • 在 pom 的dependencyManagement部分中列出依赖项(从此链接向下滚动一点),以强制依赖项具有指定的特征,无论它是什么级别的传递依赖项。 请谨慎使用此选项,因为dependencyManagement是病毒式的,因为依赖于您的项目的其他项目将被您的依赖项管理"感染"。在pom参考中还有一个关于依赖关系管理的很好的部分。

如果 0.4.0 版本通过 POM 中的另一个依赖项作为传递依赖项拉入,那么您应该能够排除它。 dependency:tree目标应该可以帮助您了解这是否正在发生。

Maven 旨在支持发布版本而不是快照版本。我不确定为什么您会在同一个 POM 中有两个依赖项,并且无法通过删除一个来解决冲突,所以我假设其中一个依赖项是从父 pom 继承的。在这种情况下,您可以将继承的依赖项设置为 <optional>true</optional>我认为它应该允许子 POM 覆盖它,即使使用较低的版本也是如此。

如果这不起作用,则糟糕/黑客的解决方案 - 以这样一种方式编辑您的本地存储库,使其没有意识到 0.5.0 版本是快照(如果您有能力,甚至可以编辑您的私有 Nexus 存储库)

最新更新