一个宁静祥和没有bug的下午和SqlSession的故事
1 背景
这是一个安静祥和没有bug的下午。
作为一只菜鸡,时刻巩固一下基础还是很有必要的,如此的大好时机,就让我来学习学习mybatis如何使用。

这可和我看到的不一样啊,让我来看看项目里怎么写的。

我们项目中的Dao都继承于BaseDao,而BaseDao继承于SqlSessionDaoSupport,每次执行sql的时候都是直接将这个sqlSession返回,然后执行sql,这难道不是一个实例变量嘛?这和你说的可不一样诶。于是带着这样的疑问,我开始了探索。
2 探索之旅
1)我们都知道,在使用mybatis时,sqlSession都来自于sqlSessionFactory,而sqlSessionFactory可以通过sqlSessionFactoryBuilder创建,也可以通过spring初始化,而项目中很显然采取了后一种方式。

2)那么我们已经得到了sqlSessionFactory,应该如何去进一步探索sqlSession的来源呢,我想到可以通过项目中已经实现的dao进行探索。我们随便选取一个dao为例。

它继承了BaseDao。

而BaseDao又继承了SqlSessionDaoSupport,在BaseDao中调用了getSqlSession方法,实际上也就是SqlSessionDaoSupport的getSqlSession方法。

而SqlSessionDaoSupport的getSqlSession方法是直接将自己的成员变量返回去的,截至目前为止,和我的怀疑点是相符合的,即目前的写法和mybatis官网的说明是冲突的。
3)反复阅读SqlSessionDaoSupport这个类后,终于被我发现了线索,细心的小伙伴应该也早已发现了,就在上图之中的注释中,“用户应该使用这个方法来获得一个SqlSession来执行sql语句,这个SqlSession被spring管理,用户不应该提交、回滚或关闭它。因为这些已经被自动执行了。”
同时,这个方法会返回一个线程安全的SqlSession。

那么这个SqlSession是从何而来的呢,从上图可以看出,它有两种赋值方式,一种是给他传一个SqlSessionFactory,生成SqlSessionTemplate,SqlSessionTemplate即为sqlSession。另一种是直接给他传一个SqlSessionTemplate作为SqlSession。根据本类的注释,如果SqlSessionFactory和SqlSessionTemplate都被定义了,那么SqlSessionFactory的方式会失效。至此,我的上述疑问已经解决了,也就是说这个SqlSession并不是一个mybatis初始的SqlSession,而是spring实现的SqlSessionTemplate。
4)但是,我又诞生了新的疑问,SqlSessionTemplate是怎么完成线程安全的呢?

于是我进入了SqlSessionTemplate的方法执行,发现实际执行语句的都是这个代理类sqlSessionProxy。

而代理工作内容就在SqlSessionInterceptor这个handler里。

进入其中,我们终于发现了它的获取和关闭操作。


