自我表扬:《Dubbo 实现原理与源码解析 —— 精品合集》
表扬自己:《D数据库实体设计合集》

摘要: 原创出处 https://my.oschina.net/u/657390/blog/653637 「udbwcso」欢迎转载,保留摘要,谢谢!


🙂🙂🙂关注微信公众号:【芋道源码】有福利:

  1. RocketMQ / MyCAT / Sharding-JDBC 所有源码分析文章列表
  2. RocketMQ / MyCAT / Sharding-JDBC 中文注释源码 GitHub 地址
  3. 您对于源码的疑问每条留言将得到认真回复。甚至不知道如何读源码也可以请教噢
  4. 新的源码解析文章实时收到通知。每周更新一篇左右
  5. 认真的源码交流微信群。

版本:mybatis-3

主要分析SqlSessionFactory的构建过程

SqlSessionFactoryBuilder从XML中构建SqlSessionFactory

String resource = "org/mybatis/example/mybatis-config.xml";
InputStream inputStream = Resources.getResourceAsStream(resource);
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);

img

SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);

SqlSessionFactoryBuilder用来创建SqlSessionFactory实例,一旦创建了SqlSessionFactory,就不再需要它了

public SqlSessionFactory build(InputStream inputStream) {
return build(inputStream, null, null);
}

调用

public SqlSessionFactory build(InputStream inputStream, String environment, Properties properties)

源码如下:

/**
* 根据配置创建SqlSessionFactory
*
* @param inputStream 配置文件输入流
* @param environment 环境名称
* @param properties 外部配置
* @return
*/
public SqlSessionFactory build(InputStream inputStream, String environment, Properties properties) {
try {
XMLConfigBuilder parser = new XMLConfigBuilder(inputStream, environment, properties);
//parser.parse()读取配置文件返回configuration
//build()根据返回的configuration创建SqlSessionFactory
return build(parser.parse());
} catch (Exception e) {
throw ExceptionFactory.wrapException("Error building SqlSession.", e);
} finally {
ErrorContext.instance().reset();
try {
inputStream.close();
} catch (IOException e) {
// Intentionally ignore. Prefer previous error.
}
}
}

最终创建DefaultSqlSessionFactory实例

public SqlSessionFactory build(Configuration config) {
return new DefaultSqlSessionFactory(config);
}

其中

XMLConfigBuilder与Configuration

img

XMLConfigBuilder的方法parse()

public Configuration parse() {
if (parsed) {
throw new BuilderException("Each XMLConfigBuilder can only be used once.");
}
parsed = true;
//读取mybatis-config.xml配置信息,"configuration"是根结点
parseConfiguration(parser.evalNode("/configuration"));
return configuration;
}

XMLConfigBuilder的方法parseConfiguration(XNode root)

/**
* 读取配置文件组装configuration
* @param root 配置文件的configuration节点
*/
private void parseConfiguration(XNode root) {
try {
//issue #117 read properties first
propertiesElement(root.evalNode("properties"));
typeAliasesElement(root.evalNode("typeAliases"));
pluginElement(root.evalNode("plugins"));
objectFactoryElement(root.evalNode("objectFactory"));
objectWrapperFactoryElement(root.evalNode("objectWrapperFactory"));
reflectionFactoryElement(root.evalNode("reflectionFactory"));
settingsElement(root.evalNode("settings"));
// read it after objectFactory and objectWrapperFactory issue #631
environmentsElement(root.evalNode("environments"));
databaseIdProviderElement(root.evalNode("databaseIdProvider"));
typeHandlerElement(root.evalNode("typeHandlers"));
mapperElement(root.evalNode("mappers"));
} catch (Exception e) {
throw new BuilderException("Error parsing SQL Mapper Configuration. Cause: " + e, e);
}
}

关于配置文件相关的源码分析参看:

http://www.iocoder.cn/MyBatis/udbwcso/Configuration

设计模式

从SqlSessionFactory和Configuration的创建过程中可以看出它们都使用了建造者模式.

666. 彩蛋

如果你对 MyBatis 感兴趣,欢迎加入我的知识一起交流。

知识星球

文章目录
  1. 1. 666. 彩蛋