Mapper解析

你有没有好奇过,使用Mybatis时,为什么我们只需定义接口及xml文件即可完成数据库操作?今天这篇文章就带大家一起来探索一下这个过程,我将从Mapper的解析、调用两方面进行叙述,发车~~~

一、Mapper解析

Mapper解析时主要完成两个任务,一是将Mapper注册至Mapper映射表mapperRegistry中,二是将注解sql、XML sql解析为mappedStatements。

因为mybatis在配置mapper扫描时有不同的方式,所以在完成Mapper的解析时也有所不同,但本质上还是不变的。

当按包路径、类路径进行扫描时,解析Mapper配置内容的统一入口为MapperAnnotationBuilder,而按resource、url进行扫描时,解析Mapper配置内容的统一入口则为XMLMapperBuilder。

以下为不同情况的Mapper配置内容解析调用链。

1、按包路径、类路径进行扫描

一旦 Mapper 注册完成,就由 MapperAnnotationBuilder.parse() 接管:既能解析接口上的注解SQL,也能在命名空间一致时加载并解析 XML,二者在底层通过 LanguageDriver 统一收敛为 SqlSource 。

2、按resource、url进行扫描

可以看出,上述两种场景下解析sql内容,前者的入口为MapperAnnotationBuilder,在解析过程中会调用XMLMapperBuilder,而后者则直接调用XMLMapperBuilder进行解析。那这么做是为什么呢?

  • 扫描 package 时,入口是接口而不是 XML 文件。系统只"知道一堆接口",所以必须以接口为主导,用 MapperAnnotationBuilder 做"总协调":既解析方法注解,也"按约定"去找同名 XML 并调用 XMLMapperBuilder 解析。也就是说,MapperAnnotationBuilder 既负责解析注解,又以约定方式"发现并解析"同名 XML,最终把所有 SQL 收敛到 MappedStatement 。
  • 扫描 resource 时,入口就是一个已知的 XML 文件。既然资源已经明确,直接构造 XMLMapperBuilder 读取并解析 XML,完全不需要经过接口协调器。也就是说,XMLMapperBuilder 直接解析 XML 中的 SQL,必要时把命名空间绑定到接口,保证执行期代理与语句能对上号。

这下,我们就知道了,当只提供"接口所在包"时,框架需要一个"总协调器"从接口视角整合注解与 XML;而当明确给了"XML 文件路径"时,框架就可以直奔主题进入 XML 解析器。这是 MyBatis 为兼容"注解 Mapper + XML Mapper + 接口配套 XML"三种使用姿势而做出的清晰职责划分。

二、Mapper调用

1、调用时序图

2、组件关系图

三、深度思考

1、接口和 SQL(XML / 注解)如何关联?

MyBatis 在初始化阶段通过以下两种方式完成绑定:

(1) XML 与接口关联:

通过 @MapperScan 注解扫描指定包下的 Mapper 接口,同时读取配置的 XML 文件路径(如 mybatis.mapper-locations=classpath:mapper/*.xml),将 XML 中 namespace(接口全限定名)与接口匹配,id(方法名)与接口方法匹配;

(2) 注解与接口关联:

扫描接口时直接解析方法上的 @Select/@Insert 等注解,无需 XML 文件,SQL 通过注解直接与方法绑定,无需额外的 namespace 配置。

2、Mapper 接口能不能进行方法重载?

不能。

原因是 MyBatis 通过 "方法名" 作为核心标识匹配 SQL(XML 中的 id 或注解绑定的方法),若存在重载方法(方法名相同、参数不同),会导致 SQL 标识冲突,MyBatis 无法区分对应的 SQL,启动时会抛出异常(如 BindingException: Invalid bound statement)。

相关推荐
松仔log11 分钟前
Kotlin中级——callbackFlow
java·前端·kotlin
知守观1 小时前
同一个团队两套分包:DDD 四层落地后,domain 层最大的类还是 5885 行
java·后端·领域驱动设计
文丑颜不良啊1 小时前
LeetCode2541~2560题目解析
java·leetcode
瑞雪兆丰年兮1 小时前
JavaWeb-day11-SpringBootWeb案例(文件上传)
java·运维·服务器·javaweb·oss
Highcharts.js2 小时前
Highcharts智能数据分析平台Orbit 多语言配置技术文档
java·前端·javascript·highcharts·orbit·智能数据分析·设置文档
Rain的Java大神之路2 小时前
设计一套生产级 API 接口:从契约、安全、幂等到限流,我踩过的坑都在这了
java·后端·面试
SimonKing2 小时前
零配置也能白嫖前沿大模型!dsh-our-free-model插件真香警告
java·后端·程序员
nice_lcj5202 小时前
【从零理解 Spring AI · 15】让检索更准:先宽召回,再精排序
java·后端·rag·spring ai·ai应用开发·检索优化·重排序
杨凯凡3 小时前
Spring Boot 链路追踪实战:Micrometer、TraceId 与异步线程上下文传播
java·spring boot·后端
计算机毕设定制辅导-无忧学长3 小时前
《基于Spring Boot的迷游哈游戏综合服务平台的开发》
java·vue.js·spring boot·mysql·迷游哈游戏综合服务平台