【MyBatis 源码阅读与笔记】Mapper 接口的动态代理实现
MyBatis 源码阅读与笔记
题目:Mapper 接口的动态代理实现
- 研究 MyBatis 如何通过动态代理为 Mapper 接口创建实现类。
- 重点分析
MapperProxy
类,理解其如何拦截方法调用并执行 SQL。
笔记
1 动态代理原理
MyBatis 使用 JDK 动态代理为 Mapper 接口创建代理类。当调用 Mapper 接口的方法时,实际上是进入 MapperProxy
类的 invoke
方法,执行 SQL 操作。
2 核心类与方法介绍
- MapperProxy:核心类,负责拦截接口方法调用并执行 SQL。
- MapperProxyFactory:创建
MapperProxy
的工厂。 - MapperMethod:封装接口方法与 SQL 之间的映射关系。
- SqlSession:MyBatis 的核心接口,负责 SQL 执行与事务管理。
3 源码结构分析
3.1 MapperProxy
类
MapperProxy
是 MyBatis 动态代理的核心类,负责拦截 Mapper 接口的方法调用并执行 SQL。
关键逻辑:
invoke()
:拦截方法调用,判断是否是Object
类方法,若是则直接执行,不进入 SQL 执行流程。- 方法缓存:使用
methodCache
缓存MapperMethod
,避免重复创建。 - SQL 执行:调用
MapperMethod.execute()
执行 SQL 语句,结果通过SqlSession
返回。
3.2 MapperMethod
类
MapperMethod
负责管理接口方法和 SQL 语句的映射关系,封装了执行 SQL 的具体细节。
关键逻辑:
execute()
:根据方法的返回类型,调用相应的SqlSession
方法(如selectOne
、insert
)。SqlCommand
:封装 SQL 的基础信息,如 SQL 类型、ID 等。MethodSignature
:确保方法签名(如返回类型和参数)一致,保证数据的正确性。
3.3 MapperProxyFactory
类
MapperProxyFactory
用于创建 MapperProxy
实例,生成具体的代理对象。
关键逻辑:
newInstance()
:通过 JDK 的Proxy.newProxyInstance()
创建代理对象,该对象拦截方法调用并执行 SQL。
3.4 SqlSession
类
SqlSession
是 MyBatis 的核心接口,负责执行 SQL 语句和事务管理。
关键逻辑:
selectOne()
:执行单条查询。insert()
:执行插入操作。- 事务管理:通过
commit()
和rollback()
管理事务。
4 知识点总结
- 动态代理实现:MyBatis 使用 JDK 动态代理为 Mapper 接口生成代理类,所有方法调用通过
MapperProxy.invoke
方法处理。 - MapperProxy 类:拦截方法调用,并通过
MapperMethod
执行 SQL。 - MapperMethod 类:负责接口方法与 SQL 语句的映射,执行 SQL 后处理结果。
- SQL 执行与封装:使用
SqlSession
执行 SQL,根据返回类型封装结果。
5 设计模式总结
5.1 代理模式 (Proxy Pattern)
- 应用场景:用于为 Mapper 接口创建代理,实现 SQL 执行的动态绑定。
- 优势:通过代理模式,开发者只需定义接口,无需实现具体的 SQL 执行逻辑。
5.2 工厂模式 (Factory Pattern)
- 应用场景:
MapperProxyFactory
用来创建MapperProxy
,集中管理代理对象创建。 - 优势:工厂模式简化了对象创建过程,提升了代码的可扩展性。
5.3 模板方法模式 (Template Method Pattern)
- 应用场景:
MapperMethod.execute
是模板方法,封装 SQL 执行的通用流程。 - 优势:提取通用逻辑,减少重复代码,提高可读性和扩展性。
本文作者:鸿·蒙
文档工具:Typora
版权声明:本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 鸿·蒙 !