(/≧▽≦)/~┴┴ 嗨~我叫小奥 ✨✨✨
👀👀👀 个人博客:小奥的博客
👍👍👍:个人优快云
⭐️⭐️⭐️:传送门
🍹 本人24应届生一枚,技术和水平有限,如果文章中有不正确的内容,欢迎多多指正!
📜 欢迎点赞收藏关注哟! ❤️
一、MyBatis整体架构
本博文主要是分享自己学习MyBatis源码的一些记录,会参考大量的博文和一些书籍,链接会放在文末。
MyBatis版本:3.5.14
下载源来自Github,fork到自己仓库中,然后clone即可。
1.1 项目结构
如下图,是MyBatis源码的目录结构下的所有包。

其中,各个包的内容简介如下:
| 包名称 | 包内内容简介 |
|---|---|
| annotation | 注解目录。包括所有的注解。如@SELECT,@UPDATE等 |
| binding | Mapper类的实例反射生成工具目录 |
| builder | 主要是注解,mapper和SqlSuorce的构造器及转换器 |
| cache | Mybatis内部缓存接口。实现了一些特定的缓存策略。FifoCache,LruCache,BlockingCache,LoggingCache等 |
| cursor | 默认的游标处理类 |
| dataSource | 数据源工厂类及实现。实现类包括JndiDataSourceFactory、PooledDataSourceFactory、UnpooledDataSourceFactory。 数据源实现类: UnpooledDataSource、PooledDataSource |
| exceptions | Mybatis自定义的三个异常类。ExceptionFactory、PersistenceException、TooManyResultsException、IbatisException。都继承自RuntimeException |
| executor | 执行器相关包。包括Key生成器、加载器(包括Cglib、Javassist的代理,结果加载器)、参数处理器接口、结果处理器、结果集(resultSet)处理器、Statement处理器(实现类:BaseStatementHandler、CallableStatementHandler、PreparedStatementHandler、RoutingStatementHandler、SimpleStatementHandler)、执行器(SimpleExecutor、ReuseExecutor、CachingExecutor、BatchExecutor、BaseExecutor) |
| io | 主要是定义的几个VFS(VFS、DefaultVFS、ClassLoaderWrapper) |
| jdbc | 与Sql相关的操作。如Sql运行器,脚本运行器和Sql封装类等 |
| lang | 指定是用java7还是java8的API的注解.UsesJava7、UsesJava8 |
| logging | 各个类型的日志适配器,都实现了Log接口。StdOutImpl、Slf4jImpl、NoLoggingImpl、Log4j2Impl、Log4jImpl、Jdk14LoggingImpl、BaseJdbcLogger、JakartaCommonsLoggingImpl |
| mapping | 主要是接口参数,sql和返回结果的映射类,主要类包括:MappedStatement,ParameterMap,ParameterMapping,ResultMap,ResultMapping,BoundSql,SqlSource等类 |
| parsing | 变量解析.如解析${},#{}等 |
| plugin | 主要包含插件的定义接口。如Interceptor,Plugin,InterceptorChain等 |
| reflection | 主要是一些反射操作的工具方法和对象工厂类,以及一些常用的包装类,如BaseWrapper,BeanWrapper,CollectionWrapper,MapWrapper,ObjectWrapper。 |
| scripting | 执行驱动和动态Sql解析 |
| session | 主要是SqlSession和SqlSessionFactory |
| transaction | 主要是mybatis简单封装的jdbc事务操作类 |
| type | 各个类型数据的处理器。用于动态的设置参数和转换数据。如IntegerTypeHandler用来处理Integer类型的值的set和get操作。除了八大基本类型。还有常用的集合及Map类型,还增加了各种时间类型的处理器 |
2 整体架构
MyBatis的整体架构分为三层:基础支持层、核心处理层和接口层。

