从本篇开始我们开始学习mybatis的系列源码,主要的主题可能就是四个方面
- 从整体把握mybatis系统架构
- 通过一个查询SQL 源码解析核心流程
- mybatis的缓存机制-源码级别
- mybatis的插件机制-源码级别
- spring是如何整合的mybatis框架的
1.整体架构
上述是mybatis的源码,那么mybatis有哪些核心模块呢,通过从下面三个点出发
基础支持层
类型转换模块
在mybatis-config.xml配置文件中 通过typeAliase、以及mybaits中JDBC类型和java类型的相关转换。
日志模块 :排查问题,集成了很多优秀的日志框架
反射工具 :在java反射的基础上进行了一层封装,为上层使用方提供更加灵活、方便的API接口。
Binding模块 :我们无需编写mapper接口的具体实现,而是利用binding模块自动生成mapper接口的动态代理对象。
数据源模块、缓存模块、解析器模块、事务管理模块
核心处理层
核心处理层涉及到mybatis初始化以及执行一条SQL的语句的全流程。
配置解析:将mybatis-config.xml 配置文件 以及mapper.xml配置文件以及mapper接口中的注解信息,解析之后保存到configuration对象中。
SQL解析与scripting模块:根据用户传入的实参,解析动态SQL的标签,形成SQL模版。
SQL执行
插件 主要提供拓展能力,在原生框架不满足某些场景的时候,可以根据业务场景开发属于自己的工具,比如慢SQL检查等。
接口层
2.造轮子的思路
通过整体上了解mybatis的架构,我们大概了解了实现一个ORM框架需要的核心功能点,如果让我们来实现一个mybatis你有什么思路嘛,我理解大概需要解决如下几个问题
- 前期准备
- 1.解析xml配置文件称一个configuration对象,以及解析mapper文件
- 2.构建核心的基础数据操作对象sqlsession,以及一个mapper文件对应的MappedStatment对象
- 执行过程
- 3.通过sqlSession执行对应的mapper文件的sql语句 ,其实也就是Executor、StatmentHandler、ParamerterHandler、ResultSetHandler、TypeHandler 这几个核心类的功能。
- 说白了就是一个SQL要执行的过程,整体来说就是SQL语句的封装,参数解析,类型转换、结果解析等
- 生成mapper接口代理类
- 这部分其实就需要根据原始SQL 进行利用jdk动态代理实现。
3.存储数据类对象
java
概念:在Java中(JVM)对Mybatis相关的配置信息进行封装
mybatis-config.xml ----> Configuration
Configuration
1. 封装了mybatis-config.xml
2. 封装了mapper 文件 MappedStatement
3. 创建Mybatis其他相关的对象
XXXDAOMapper.xml ----> MappedStatement(形象的认知,不准确)
nt对象
对应的就是 Mapper文件中的一个一个的 配置标签
<select id. -----> MappedStatement
<insert id. -----> MappedStatement
注定 一个Mybatis应用中 N个MappedStament 对象
MappedStatment ---> Configuration
MappedStatment 中 封装SQL语句 ---> BoundSql
4.操作类对象
java
2. 操作类对象 (SqlSession) ---> 门面
Excutor
Excutor 是Mybatis中处理功能的核心
1. 增删改update 查query
2. 事务操作
提交 回滚
3. 缓存相关的操作
Excutor接口
BatchExcutor
JDBC中批处理的操作, BatchExcutor
ReuseExcutor
目的:复用 Statement
insert into t_user(ID,name)values(1,'孙帅');
insert into t_user(ID,name)values(2,'孙帅1');
SimpleExcutor
常用Excutor Mybatis推荐 默认
Configuration protected ExecutorType defaultExecutorType = ExecutorType.SIMPLE;
StatmentHandler
StatementHandler是Mybatis封装了JDBC Statement,真正Mybatis进行数据库访问操作的核心
功能:增删改差
StatementHandler接口
SimpleStatementHandler
JDBC 操作
PreparedStatementHandler
CallableStatementHandler
ParameterHandler
目的:Mybatis参数 ---》 JDBC 相关的参数
@Param ---> #{} --- > ?
ResultSetHandler
目的:对JDBC中查询结果集 ResultSet 进行封装
TypeHandler
Java程序操作 数据库
Java类型 数据库类型
String varchar
int number
int int
5.串联源码
其实我们可以通过一个简单的SQL就可以了解整体过程。
java
// 读取配置配置文件
InputStream inputStream = Resources.getResourceAsStream("mybatis-config.xml");
// 1.解析xml配置文件以及mappers配置文件
// 2.new DefaultSqlSessionFactory对象
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
// 3.创建DefaultSqlSession对象
SqlSession sqlSession = sqlSessionFactory.openSession();
// 4.生成mapper的代理类对象
UserDAO userDAO = sqlSession.getMapper(UserDAO.class);
// 5.利用反射执行目标方法
// 6.根据入参数和结果处理 返回最终的值。
List<User> users = userDAO.queryAllUsers();
整体就是这个几个类进行完成的一个SQL的执行。
5.总结
对于优秀的开发人员来说,不仅要能看到代码细节处的优秀设计,而且还能站在更高的角度看整体框架的架构之美,这才是分析一个开源框架更重要的两部分收获。
在学习一个框架的源码的时候 我理解应该把握几个原则,
1.了解这个框架解决了什么问题 如何使用的
2.掌握核心底层原理,以及掌握后边设计的思想原则。
3.其中对于软件设计模式的使用,借鉴学习
4.如果自己造轮子的话 框架有哪些优缺点。