MyBatis-Spring中MyBatis概要流程

news/2024/12/25 15:09:12/文章来源:https://www.cnblogs.com/party-abu/p/18524093

一、初始化SqlSessionFactory

核心流程

核心使用到了SqlSessionFactoryBean的afterPropertiesSet、getObject方法

afterPropertiesSet:用于初始化并封装数据

getObject:用于注入DefaultSqlSessionFactory对象到容器中

详情逻辑

一、在将SqlSessionFactoryBean放在IOC容器过程中,由于SqlSessionFactoryBean实现了InitializingBean#afterPropertiesSet方法
afterPropertiesSet会做以下几件事
1. 将配置信息封装到Configuration对象中
2. 读取并解析各个配置的xml文件并封装到Configuration的Map<String, MappedStatement> mappedStatements对象中,key是xml的名称空间+各个标签id,value是标签的内容
3. 同时会加载各个名称空间得到Class对象,构建相应的代理工厂对象MapperProxyFactory到MapperRegistry的Map<Class<?>, MapperProxyFactory<?>> knownMappers中,方便创建代理对象使用
将封装好数据的Configuration对象作为属性放在创建的DefaultSqlSessionFactory对象中,这样就构建了DefaultSqlSessionFactory对象二、SqlSessionFactoryBean其实现了FactoryBean#getObject方法,getObject方法会将上边的DefaultSqlSessionFactory对象注入到IOC容器中

相应配置

<bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean"><property name="dataSource" ref="dataSource"/><!--映射配置文件位置--><property name="mapperLocations" value="classpath:/mapper/*.xml"/><!--其他配置--><property name="configuration"><bean class="org.apache.ibatis.session.Configuration"><!--开启列名转驼峰映射配置--><property name="mapUnderscoreToCamelCase" value="true"/><!--日志输出到控制台--><property name="logImpl" value="org.apache.ibatis.logging.stdout.StdOutImpl"/></bean></property>
</bean>

二、创建接口的代理对象并放在IOC容器中

核心流程

为每个接口创建间桥梁sqlSessionTemplate对象

将创建的映射器接口代理对象放在IOC容器中

详情逻辑

MapperFactoryBean继承了SqlSessionDaoSupport,会为每个接口创建sqlSessionTemplate对象,其作为一个中间桥梁,当sqlSessionTemplate执行方法时会委托给其内部的sqlSessionProxy代理对象执行

sqlSessionProxy代理对象执行相应的方法时会走增强逻辑SqlSessionInteceptior#invoke方法,invoke方法才会真正创建DefaultSqlSession对象,

创建DefaultSqlSession对象有以下重要步骤

  1. 会将DefaultSqlSession作为value,DefaultSqlSessionFactory对象作为key放在线程的局部变量TheadLocal
  2. 会与Spring的事务进行挂钩,创建Executor对象(比如SimpleExecutor),并将Spring事务放在BaseExecutor,为了后续在Executor执行方法时从Spring事务中获取数据库连接(spring事务本质上也是通过ThreadLocal对象拿的数据库连接,数据源作为key,数据库连接对象作为value)
    相关方法:
    org.mybatis.spring.SqlSessionTemplate.SqlSessionInterceptor#invoke
    org.mybatis.spring.SqlSessionUtils#getSqlSession()
    org.apache.ibatis.executor.SimpleExecutor#prepareStatement
    org.mybatis.spring.transaction.SpringManagedTransaction#openConnection

通过org.mybatis.spring.mapper.MapperFactoryBean#getObject方法将生成的映射器接口代理对象放在IOC容器中

<bean id="tbRoleInfoMapper" class="org.mybatis.spring.mapper.MapperFactoryBean"><property name="mapperInterface" value="com.abucloud.mapper.TbRoleInfoMapper"/><property name="sqlSessionFactory" ref="sqlSessionFactory"/>
</bean>
<bean id="userInfoMapper" class="org.mybatis.spring.mapper.MapperFactoryBean"><property name="mapperInterface" value="com.abucloud.mapper.UserInfoMapper"/><property name="sqlSessionFactory" ref="sqlSessionFactory"/>
</bean>

补充:MapperFactoryBean有两个重要作用,一是将接口的代理对象注入到容器中,二是当没有指定mapperLocations配置文件时,会自动以接口的全限定名去相同的类路径下找匹配的xml文件

三:代理对象执行目标方法

核心流程

通过MapperProxy#invoke作为入口,SqlSesionTemplate中间桥梁委托给sqlSessionProxy执行,再通过SqlSessionInterceptor#invoke方法创建真正的DefaultSqlSession对象执行crud

详情逻辑

1. 代理对象执行目标方法,就会执行MapperProxy#invoke方法,会构建MapperMethod,解析拿到映射器接口及相应的mapperStatement对象
2. 通过mapperMethod找到执行哪个操作(crud),接着继续委托给sqlSessionTemplate(是在创建MapperProxy对象塞进去的)执行
3. sqlSessionTemplate会继续委托给sqlSessionProxy对象执行,其是代理对象,执行操作会触发增强逻辑SqlSessionInterceptor执行
4. SqlSessionInterceptor内部会创建DefaultSqlSession对象,反射执行内部相应的方法
5. DefaultSqlSession会继续委托给相应的Exexutor(比如是simpleExecutor)
6. Exexutor会从数据源中拿数据库连接对象,通过ParameterHandler进行参数解析(Java数据->sql数据)
7. 最终通过PreparedStatementHandler执行jdbc操作,拿到返回结果集通过ResultSetHandler处理解析结果集(sql数据->Java数据)

其他

1.在同一个spring事务中,自始至终使用的都是同一个DefalutSqlSession对象,原因是创建DefalutSqlSession时会将其绑定到线程的局部变量中,key是DefalutSqlSessionFactory,value是DefalutSqlSession对象
2.真正关闭sqlSession对象在SqlSessionTemplate的beforeCompletion/afterCompletion,而这两个方法beforeCompletion/afterCompletion触发的时机是spring事务TransationAspectSupport执行结束后会触发3.TransactionSynchronizationManager#isSynchronizationActive的理解

image

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/826370.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

DP杂题专练

前言 DP 方面太菜了,要多练习,多思考,多做好题。 摘花生Hello Kitty想摘点花生送给她喜欢的米老鼠。 她来到一片有网格状道路的矩形花生地(如下图),从西北角进去,东南角出来。 地里每个道路的交叉点上都有种着一株花生苗,上面有若干颗花生,经过一株花生苗就能摘走该它上…

基于Axure,对抖音直播,淘宝直播和b站直播的对比分析

设计思路 一、竞品分析 1.竞品选择 淘宝直播,抖音直播,b站直播 2.产品定位对比 2.1搜索指数:从2024年年初到2024年10月底,不难看出抖音直播相较于淘宝和b站直播来说,搜索指数更加的高昂,所带来的流量数据也更多。 抖音直播(绿色线)整体搜索量最高,日均值为2,694,且在…

基于Java+SpringBoot+Mysql实现的快递柜寄取快递系统功能实现七

二、主要技术: 2.1 SpringBoot技术SpringBoot是基于Spring框架的一个开发框架,旨在简化Spring应程序的搭建和开发过程以下是关于SpringBoot技术的一些主要特点和优势: SpringBoot提供了许多自动配置的功能,可以根据的依赖和需要自动配置应程序所需的环境,大大少了开发人员…

学期2024-2025-1 学号20241306 《计算机基础与程序设计》第6周学习总结

学期(如2024-2025-1) 学号(如:20241300) 《计算机基础与程序设计》第X周学习总结 作业信息这个作业属于哪个课程 2024-2025-1-计算机基础与程序设计(https://edu.cnblogs.com/campus/besti/2024-2025-1-CFAP))这个作业要求在哪里 [2024-2025-1计算机基础与程序设计第6周作…

九州信泰杯 第十一届山东省网络安全技能大赛

九州信泰杯 第十一届山东省网络安全技能大赛MISC1.签到这是真签到,下载后即可得到flag2.ezpic打开后,这是一个给了一张图片然后拖到010里面,在末尾找到了一半flag另一半打开打stegsloves通过改变背景颜色然后在里面找到了一个二维码扫码后得到flag的另一半最后拼接flag{cf74…

2024数模b题-问题一思路构建

2024数模b题-问题一思路构建样本量计算根据置信空间的计算公式,逆累积分布函数(ICDF):逆累积分布函数(ICDF)是从累积分布函数的值反推出对应的Z分数。在MATLAB中,norminv 函数就是计算标准正态分布的逆累积分布函数的值我们通过这个公式来得到我们可以得到对于95%置信水平…

数据结构与算法 - 串

KMP字符串匹配算法next数组的计算方法: 看该字符前的字符串的前缀和后缀有多少相同(可以交叉重叠),就让相同的数量值加一即为当前next值。 也可以这样计算:看前一个字符的next值处是否与前一个字符相同,若相同,则当前next值为上一next值加一;若不相同,则查看上一next值…

【产品经理简历模板】绿色清新产品经理求职简历模板下载

【产品经理简历模板】绿色清新产品经理求职简历模板下载,Word【可编辑】,个人简历,免费简历​产品经理求职简历模板下载 绿色清新产品经理求职简历免费下载,可编辑WORD格式简历模板免费下载直接修改,高效-便捷-实用,满足求职者的简历制作需求,简历编辑制作不求人,有效…

【产品经理经理模板】清爽产品经理求职简历模板下载

【产品经理经理模板】清爽产品经理求职免费简历模板下载,Word【可编辑】,个人简历,免费简历模板​产品经理求职简历模板下载 清爽产品经理求职简历免费下载,可编辑WORD格式简历模板免费下载直接修改,高效-便捷-实用,满足求职者的简历制作需求,简历编辑制作不求人,有效…

vovsoft Text Edit Plus v14 离线激活

vovsoft Text Edit Plus v14 目录vovsoft Text Edit Plus v14程序信息text-edit定位按钮事件NagScreen: TNagScreenTNagScreen.BitBtn3ClickTNagScreen.TimerContinueTimerTNagScreen.TimerActivatorTimer离线校验逻辑TChecker 类TChecker.Executecheck_9A6AEC网络请求失败时,校…

指针、引用

内存 1.什么是内存?内存也叫主存储器,用于临时存储数据和程序指令,便于CPU(也就是处理器)快速访问读写非常快,对比硬盘等外存,一秒一般 \(10^8\) 次读写,下面是一个输出一秒大致多少次运算的程序 int main() {//clock_t 是一个用来表示CPU时钟的变量 clock()函数是获取…

javaweb基础总结

截至目前还差最后一个案例 最后再重写一遍所有功能即可 但也包括一些新的功能 学习笔记如下图 一大半代码还是自己敲得 摸样的话大部分都是这样的