最近发现自己对jdbc和mybatis底层实现了解很浅,特此写一篇关于mybatis的底层实现文章来增加自己的理解
在说mybatis底层实现之前,先看下基本的知识点jdbc
jdbc是连接数据库的最基本实现,任何对数据库的操作都是基于jdbc
1. 注册驱动
Class.forName("com.mysql.jdbc.Driver");
2.获取数据库连接
Connection conn =DriverManager.getConnection(url,user,p);
3.创建向数据发送sql 的statement对象
Statement stmt = conn.CreateStatement();
4. 向数据库发送sql
ResultSet rs = stmt.executeQuery(sql)//select语句
int updateaSum = stmt.executeUpdate(sql)//insert,update delete语句
5. 处理结果集
while(rs.next()){
rs.getString(列名)
rs.getInt(列名)
}
6. 关闭资源
rs.close();
stmt.close();
conn.close();
关于jdbc更详细内容可以看我另一篇博客:jdbc原理详解,这里就不细讲了
Mybatis之Sqlsession、Connection和Transaction解析关系与原理
Connection
JDBC 是我们用来与数据库交互最基础的API。
Connection 作为一个特定数据库的会话,在一个连接的上下文中,sql语句被执行,然后结果被返回。
我们先看下使用sqlsession进行数据库操作的基本流程
SqlSession
可以看作是对Connection 更加高级的抽象,从其方法上更加可以看出他具有更加明显的操作特征。
Transaction
事务(Transaction) ,正是对N(N>=1)个操作执行时,同时成功或同时失败的 关系 的具象。
我们先看下sqlsession是如何进行数据库操作的:
String resource = "mybatis-config.xml";
//获取数据配置流
InputStream inputStream = Resources.getResourceAsStream(resource);
//通过SqlSessionFactoryBuilder获取SqlSessionFactory
SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream);
//通过sqlSessionFactory获取sqlSession
SqlSession sqlSession = sqlSessionFactory.openSession();
//对数据库执行操作
try {
TbUserMapper userMapper = sqlSession.getMapper(TbUserMapper.class);
TbUser user = new TbUser("liybk", "liybk","186..","123");
userMapper.insertUser(user);
sqlSession.commit();// 这里一定要提交,不然数据进不去数据库中
} finally {
sqlSession.close();
}
我门先看SqlSessionFactoryBuilder().build(inputStream)方法:
public SqlSessionFactory build(InputStream inputStream, String environment, Properties properties) {
SqlSessionFactory var5;
try {
XMLConfigBuilder parser = new XMLConfigBuilder(inputStream, environment, properties);
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;
}
public SqlSessionFactory build(Configuration config) {
return new DefaultSqlSessionFactory(config);
}
最终执行通过一系列的xml文件解析,返回了DefaultSqlSessionFactory,进入DefaultSqlSessionFactory构造函数
public DefaultSqlSessionFactory(Configuration configuration) {
this.configuration = configuration;
}
构造函数只是初始化了其configuration 属性,这个configuration 里面包含了一个Environment属性,而Environment属性里又有数据源,connect,事务等等一系列关于数据库操作的基本属性
public final class Environment {
private final String id;
private final TransactionFactory transactionFactory;
private final DataSource dataSource;
....
}
好的,我们回到主步骤SqlSession sqlSession = sqlSessionFactory.openSession()方法
其执行类是DefaultSqlSessionFactory,目的是获取sqlSession
public SqlSession openSession() {
return
//调用该类的openSessionFromDataSource方法
this.openSessionFromDataSource(this.configuration.getDefaultExecutorType(), (TransactionIsolationLevel)null, false);
}
//openSessionFromDataSource方法
private SqlSession openSessionFromDataSource(ExecutorType execType, TransactionIsolationLevel level, boolean autoCommit) {
Transaction tx = null;
DefaultSqlSession var8;
try