说明
MyBatis版本:3.5.1
相关历史文章(阅读本文之前,您可能需要先看下之前的系列)
Spring Boot MyBatis最全教程:你值得拥有MyBatis能脱离Spring吗一图纵览MyBatis的工作原理
说明
MyBatis版本:3.5.1
相关历史文章(阅读本文之前,您可能需要先看下之前的系列)
Spring Boot MyBatis最全教程:你值得拥有
前言
通过上面我们已经可以构建了SqlSessionFactory,接下来的话就是要怎么获取一个SqlSession。
一、分析
对于SqlSession的构建的话,需要有一个属性Configuration,这个属性在上面的SqlSessionFactory已经有了;另外对于SqlSession的真正的Sql执行是交给了Executor,Executor是真正和数据库进行交互了,所以需要将数据库配置信息传给Executor。
二、编码
2.1 Executor
构造SqlSession需要有Executor,我们先创建一个Executor接口:
package com.kfit.mybatis.session; import java.util.List; import com.kfit.mybatis.config.MapperStatement; public interface Executor { <E> List<E> query(MapperStatement ms, Object parameter); }
我们实现一个最基本的SimpleExecutor:
package com.kfit.mybatis.session.impl; import java.util.List; import com.kfit.mybatis.config.JdbcProperties; import com.kfit.mybatis.config.MapperStatement; import com.kfit.mybatis.session.Executor; public class SimpleExecutor implements Executor { private JdbcProperties jdbcProperties; public SimpleExecutor(JdbcProperties jdbcProperties) { this.jdbcProperties = jdbcProperties; } public <E> List<E> query(MapperStatement ms, Object parameter) { //具体的方法待实现 return null; } }
说明:
(1)这里我们实现了最基本的Simple,在MyBatis有3种情况需要处理,我们实现最简单的方式。
(2)这里我们接收了jdbcproperties为了之后直接进行数据库的连接操作,在mybatis数据库的连接关闭,提交,回滚是有一个事务类Transaction。
2.2 SqlSessionFactory
在SqlSessionFactory中添加一个获取SqlSession的方法:
public interface SqlSessionFactory { public Configuration getConfiguration(); public SqlSession openSession(); }
在DefaultSqlSessionFactory实现openSession()方法:
public SqlSession openSession() { Executor executor = new SimpleExecutor(configuration.getJdbcProperties()); SqlSession sqlSession = new DefaultSqlSession(configuration, executor); return sqlSession; }
2.3 SimpleExecutor数据库操作
我们这个对数据库操作的核心代码:
package com.kfit.mybatis.session.impl; import java.lang.reflect.Field; import java.lang.reflect.Type; import java.sql.Connection; import java.sql.DriverManager; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import java.util.ArrayList; import java.util.List; import com.kfit.mybatis.config.JdbcProperties; import com.kfit.mybatis.config.MapperStatement; import com.kfit.mybatis.session.Executor; public class SimpleExecutor implements Executor { private JdbcProperties jdbcProperties; public SimpleExecutor(JdbcProperties jdbcProperties) { this.jdbcProperties = jdbcProperties; } public <E> List<E> query(MapperStatement ms, Object parameter) { List<E> ret = new ArrayList<E>(); // 具体的方法待实现 try { // 加载驱动 Class.forName(jdbcProperties.getDriver()); } catch (ClassNotFoundException e) { e.printStackTrace(); } Connection connection = null; PreparedStatement preparedStatement = null; ResultSet resultSet = null; try { // 获取连接 connection = DriverManager.getConnection(jdbcProperties.getUrl(), jdbcProperties.getUsername(), jdbcProperties.getPassword()); // 预编译sql语句 preparedStatement = connection.prepareStatement(ms.getSql()); // 处理sql语句中的占位符 parameterize(preparedStatement, parameter); // 执行sql语句 resultSet = preparedStatement.executeQuery(); // 处理结果 handlerResultSet(resultSet, ret, ms.getResultType()); } catch (SQLException e) { e.printStackTrace(); } return ret; } private void parameterize(PreparedStatement preparedStatement, Object parameter) throws SQLException { if (parameter instanceof String) { preparedStatement.setString(1, (String) parameter); } else if (parameter instanceof Long) { preparedStatement.setLong(1, (Long) parameter); } else if (parameter instanceof Integer) { preparedStatement.setInt(1, (Integer) parameter); } } private <E> void handlerResultSet(ResultSet resultSet, List<E> ret, String className) { Class<E> clazz = null; try { clazz = (Class<E>) Class.forName(className); } catch (ClassNotFoundException e) { e.printStackTrace(); } try { while (resultSet.next()) { // 通过反射实例化对象 Object entity = clazz.newInstance(); // 使用反射工具将resultSet中的数据填充到entity中 // id,name,sex,age // 获取实体类的所有属性,返回Field数组 Field[] fields = clazz.getDeclaredFields(); for (Field field : fields) { field.setAccessible(true); String fname = field.getName(); Type type = field.getGenericType(); if (type.toString().equals("class java.lang.String")) { String column = resultSet.getString(fname); field.set(entity, column); }else if (type.toString().equals("long")) { Long column = resultSet.getLong(fname); field.set(entity, column); } } ret.add((E) entity); } } catch (SQLException e) { e.printStackTrace(); } catch (InstantiationException e) { e.printStackTrace(); } catch (IllegalAccessException e) { e.printStackTrace(); } } }
说明:
(1)在MyBatis中这个代码是分好几个类进行处理的,这里为了讲解方便,统一放在一个类中。
(2)数据库的连接操作:这里使用jdbc连接数据库获取到connection进行操作。
(3)使用泛型处理返回的结果(handlerResultSet)。
2.4 SqlSession的方法
到这里,我们就可以编写SqlSession的方法了,这里定义两个方法SelectOne和SelectList();
public interface SqlSession { <T> T selectOne(String statement, Object parameter); <E> List<E> selectList(String statement); <E> List<E> selectList(String statement, Object parameter); }
对应的DefaultSqlSession:
package com.kfit.mybatis.session.impl; import java.util.List; import com.kfit.mybatis.config.Configuration; import com.kfit.mybatis.session.Executor; import com.kfit.mybatis.session.SqlSession; public class DefaultSqlSession implements SqlSession { private Configuration configuration; private Executor executor; public DefaultSqlSession(Configuration configuration,Executor executor) { this.configuration= configuration; this.executor = executor; } public <E> List<E> selectList(String statement) { return executor.query(configuration.getMapperStatement(statement),null); } public <E> List<E> selectList(String statement,Object parameter) { return executor.query(configuration.getMapperStatement(statement), parameter); } public <T> T selectOne(String statement,Object parameter) { List<T> list = executor.query(configuration.getMapperStatement(statement),parameter); if(list.size()>0) { return list.get(0); } return null; } }
说明:DefaultSqlSession的具体处理交给了Executor,所以这里的具体的实现就比较简单了。
2.5 测试下
在main方法来进行测试一下吧:
public static void main(String[] args) { String resource = "mybatis-config.xml"; InputStream inputStream = App.class.getClassLoader().getResourceAsStream(resource); SqlSessionFactory sqlSessionFactory = new SqlSessionFactoryBuilder().build(inputStream); System.out.println(sqlSessionFactory); System.out.println(sqlSessionFactory.getConfiguration().getJdbcProperties().getUrl()); SqlSession sqlSession = sqlSessionFactory.openSession(); Demo demo = null; List<Demo> demos = null; //使用sqlSession直接查询 demo = sqlSession.selectOne("com.kfit.mybatis.demo.mapper.DemoMapper.getById",1L); System.out.println(demo); demos = sqlSession.selectList("com.kfit.mybatis.demo.mapper.DemoMapper.getAll"); System.out.println(demos); }
这个方法和之前写mybatis的使用方式上是一模一样的,运行看下效果吧:
Demo[id=1, name=张三1]
[Demo [id=1, name=张三1], Demo [id=9, name=张三], Demo [id=10, name=张三], Demo [id=11, name=张三], Demo [id=12, name=张三], Demo [id=13, name=张三]]
看到如此帅气的结果,这是爽歪歪,厉害了我的哥。本篇就先介绍到这里,下一篇我们将会介绍无敌的Mapper实现。
我就是我,是颜色不一样的烟火。
我就是我,是与众不同的小苹果。
à悟空学院:https://t.cn/Rg3fKJD
学院中有Spring Boot相关的课程!点击「阅读原文」进行查看!
SpringBoot视频:http://t.cn/A6ZagYTi
Spring Cloud视频:http://t.cn/A6ZagxSR
SpringBoot Shiro视频:http://t.cn/A6Zag7IV
SpringBoot交流平台:https://t.cn/R3QDhU0
SpringData和JPA视频:http://t.cn/A6Zad1OH
SpringSecurity5.0视频:http://t.cn/A6ZadMBe
Sharding-JDBC分库分表实战:http://t.cn/A6ZarrqS
分布式事务解决方案「手写代码」:http://t.cn/A6ZaBnIr
相关推荐
开源框架面试题系列:Spring+SpringMVC+MyBatis08
开源框架面试题系列:Spring+SpringMVC+MyBatis。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。
手写mybatis核心流程代码demo手写mybatis核心流程代码demo手写mybatis核心流程代码demo手写mybatis核心流程代码demo手写mybatis核心流程代码demo手写mybatis核心流程代码demo手写mybatis核心流程代码demo手写mybatis...
开源框架面试题系列:Spring+SpringMVC+MyBatis.zip
手写mybatis,实现了基于JDBC访问数据库层,以及mybatis的XML映射
阿里巴巴P7架构师纯手工打造MyBatis源码——1小时解密底层源码.txt 需要更多往期录播资料可以联系我
手写mybatis框架源码 不借助其他任何框架,从最底层开始着手,用最简单的代码,将mybatis的底层框架,手写出来,让你对mybatis有一个更加深刻和直观的理解 详见:...
本资源是手写mybatis实现查询所有操作,详细描述了mybatis框架查询所有操作的实现过程,通过手动模拟mybatis框架的实现过程对mybatis框架有更深刻的认识。
另外还有加入框架的写法,此是最基础 的登录十天免登陆的。
开源框架面试题系列集:Spring+SpringMVC+MyBatis
开发工具 框架JAR mybatis-3.4.2开发工具 框架JAR mybatis-3.4.2开发工具 框架JAR mybatis-3.4.2开发工具 框架JAR mybatis-3.4.2开发工具 框架JAR mybatis-3.4.2开发工具 框架JAR mybatis-3.4.2开发工具 框架JAR ...
经典面试学习知识
SSM框架课程中共包含5个课程模块,分别是Spring框架、SpringMVC框架、Maven高级(缺)、SpringBoot框架、MyBatis-Plus框架。
自己手写的一个半自动框架,里面有运行例子,部分代码从mybatis中抽出
采用SpringBoot2.0、MyBatis-Plus、Shiro框架,开发的一套权限系统 采用SpringBoot2.0、MyBatis-Plus、Shiro框架,开发的一套权限系统 采用SpringBoot2.0、MyBatis-Plus、Shiro框架,开发的一套权限系统 采用...
手写实现mybatis,mybatis处理流程图,mybatis实现需要的几个函数,各个函数的调用。
《手写Mybatis》第4章:Mapper XML的解析和注册使用.doc
J2ee开源模板后台是基于 springmvc+mybatis+easyui+velocity 技术实现的一套模板后台,把一些通用的功能模板化,可以在线打包生成整站源码包括 jsp页面,为开发人员节省时间 ,生成的功能有增删改查,查询包括按列...
本课程全面讲解了Mybatis-Plus框架的使用,从快速入门到原理分析再到插件的应用。每一个知识点都有案例进行演示学习,最终通过学习你将全面掌握MP的使用,从而使Mybatis的的开发更加的高效,达到事半功倍的效果。 ...
围绕什么是mybatis框架?,mybatis框架原理介绍 ,mabatis的使用的代码示例以及心得体会