Maven:如何覆盖依赖项

时间:2018-08-03 07:00:52

标签: java maven dependency-management

我的情况有点奇怪:

工件ID为​​:绒球中的yyy的依赖关系(如下所示)具有依赖关系:

<dependency>
   <groupId>javax.servlet</groupId>
   <artifactId>javax.servlet-api</artifactId>
   <version>2.5</version>
</dependency>

所以问题是我需要在当前模块中使用3.1.0版本,因为它具有额外的功能:

<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.1.0</version>
</dependency>

我已经尝试了页面上的示例中说明的排除标记和依赖性管理标记:Maven: how to override the dependency added by a library

它不起作用。我还阅读并尝试了本文中的3个示例:https://spring.io/blog/2016/04/13/overriding-dependency-versions-with-spring-boot

它也不起作用。因此,我要做的是重新排序我的pom依赖关系,以使3.1.0早于带有工件yyy的pom依赖,并且我很高兴它成功地完成了全新安装的工作。我的幸福是短暂的,因为在全新安装后pom会自动重新排序,而3.1.0会自动重新排序到yyy以下。这意味着下一个版本将再次使用2.5并失败。

我的pom结构片段如下:

<dependencies>
  <dependency>
    <groupId>xxxx.xxx.xxxx</groupId>
    <artifactId>yyy</artifactId>
    <version>1.0.0</version>
  </dependency>
  <dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.1.0</version>
  </dependency>
<dependencies>

2 个答案:

答案 0 :(得分:0)

  

我的幸福是短暂的,因为经过全新安装的pom   自己重新排序,并且3.1.0自动重新排序   低于yyy。这意味着下一个版本将再次使用2.5并失败。

请注意,javax.servlet:javax.servlet-api必须包含在WAR中,但只能包含在包含并引导servlet容器的独立JAR中。
如果构建标准WAR,则必须使用服务器提供的依赖项。因此,应使用provided范围声明依赖项。

  

我已经尝试了排除标签和依赖管理标签的解释   在页面上的示例中:Maven:如何覆盖依赖项   由图书馆添加

dependencyManagement在这里将毫无帮助,因为该问题与您在dependencyManagement元素之外包含的依赖项有关。
但是在exclusions声明中使用dependency选项是正确的方法。如果以此方式使用,则应排除2.5工件的javax.servlet-api版本:

<dependencies>
  <dependency>
    <groupId>xxxx.xxx.xxxx</groupId>
    <artifactId>yyy</artifactId>
    <version>1.0.0</version>
    <exclusions>
      <exclusion>
        <artifactId>javax.servlet</artifactId>
        <groupId>javax.servlet-api</groupId>
      </exclusion>
    </exclusions>
  </dependency>
  <dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.1.0</version>
  </dependency>
</dependencies>

如果问题仍然存在,则意味着该依赖关系可能已由另一个依赖关系拉动。
一些提示通常有助于发现这一点:

  • 检查是否不使用WAR叠加功能。但是这里不太可能,因为您仅检索到1个版本的依赖项

  • 在WAR项目上使用mvn dependency:tree检查所有提取的依赖项。
    为了简化可读性,您还可以按以下方式进行过滤:
    mvn dependency:tree -Dincludes=javax.javax.servlet-api

答案 1 :(得分:0)

以下解决方案已忽略版本2.5,因此它可以正常工作。但是我不知道这意味着什么。它会删除其他依赖项吗?请用简单的英语解释groupId和artifactId中的星号的含义。我想知道这些风险,因为我使用的是多模块系统,其中其他依赖项中有许多嵌套的依赖项。到目前为止,我将继续进行研究,但是如果有人可以解释,请这样做。谢谢

    <dependencies> 
      <dependency>
         <groupId>xxxx.xxx.xxxx</groupId>
         <artifactId>yyy</artifactId>
         <version>1.0.0</version>
         <exclusions> 
            <exclusion> 
              <groupId>javax.servlet</groupId>  // this works or 
              <groupId>*</groupId> // this works
              <artifactId>*</artifactId> // this part was a mandatory *
            </exclusion> 
         </exclusions> 
      </dependency> 
      <dependency>
         <groupId>javax.servlet</groupId>
         <artifactId>javax.servlet-api</artifactId>
         <version>3.1.0</version>
      </dependency>
    </dependencies>