Force Maven仅使用第一级依赖项

我有一个Maven Java项目。 在编译项目时,我不希望通过一系列子依赖项偶然满足我的项目依赖项。 在构建最终战争时,当maven必须检查所有使用的依赖项并为战争添加必要的lib时,这是可以的,但是在编译代码时我想确保只使用直接依赖项。 为什么?

假设我有两个依赖项:

 com.package module-1   com.package module-2  

对于我们的项目模块-1和模块-2提供完全不同的目的,但在模块-2的依赖树中的某处,使用模块-1。 我删除了module-1依赖项,但maven继续构建我的项目而没有编译错误,因为它从module-2子依赖项中解析了module-1。 这种变化没有被注意到。

一段时间后我们决定删除module-2,因为我们不需要它。 很奇怪,但我们不能再使用从模块1导入的编译类,并且没有连接到模块2逻辑。

这是一个简单的案例,但在大项目中,这可能会造成相当大的依赖性。

您可以使用Maven依赖项插件目标“dependency:analyze”为您提供未在当前模块上声明的所有已使用依赖项的报告(包含传递)。 那样Maven仍然会使用传递依赖(我猜不知道),但你可以通过插件强制自己确保这些也被声明。 它还会警告您不必要的依赖。 介意,插件分析编译的类。 有时,您可能需要配置插件,因为有时它可能无法在编译时检测到需要依赖项,而不是在运行时,例如因为内联常量。

如果您确实需要这样做,那么您可以在pom中设置排除项。

例如,这是我的一个poms中的排除示例,我不希望它自动获取公共日志记录,因为我正在使用不同的日志记录提供程序。

   org.springframework spring-context ${org.springframework-version}    commons-logging commons-logging    

你可以这样做(未经测试)

  com.package module-2   com.package module-1    

我不一定会推荐这个。 在我的日志记录排除的情况下这是有道理的,因为我使用slf4j而不是公共日志记录。 我已经看过其他例子,如果整个项目使用弹簧3,则用于排除弹簧2。

从你的例子中说出来有点困难,因为它太模糊了。 通常,您应该将依赖关系保持在最低限度。 如果module-2依赖于module-1,那么它意味着你的应用程序不会在没有module-1的情况下编译或运行。 事实上,如果没有它,它可以幸福地生活,那么它并不是真正的依赖。

作为旁注,有一点令人担忧的是你没有针对依赖项的版本号。 你可能会发现maven警告你这件事。 始终包含版本号是一种很好的做法。 如果您依赖于当前正在开发的模块,那么您应该在版本上使用.SNAPSHOT后缀来获取该版本的最新版本。

似乎没有办法告诉maven不要过渡地解决依赖关系: 如何排除Maven依赖关系的所有传递依赖关系 。 我认为其中一个原因是,当用户发现某些工件未在运行时解析或存在工件版本问题时,用户很快就会遇到运行时故障。 但是,如果检查链接,则可以使用通配符排除模式使每个dep’独立’。

另一个选择是为每个module-X子依赖项使用依赖项。 这将确保项目编译和非module-X将被传递解决。 喜欢:

  com.package module-1 true  

尽管如此,分析依赖树可能是最安全和可预测的选择。

你打算做什么听起来有点奇怪。 在某种程度上,您破坏了您想要使用的依赖关系管理。

如果你的module-2依赖于module-1并且依赖于它,那么依赖于module-2的任何模块只需要定义那个模块。

您可以使用排除限制分辨率的深度: 排除单个依赖关系的所有传递依赖关系

较新版本的maven允许使用通配符。

但是:你需要重新添加你真正需要的那些,这是通过重复你有其他模块的依赖。 这复制了工作。

如果存在导致怪异的工件,则可以定义范围: http : //maven.apache.org/guides/introduction/introduction-to-dependency-mechanism.html因此它也不会传播到依赖模块。