Main函数
首先来看看sqlSessionFactory对象的创建过程
sqlSessionFactory的创建需要有Builder来build(),所以我们先看看build方法:
public SqlSessionFactory build(InputStream inputStream, String environment, Properties properties) {
SqlSessionFactory var5;
try {
//创建一个xml解析器
XMLConfigBuilder parser = new XMLConfigBuilder(inputStream, environment, properties);
//通过xml构建SqlSessionFactory
var5 = this.build(parser.parse());
} catch (Exception var14) {
throw ExceptionFactory.wrapException("Error building SqlSession.", var14);
} finally {
ErrorContext.instance().reset();
try {
inputStream.close();
} catch (IOException var13) {
;
}
}
return var5;
}
可以看到,build方法中,首先是创建一个xml解析器,解析器的种类有很多,但是都有一个基类 BaseBuilder
这个基类有三个属性,根据名字便可以知道是配置对象,别名注册对象,类型拦截器
解析完后调parser.parse()返回一个Configuration对象:
我们来看看parseConfiguration方法:
解析配置文件种的各个节点,我们来看下解析mappers节点的过程:
拿到接口注册:
Configuration对象就是一个封装了配置文件中<configuration>标签里的配置信息的对象:
并将配置信息放入SqlSessionFactory中,接下来就是通过SqlSessionFactory拿到SqlSession对象.
private SqlSession openSessionFromDataSource(ExecutorType execType, TransactionIsolationLevel level, boolean autoCommit) {
Transaction tx = null;
DefaultSqlSession var8;
try {
Environment environment = this.configuration.getEnvironment();
//获取事务管理器
TransactionFactory transactionFactory = this.getTransactionFactoryFromEnvironment(environment);
tx = transactionFactory.newTransaction(environment.getDataSource(), level, autoCommit);
//获取sql的执行对象
Executor executor = this.configuration.newExecutor(tx, execType);
//获取sqlSession对象
var8 = new DefaultSqlSession(this.configuration, executor, autoCommit);
} catch (Exception var12) {
this.closeTransaction(tx);
throw ExceptionFactory.wrapException("Error opening session. Cause: " + var12, var12);
} finally {
ErrorContext.instance().reset();
}
return var8;
}
Mybatis中所有的Mapper语句的执行都是通过Executor进行的,Executor是Mybatis的一个核心接口,其定义如下。从其定义的接口方法我们可以看出,对应的增删改语句是通过Executor接口的update方法进行的,查询是通过query方法进行的。虽然Executor接口的实现类有BaseExecutor和CachingExecutor,而BaseExecutor的子类又有SimpleExecutor、ReuseExecutor和BatchExecutor,但BaseExecutor是一个抽象类,其只实现了一些公共的封装,而把真正的核心实现都通过方法抽象出来给子类实现,如doUpdate()、doQuery();CachingExecutor只是在Executor的基础上加入了缓存的功能,底层还是通过Executor调用的,所以真正有作用的Executor只有SimpleExecutor、ReuseExecutor和BatchExecutor。
接下来我们主要来看看 var8 = new DefaultSqlSession(this.configuration, executor, autoCommit);
拿到sqlSession后就可以通过getMapper来获取了,我们来看看这个方法:
可以看到,它是从原来的knownMappers中获取,并通过反射创建代理对象