为什么Maven依赖的顺序很重要?

Eld*_*rry 52 spring jersey maven

我认为Maven依赖关系的顺序以前并不重要,并认为这是它的专家.这是我以前pom.xml的依赖:

<dependencies>

    <dependency>
        <groupId>org.glassfish.jersey.containers</groupId>
        <artifactId>jersey-container-servlet</artifactId>
        <version>2.19</version>
    </dependency>

    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-web</artifactId>
        <version>4.1.7.RELEASE</version>
    </dependency>

    <dependency>
        <groupId>org.glassfish.jersey.ext</groupId>
        <artifactId>jersey-spring3</artifactId>
        <version>2.19</version>
    </dependency>

    <dependency>
        <groupId>org.glassfish.jersey.media</groupId>
        <artifactId>jersey-media-moxy</artifactId>
        <version>2.19</version>
    </dependency>

</dependencies>
Run Code Online (Sandbox Code Playgroud)

它运作良好,今天我想将弹簧依赖性移到底部,以便那些相关的球衣可以在一起.然而,我不能再让它工作了,我的Jetty抱怨道:

[ERROR] Failed to execute goal org.eclipse.jetty:jetty-maven-plugin:9.3.0.M1:run (default-cli) on project mtest: Execution default-cli of goal org.eclipse.jetty:jetty-maven-plugin:9.3.0.M1:run failed: A required class was missing while executing org.eclipse.jetty:jetty-maven-plugin:9.3.0.M1:run: org/apache/commons/logging/LogFactory
Run Code Online (Sandbox Code Playgroud)

这真的令人困惑,所以我必须关注依赖顺序吗?我怎么知道正确的订单?

kry*_*ger 79

依赖的顺序的事情,因为Maven的是如何解析传递依赖,从2.0.9版本.摘自文档:

(...)这确定在遇到多个版本的工件时将使用哪个版本的依赖项.(...)您可以通过在项目的POM中明确声明版本来保证版本.(...)从Maven 2.0.9开始,它就是声明中的顺序:第一个声明获胜.

  • 我不确定为什么这个答案被低估了.它至少部分地回答了为什么声明的顺序很重要的问题. (4认同)
  • 请注意,Maven 首先选择与您的项目“最接近”的工件版本。只有当两个不同版本同样接近时,才会使用该顺序来解决冲突。 (3认同)

Kyl*_*ull 17

要扩展另一个答案(声明声明顺序会影响Maven对传递依赖的依赖性中介),可以使用一些工具:

  • mvn dependency:tree [-Dscope=[runtime|test]]将显示所选范围可用的依赖项. 详情请见此处
  • mvn dependency:build-classpath为您提供类路径中可用依赖项的顺序(如果两个或多个类路径条目具有相同的类,则前一个获胜). 详情请见此处

我对你的情况了解不多,但通常情况下你会在编译/运行时使用1个或更多jar的错误版本. 声明自己的库版本有问题或版本锁定下来<dependencyManagement>是选择这里.

现在回答您的另一个问题 - 在声明依赖关系时,您如何知道正确的顺序是什么?

我的建议 - 正确的声明顺序是按照您希望的顺序为您提供所需依赖项的版本的顺序.使用上面的工具检查您的依赖关系,并在必要时调整声明的顺序.

请注意,大多数jar包含不相关命名的类,因此jar类在类路径中出现的确切顺序通常并不重要.我注意到的唯一例外是SLF4J中的一些jar,它们故意影响它要替换的其他记录器库中的类.