过一遍mybatis源码-1
Posted 叔叔的博客
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了过一遍mybatis源码-1相关的知识,希望对你有一定的参考价值。
先过一遍mybatis的简单介绍和使用。
http://www.mybatis.org/mybatis-3/zh/getting-started.html
比较好的mybatis源码解析 https://blog.csdn.net/nmgrd/article/details/54608702
这么好的框架,自己撸一遍收获会很大。
我看的是这位大牛翻译的源码 https://github.com/tuguangquan/mybatis.git
先分析初始化过程。(暂时只分析xml配置方式)
从这段开始看。
@Test
public void test() throws IOException {
InputStream inputStream = Resources.getResourceAsStream("resources/mybatis-config.xml");
SqlSessionFactory build = new SqlSessionFactoryBuilder().build(inputStream);
SqlSession sqlSession = build.openSession();
Object result = sqlSession.selectOne("select * from user");
}
一、读取配置文件
InputStream inputStream = Resources.getResourceAsStream("resources/mybatis-config.xml");
主要是加载5个类加载器去查找资源
//一共5个类加载器
ClassLoader[] getClassLoaders(ClassLoader classLoader) {
return new ClassLoader[]{
classLoader,
defaultClassLoader,
Thread.currentThread().getContextClassLoader(),
getClass().getClassLoader(),
systemClassLoader};
}
二、创建SqlSessionFactory
SqlSessionFactory build = new SqlSessionFactoryBuilder().build(inputStream);
这步就是mybatis的初始化。
public SqlSessionFactory build(InputStream inputStream, String environment, Properties properties) {
XMLConfigBuilder parser = new XMLConfigBuilder(inputStream, environment, properties);
return build(parser.parse());
}
会创建XMLConfigBuilder
//上面6个构造函数最后都合流到这个函数,传入XPathParser
private XMLConfigBuilder(XPathParser parser, String environment, Properties props) {
//首先调用父类初始化Configuration
super(new Configuration());
//错误上下文设置成SQL Mapper Configuration(XML文件配置),以便后面出错了报错用吧
ErrorContext.instance().resource("SQL Mapper Configuration");
//将Properties全部设置到Configuration里面去
this.configuration.setVariables(props);
this.parsed = false;
this.environment = environment;
this.parser = parser;
}
```
这里configuration会注册一些类型别名。
然后parser.parse()解析节点,根节点是/configuration。
```
// <?xml version="1.0" encoding="UTF-8" ?>
// <!DOCTYPE configuration PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
// "http://mybatis.org/dtd/mybatis-3-config.dtd">
// <configuration>
// <environments default="development">
// <environment id="development">
// <transactionManager type="JDBC"/>
// <dataSource type="POOLED">
// <property name="driver" value="${driver}"/>
// <property name="url" value="${url}"/>
// <property name="username" value="${username}"/>
// <property name="password" value="${password}"/>
// </dataSource>
// </environment>
// </environments>
// <mappers>
// <mapper resource="org/mybatis/example/BlogMapper.xml"/>
// </mappers>
// </configuration>
对这些node进行解析,塞到configuration中。
解析完后,进行build,返回DefaultSqlSessionFactory。
三、生成SqlSession
private SqlSession openSessionFromDataSource(ExecutorType execType, TransactionIsolationLevel level, boolean autoCommit) {
Transaction tx = null;
try {
final Environment environment = configuration.getEnvironment();
final TransactionFactory transactionFactory = getTransactionFactoryFromEnvironment(environment);
//通过事务工厂来产生一个事务
tx = transactionFactory.newTransaction(environment.getDataSource(), level, autoCommit);
//生成一个执行器(事务包含在执行器里)
final Executor executor = configuration.newExecutor(tx, execType);
//然后产生一个DefaultSqlSession
return new DefaultSqlSession(configuration, executor, autoCommit);
} catch (Exception e) {
//如果打开事务出错,则关闭它
closeTransaction(tx); // may have fetched a connection so lets call close()
throw ExceptionFactory.wrapException("Error opening session. Cause: " + e, e);
} finally {
//最后清空错误上下文
ErrorContext.instance().reset();
}
}
第一步生成事务
第二步生成执行器,这里会选择一种执行器,另外,会调用插件,通过插件可以改变Executor行为。
第三步,return new DefaultSqlSession(configuration, executor, autoCommit);
这样sqlSession就生成了。
四、总结
初始化还算思路简单清晰。
这里用到的设计模式有,工厂,单例,构造者模式,拓展性强。
第一天代码放在了 https://coding.net/u/unclehh/p/mybatis-review/git/tree/day-1?public=true
以上是关于过一遍mybatis源码-1的主要内容,如果未能解决你的问题,请参考以下文章
#yyds干货盘点# mybatis源码解读:executor包(语句处理功能)