深入理解Maven依赖管理:MySQL驱动版本冲突案例分析

背景介绍

  1. 我有一个 common 工程,引入了一个版本较高的 MySQL 驱动依赖
xml 复制代码
<dependency>
    <groupId>com.mysql</groupId>
    <artifactId>mysql-connector-j</artifactId>
</dependency>
  1. IDEA 中把 common 工程使用maven插件deploy到远程私有maven仓库
  2. 另一个maven工程A中引入了该common包
xml 复制代码
<dependency>
    <groupId>com.demo</groupId>
    <artifactId>common</artifactId>
    <version>0.0.1-SNAPSHOT</version>
</dependency>
  1. 由于工程A需要使用版本较低的MySQL驱动,所以又引入了一个低版本MySQL驱动依赖(在common包依赖的下方,划重点!!!
xml 复制代码
<dependency>
    <groupId>com.demo</groupId>
    <artifactId>common</artifactId>
    <version>0.0.1-SNAPSHOT</version>
</dependency>

<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.49</version>
</dependency>

问题呈现

  1. 运行工程,调用包含数据库操作的接口,我期望使用低版本依赖,实际使用的是高版本依赖。控制台打印由于MySQL驱动和数据库版本不匹配导致的异常信息
swift 复制代码
java.sql.SQLNonTransientConnectionException: CLIENT_PLUGIN_AUTH is required
	at com.mysql.cj.jdbc.exceptions.SQLError.createSQLException(SQLError.java:110) ~[mysql-connector-j-8.0.31.jar:8.0.31]

可以看到,异常信息来自高版本的MySQL驱动包[mysql-connector-j-8.0.31.jar:8.0.31]

问题分析

  1. 目前工程A中引入了两个MySQL驱动依赖,一个是直接引入的,另一个是通过common包间接引入的,scope标签都未指定,默认为compile
  2. 在工程A的pom.xml文件中引入依赖的顺序是,先引入common包,后引入低版本MySQL驱动包,如背景介绍中第四点所示

maven 解析依赖规则

  1. 路径最短者优先:路径距离是从项目开始到依赖项的距离,直接依赖的距离为0,间接依赖的距离为1,以此类推。路径最短的依赖项会被优先使用
  2. 首次声明者优先:在POM文件中首次声明的依赖项会被优先使用

那么这两个规则哪个优先级更高呢?根据我的实践结果来看,显然第二条优先级更高。

解决办法

  1. 方式一 :在工程A的pom.xml文件中排除高版本的依赖
xml 复制代码
<dependency>
    <groupId>com.demo</groupId>
    <artifactId>common</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <exclusions>
        <exclusion>
            <artifactId>mysql-connector-j</artifactId>
            <groupId>com.mysql</groupId>
        </exclusion>
    </exclusions>
</dependency>

<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.49</version>
</dependency>
  1. 方式二:调换common包和MySQL驱动包的引入顺序
xml 复制代码
<dependency>
    <groupId>mysql</groupId>
    <artifactId>mysql-connector-java</artifactId>
    <version>5.1.49</version>
</dependency>

<dependency>
    <groupId>com.demo</groupId>
    <artifactId>common</artifactId>
    <version>0.0.1-SNAPSHOT</version>
</dependency>
相关推荐
952365 小时前
MyBatis
后端·spring·mybatis
uzong8 小时前
9 种 RAG 架构,每位 AI 开发者必学:完整实战指南
后端
小江的记录本8 小时前
【Kafka核心】架构模型:Producer、Broker、Consumer、Consumer Group、Topic、Partition、Replica
java·数据库·分布式·后端·搜索引擎·架构·kafka
止语Lab8 小时前
从手动到框架:Go DI 演进的三个拐点
开发语言·后端·golang
Daybreak11 小时前
Elasticsearch 里的索引和 Mapping,到底是什么关系?
后端
Lee川11 小时前
Prisma 实战指南:像搭积木一样设计古诗词数据库
前端·数据库·后端
李小狼lee11 小时前
深入浅出sse协议,用代码自己实现
后端
SamDeepThinking12 小时前
并发量就算只有2,该上锁还得上呀
java·后端·架构