美文网首页IT修真院_JAVA
maven 依赖传递和版本冲突

maven 依赖传递和版本冲突

作者: tzr | 来源:发表于2017-08-30 10:25 被阅读315次

    大家好,我是IT修真院北京分院第22期的学员童志荣,一枚正直纯洁善良的java程序员。


    maven依赖传递和版本冲突的解决_腾讯视频

    PPT戳这里

    一、背景介绍

    如果 Maven 的依赖构建必须每一个项目都指定,那配置是累死人了,比如A依赖了20个项目,B依赖A,那么还要添加20个项目,那就悲剧了,所以 maven有依赖传递的功能。

    二、知识剖析

    Maven采用“最近获胜策略(nearest wins strategy)”的方式处理依赖冲突。

    换句话说,如果一个项目依赖于相同artifact的多个版本,在依赖树中离项目最近的那个版本将被使用。

    三、常见问题

    现在有一个web应用resolve-web。

    4个jar包:project-A,project-B,project-C,project-Common

    resolve-web 依赖于project-A和project-B,

    project-A依赖于project-common的1.0版本,调用了其中的sayHello()方法。

    project-B依赖于project-C,而project-C又进一步依赖于project-common的2.0版本,并调用其中的sayGoodBye()方法。

    project-common的1.0和2.0版本唯一区别在于,1.0中包含sayHello()方法,而2.0中包含了sayHello()和sayGoodBye()两个方法。

    根据Maven的依赖传递机制,resolve-web将同时依赖于project-common的1.0和2.0版本,这就造成了依赖冲突。

    而根据最近获胜策略,Maven将选择project-common的1.0版本作为最终的依赖。

    对于Maven 来说,由于proejct-common的1.0版本比2.0版本在依赖树中离resolve-web更近,故1.0版本获胜。

    在resolve-web中执行"mvn dependency:tree -Dverbose"可以看到resolve-web的依赖关系:

    可以看到,project-common:project-commmon:jar:2.0被忽略掉了。

    此时在resolve-web的war包中将只包含project-common的1.0版本。

    所以现在就产生问题了。由于project-common的1.0版本中不包含sayGoodBye()方法,而该方法正是project-C所需要的,所以运行时将出现“NoSuchMethodError”。

    四、解决方案

    方法1:显式加入对project-common 2.0版本的依赖。

    先前的2.0版本不是离resolve-web远了点吗,那我们就直接将它作为resolve-web的依赖,这不就比1.0版本离resolve-web还近吗?

    在resove-web的pom.xml文件中直接加上对project-common 2.0 的依赖:

    方法2:resolve-web对project-A的dependency声明中,将project-common排除掉。在resolve-web的pom.xml文件中修改对project-A的dependency声明:

    五、编码实战

    六、扩展思考

    七、参考文献

    http://www.cnblogs.com/davenkin/p/advanced-maven-resolve-dependencies-conflicts.html

    八、更多讨论

    相关文章

      网友评论

        本文标题:maven 依赖传递和版本冲突

        本文链接:https://www.haomeiwen.com/subject/nrmzdxtx.html