也就是说,每次执行,代理都会调用sessionFactory的openSession方法获得一个新的session。
3 总结
终于的终于,mybatis,spring,项目以及我的疑问得到了统一,真是一个宁静祥和而又没有bug的下午呀。
作者:马跃
一个宁静祥和没有bug的下午和SqlSession的故事的更多相关文章
- ASP.NET MVC的Ajax.ActionLink 的HttpMethod="Get" 一个重复请求的BUG
这段时间使用BootStrap+Asp.net Mvc5开发项目,Ajax.ActionLink遇到一个重复提交的BUG,代码如下: @model IList<WFModel.WF_Temp&g ...
- 最近提交一个mysql5.7的bug,提醒自己以后注意写SQL要规范
最近帮朋友提交一个mysql5.7的bug , oracle mysql 的大神还回复我 , 以后注意书写sql规范 , 潜台词是不是不要给他们增加工作量 https://bugs.mysql.com ...
- 移动端一个奇怪的触摸bug
这两天遇到一个很奇怪的bug,在移动端,一个页面里所有的input框都不能点击,我查了一下,里面的没有设置readonly属性,只要页面滚动一下就可以用了,而且,只要我在真机测试的时候,f12开发者模 ...
- “在注释中遇到意外的文件结束”--记一个令人崩溃的bug
下午写程序,写的好好的,突然报错"在注释中遇到意外的文件结束". 下面是官方给出的错误原因是缺少注释终结器 (* /). // C1071.cpp int main() { } / ...
- STL 库中的陷阱----一个难以察觉的 bug
请找出下面程序的 bug? int maxProfit2(vector<int> &prices) { int local[3] = {0}; int global[3] = {0 ...
- 一个因为粗心的Bug
/** * 数据绑定,分页显示 */ private void updataMenu(final EditText search) { if(listwz==null) { return; } pag ...
- 一个空格引发的bug
好久没写博客了. 我们的一个项目用的thinkphp框架,当在debug模式下面运行很正常,但切换到生产模式时,刷新页面第一次可以正常显示,刷新第二次会出现错误如下: Fatal error: Cal ...
- 表与表的关系把RD搞乱了,记一个Procedure中的bug
就是6张表的关联查询,写了一个存储过程,使用4层for来处理 bug:最后一个for中,两张表的关联条件少了一个,结果数据多查了. 排查办法:使用dbms_output.printline('');每 ...
- 记一个CRenderTarget中的BUG及解决办法
转载请注明出处:http://www.cnblogs.com/Ray1024 一.问题描述 在MFC中使用Direct2D有现成的方法,在Visual Studio 2010 SP1及以上环境中MFC ...
- 一个毕生难忘的BUG
记得以前接手过一个Java项目,服务器程序,直接让Jar在linux上跑的那种, 这个项目由两个web服务组成,也就是两条Java进程,主进程 xxx.jar,辅助进程 xxx_helper.jar. ...
随机推荐
- 如何使用helm优雅安装prometheus-operator,并监控k8s集群微服务
前言:随着云原生概念盛行,对于容器.服务.节点以及集群的监控变得越来越重要.Prometheus 作为 Kubernetes 监控的事实标准,有着强大的功能和良好的生态.但是它不支持分布式,不支持数据 ...
- 【一月一本技术书】-【MySQL是怎样运行的】- 8月
mysql 基础 mysql分为 客戶端/服务端 客户端向服务端发送一段文本(mysql语句),服务器处理后向客户端进程返回一段文本. 查询请求执行过程 客户端->处理连接->查询缓存-& ...
- 我也是一个“翻译家”——关于“robust”
每次看到"鲁棒性",总是不知道是什么意思,一度怀疑自己是不是中国人,是不是说汉语.每次都要查英汉字典,然后一次次看到: robust(adj.精力充沛的; 坚定的; 粗野的,粗鲁的 ...
- 4.Ceph 基础篇 - 对象存储使用
文章转载自:https://mp.weixin.qq.com/s?__biz=MzI1MDgwNzQ1MQ==&mid=2247485256&idx=1&sn=39e07215 ...
- Grafana 入门知识介绍
通过[Configuration]>[Plugins]添加插件 通过[Configuration]>[Data Sources]添加数据源(分析对象) 通过[Server Admin]&g ...
- 高光谱图像分类简述+《Deep Learning for Hyperspectral Image Classification: An Overview》综述论文笔记
论文题目<Deep Learning for Hyperspectral Image Classification: An Overview> 论文作者:Shutao Li, Weiwei ...
- SqlKata - 方便好用的 Sql query builder
SqlKata查询生成器是一个用C# 编写的功能强大的Sql查询生成器.它是安全的,与框架无关.灵感来源于可用的顶级查询生成器,如Laravel Query Builder和 Knex. SqlKat ...
- PHP全栈开发(三):CentOS 7 中 PHP 环境搭建及检测
简单回顾一下我们在(一).(二)中所做的工作. 首先我们在(一)中设置了CentOS 7的网络. 其实这些工作在CentOS 6中都是很容易的,因为有鸟哥的Linux私房菜这样好的指导. 但是这些操作 ...
- 洛谷P7167 [eJOI 2020 Day1] Fountain (单调栈+ST)
开两个数组:to[i][j]表示从i这个位置向下的第2j个圆盘是哪个,f[i][j]表示流满从i这个位置向下的 2j 个圆盘需要多少体积的水. 详情见代码: 1 #include<bits/st ...
- Linux中CentOS 7版本安装JDK、Tomcat、MySQL、lezsz、maven软件详解
软件安装 在Linux系统中,安装软件的方式主要有四种,这四种安装方式的特点如下: 安装方式 特点 二进制发布包安装 软件已经针对具体平台编译打包发布,只要解压,修改配置即可 rpm安装 软件已经按照 ...