本文主要是介绍Mybatis OpenSession源码分析,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
openSession执行时序图
上一节提到SqlSessionFactoryBuilder的build()方法返回的是DefaultSqlSessionFactory这个SqlSessionFactory的实现类,那么openSession也是DefaultSqlSessionFactory这个类里面的方法
/*** 默认的SqlSessionFactory* */
public class DefaultSqlSessionFactory implements SqlSessionFactory {private final Configuration configuration;public DefaultSqlSessionFactory(Configuration configuration) {this.configuration = configuration;}//最终都会调用2种方法:openSessionFromDataSource,openSessionFromConnection//以下6个方法都会调用openSessionFromDataSource@Overridepublic SqlSession openSession() {return openSessionFromDataSource(configuration.getDefaultExecutorType(), null, false);}
调用下边的private方法
private SqlSession openSessionFromDataSource(ExecutorType execType, TransactionIsolationLevel level, boolean autoCommit) {Transaction tx = null;try {
// 获取环境信息final Environment environment = configuration.getEnvironment();
// 获取environment节点下的事务配置信息 默认情况下是ManagedTransactionFactory,
// 如果配置了transactionManager节点并且type为JDBC,则返回JdbcTransactionFactory事务工厂final TransactionFactory transactionFactory = getTransactionFactoryFromEnvironment(environment);//通过事务工厂来产生一个事务,tx = transactionFactory.newTransaction(environment.getDataSource(), level, autoCommit);//生成一个执行器(事务包含在执行器里)final Executor executor = configuration.newExecutor(tx, execType);//然后产生一个DefaultSqlSessionreturn 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();}}
//获取mybatis-config.xml中配置的事务
// <environment id="development">
// <transactionManager type="JDBC"/>
// <dataSource type="POOLED">
// <property name="driver" value="${jdbc.driver}"/>
// <property name="url" value="${jdbc.url}"/>
// <property name="username" value="${jdbc.username}"/>
// <property name="password" value="${jdbc.password}"/>
// </dataSource>
// </environment>private TransactionFactory getTransactionFactoryFromEnvironment(Environment environment) {//如果没有配置事务工厂,则返回托管事务工厂if (environment == null || environment.getTransactionFactory() == null) {return new ManagedTransactionFactory();}return environment.getTransactionFactory();}
接下来new Executor执行器
//产生执行器public Executor newExecutor(Transaction transaction, ExecutorType executorType) {executorType = executorType == null ? defaultExecutorType : executorType;//这句再做一下保护,囧,防止粗心大意的人将defaultExecutorType设成null?executorType = executorType == null ? ExecutorType.SIMPLE : executorType;Executor executor;//然后就是简单的3个分支,产生3种执行器BatchExecutor/ReuseExecutor/SimpleExecutorif (ExecutorType.BATCH == executorType) {executor = new BatchExecutor(this, transaction);} else if (ExecutorType.REUSE == executorType) {executor = new ReuseExecutor(this, transaction);} else {executor = new SimpleExecutor(this, transaction);}//如果要求缓存,生成另一种CachingExecutor(默认就是有缓存),装饰者模式,所以默认都是返回CachingExecutorif (cacheEnabled) {executor = new CachingExecutor(executor);}//此处调用插件,通过插件可以改变Executor行为executor = (Executor) interceptorChain.pluginAll(executor);return executor;}
最后new DefaultSqlSession并返回
public DefaultSqlSession(Configuration configuration, Executor executor, boolean autoCommit) {this.configuration = configuration;this.executor = executor;this.dirty = false;this.autoCommit = autoCommit;}
这篇关于Mybatis OpenSession源码分析的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!