(1)基础支持层
基础支持层,包含整个 MyBatis 的基础模块,这些模块为核心处理层的功能提供了良好的支撑
- 反射模块:对 Java 原生的反射进行良好的封装,进行了一系列的优化,提供更加简洁易用的 API 方便使用。并且对反射操作进行了一系列优化,例如缓存了类的元数据,提高反射操作的性能
- 类型转换模块:类型转换模块主要提供了两个主要功能,一个是别名机制,MyBatis为了简化配置文件提供了别名机制;另一个功能是实现JDBC类型与Java类型之间的转化,该功能在为SQL语句绑定实参以及映射查询结果集时都会涉及
- 日志模块:提供日志输出,支持集成第三方日志框架
- 资源加载模块:主要是对类加载器进行封装,确定类加载器的使用顺序,并提供了加载类文件以及其他资源文件的功能
- 解析器模块:主要提供两个功能,一个是对XPath的封装,为MyBatis初始化时解析mybatis-config.xml配置文件以及映射配置文件提供支持;另一个功能是为处理动态SQL语句中的占位符提供支持
- 数据源模块:提供相应的 DataSource 数据源实现,支持与第三方数据源的继承
- 事务模块:对数据库中的事务进行了抽象,提供事务接口的简单实现
- 缓存模块:提供一级缓存和二级缓存的支持
- Binding 模块:提供 Mapper 接口与 XML 映射文件进行关联的支持
- 异常模块:定义 MyBatis 自己的 Exception
- 注解模块:提供MyBatis相关注解支持
(2)核心处理层
核心处理层实现了MyBatis的核心处理流程,其中包括MyBatis的初始化以及完成一次数据库操作涉及的全部流程。
① 配置解析
在 MyBatis 初始化过程中,会加载 mybatis-config.xml 配置文件、映射配置文件以及 Mapper 接口中的注解信息,解析后的配置信息会形成相应的对象并保存到 Configuration 对象中。之后,利用该 Configuration 对象创建 SqlSessionFactory 对象。待 MyBatis 初始化之后,开发人员可以通过初始化得到 SqlSessionFactory 创建 SqlSession 对象并完成数据库操作。
② SQL解析和scripting模块
MyBatis实现动态SQL功能,提供了多种动态SQL语句对应的节点。如<where>、<if>等节点,通过这些节点的组合使用,开发人员可以写出几乎满足所有需求的动态SQL语句。
MyBatis 中的 scripting 模块会根据用户传入的实参,解析映射文件中定义的动态 SQL 节点,并形成数据库可执行的 SQL 语句。之后会处理 SQL 语句中的占位符,绑定用户传入的实参。
③ SQL执行
SQL 语句的执行涉及多个组件,其中比较重要的是 Executor 、StatementHandler 、ParameterHandler 和 ResultSetHandler。
Executor 主要负责维护一级缓存和二级缓存,并提供事务管理的相关操作,它会将数据库相关操作委托给StatementHandler 完成。StatementHandler 首先通过 ParameterHandler 完成 SQL 语句的实参绑定;然后通过 java.sql.Statement 对象执行 SQL 语句并得到结果集;最后通过 ResultSetHandler 完成结果集的映射,得到结果对象并返回。
④ 插件
用户可以通过添加自定义插件的方式对 MyBatis 进行扩展。用户自定义插件也可以改变 MyBatis 的默认行为,例如,我们可以拦截 SQL 语句并对其进行重写。由于用户自定义插件会影响 MyBatis 的核心行为,在使用自定义插件之前,开发人员需要了解 MyBatis 内部的原理,这样才能编写出安全、高效的插件。
下图展示了MyBatis执行一条SQL语句的大致过程:

(3)接口层
接口层相对简单,其核心是SqlSession接口,该接口中定义了MyBatis暴露给应用程序调用的Api,也就是上层应用与MyBatis交互的桥梁。接口层在收到调用请求时,会调用核心处理层的相应模块来完成具体的数据库操作。
(4)总结
MyBatis的代码并不是很多,相对于源码阅读入门的同学来说还是比较简单的,我会按照以上三个模块(基础支持层 ==> 核心处理层 ==> 接口层)进行逐步分析。
本文详细介绍了MyBatis3.5.14的整体架构,包括基础支持层(如反射、类型转换和缓存)、核心处理层(配置解析、SQL解析、执行和插件)和接口层(SqlSessionAPI)。通过源码学习,帮助读者理解MyBatis的工作流程和扩展点。
464





