依赖pipe理和范围

我通常在parent-project/pom.xml放置一个<dependencyManagement>部分。 这个<dependencyManagement>部分包含像这样的子模块(即没有<scope>元素)的所有依赖关系的声明和版本:

 <dependencyManagement> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.10</version> </dependency> </dependencies> </dependencyManagement> 

在所有的子模块(即moduleX / pom.xml)中,我有:

  <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <scope>test</scope> </dependency> </dependencies> 

显然,在这个例子中,我为同一个依赖重复了<scope>test</scope>多次(每个子模块需要junit一次)。

我的问题是:有关<scope>声明的最佳实践是什么? 将它放在<dependencyManagement>会更好吗? 或者是最好把它放在子模块的<dependencies>部分(如在这篇文章中)? 为什么? 这个问题有什么明确的答案吗?

晚会有点迟,但我会加两分钱。 我最近遇到了一个很难debugging的问题。 我有一个父POMpipe理跨多个项目的依赖关系。 我设置了它们之间通用的所有依赖关系,包括groupId,artifactId,版本和最常见的范围 。 我的想法是,如果符合最常见的范围 ,我不必在每个项目的实际依赖项部分中包含范围 。 当一些依赖显示为传递依赖时,问题就出现了。 例如,如果

  • A在编译范围上依赖于B.
  • B在编译范围上依赖于C.
  • C设置为在父项的依赖pipe理中提供

那么A的传递依赖于C被确定提供。 我不确定这是否合理,但肯定是令人困惑的。

无论如何,保存你的麻烦,并离开你的依赖pipe理范围。

dependencyManagement就是在这里为所有项目子模块定义依赖项版本,本节中唯一相关的范围是对于BOM的import

范围必须在dependencies部分定义。

(对于一个给定的依赖关系,它决定了使用上下文,它只允许在需要执行的时候包含依赖关系,例如,耳朵不会被包装在Java-ee依赖关系( provided作用域)中,因为它可以在目标上find它们服务器。)

[编辑]

第一个语句有一个例外,在dependencyManagement部分provided的范围将覆盖dependencyManagement部分中定义的范围。 请参阅依赖pipe理来强制范围

对于任何范围,向依赖项pipe理添加单个依赖项没有任何好处。 你所拥有的就是重复。 如果您希望版本可configuration,请添加一个属性并将其用于依赖项中:

 <properties> <junit.version>4.10</junit.version> ... <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>${junit.version}</version> </dependency> </dependencies> 

但是,在某些情况下,依赖关系pipe理会发光 – 当您使用boms来编排大量工件的版本时,比如使用特定版本的Java EE实现:

 <dependencyManagement> <dependencies> <dependency> <groupId>org.jboss.bom</groupId> <artifactId>jboss-javaee-6.0-with-tools</artifactId> <version>${javaee6.with.tools.version}</version> <type>pom</type> <scope>import</scope> </dependency> .... 

和其他答案一样,最好的做法是将范围从dependencyManagement中排除,并在定义依赖关系时明确指定它。 这是一个罕见的情况,你会想在不同的作用域中使用不同版本的相同的依赖关系,例如,在编译你的应用时需要一个版本,而在运行时需要另外一个版本 – 我能想到的唯一情况是你想明确地运行你的在用户使用该版本而不是您指定的版本的情况下,针对不同版本的库进行testing。

如果您在dependencyManagement中定义了作用域,那么它将该版本的使用仅限制在定义的作用域中,因此任何其他作用域都将随机select一个依赖关系。 我昨天遇到了这个问题,我们在dependencyManagement中定义了junit 4.12和test scope,但是我们常用的testing框架模块使用了junit和编译范围,所以它select了4.8.2版本。