spring 事务回滚失败异常

1 背景介绍

事务模板里抛异常,抛异常前的update操作成功,事务没有回滚成功,业务数据还是落db了。debug代码,发现GenericConnectionContext类中derivedConnectionMap是空的,导致回滚代码没有执行

2 解决方案

保证事务内所有的 DAO 操作所涉及的数据源和事务模板所关联的数据源都是同一个对象, bundle 都是 Spring 上下文隔离的,也需要 DAO 和事务模板在同一个 bundle 内。

需要注意创建事务模版地方的数据源,和 dao 对应的数据源是同一个,如果不是,需要重新建一个事务模版。

3 更多基础知识

事务五个隔离

3.1** ISOLATION_DEFAULT:默认隔离级别**

这是一个PlatfromTransactionManager默认的隔离级别,使用数据库默认的事务隔离级别,

**oracle默认的是.:READ_COMMITTED **,

**mysql默认的是:REPEATABLE_READ **

另外四个与JDBC的隔离级别相对应;

3.2** **ISOLATION_READ_UNCOMMITTED:读未提交

这是事务最低的隔离级别,它充许别外一个事务可以看到这个事务未提交的数据。

这种隔离级别会产生脏读,不可重复读和幻像读。

3.3** ****ISOLATION_READ_COMMITTED:读已提交 **

保证一个事务修改的数据提交后才能被另外一个事务读取。另外一个事务不能读取该事务未提交的数据。

这种事务隔离级别可以避免脏读出现,但是可能会出现不可重复读和幻像读。

3.4** ****ISOLATION_REPEATABLE_READ:可重复读 **

这种事务隔离级别可以防止脏读,不可重复读。但是可能出现幻像读。

它除了保证一个事务不能读取另一个事务未提交的数据外,还保证了避免下面的情况产生(不可重复读)。

3.5** ****ISOLATION_SERIALIZABLE:序列化 **

这是花费最高代价但是最可靠的事务隔离级别。事务被处理为顺序执行。

除了防止脏读,不可重复读外,还避免了幻像读。

什么是 脏读,不可重复读,虚读?

脏读 :指一个事务读取了一个未提交事务的数据

**说明:**事务1更新了记录,但没有提交,事务2读取了更新后的行,然后事务T1回滚,现在T2读取无效。

不可重复读 :在一个事务内读取表中的某一行数据,多次读取结果不同.一个事务读取到了另一个事务提交后(update)的数据.

**说明:**事务1读取记录时,事务2更新了记录并提交,事务1再次读取时可以看到事务2修改后的记录;

虚读(幻读) :在一个事务内读取了别的事务插入的数据,导致前后读取不一致(insert)

**说明:**事务1读取记录时事务2增加了记录并提交,事务1再次读取时可以看到事务2新增的记录;

不可重复读与幻读的区别?

不可重复读的重点是修改: 同样的条件, 你读取过的数据, 再次读取出来发现值不一样了

在一个事务中前后两次读取的结果并不一致,导致了不可重复读。

例如:在事务1中,Mary 读取了自己的工资为1000,操作并没有完成

c 复制代码
con1 = getConnection();  
    select salary from employee empId ="Mary";

在事务2中,这时财务人员修改了Mary的工资为2000,并提交了事务.

c 复制代码
con2 = getConnection();  
    update employee set salary = 2000;  
    con2.commit();

在事务1中,Mary 再次读取自己的工资时,工资变为了2000

c 复制代码
//con1  
    select salary from employee empId ="Mary";

幻读的重点在于新增或者删除:

同样的条件, 第1次和第2次读出来的记录数不一样

例如:目前工资为1000的员工有10人。事务1,读取所有工资为1000的员工。

c 复制代码
con2 = getConnection();  
    Insert into employee(empId,salary) values("Lili",1000);  
    con2.commit();

事务1再次读取所有工资为1000的员工

c 复制代码
select * from employee where salary =1000;

共读取到了11条记录,这就产生了幻读。

从总的结果来看, 似乎不可重复读和幻读都表现为两次读取的结果不一致。

但如果你从控制的角度来看, 两者的区别就比较大。 对于前者, 只需要锁住满足条件的记录。 对于后者, 要锁住满足条件及其相近的记录。

4 事务的四个特性?

事务的四个特性(ACID)

4.1 原子性

原子性(Atomicity):操作这些指令时,要么全部执行成功,要么全部不执行。只要其中一个指令执行失败,所有的指令都执行失败,数据进行回滚,回到执行指令之前的数据状态

4.2 一致性

一致性(Consistency):事务的执行使数据从一个状态转换为另一个状态,但是对于整个数据的完整性保持稳定

4.3 隔离性

隔离性(Isolation):是当多个用户并发访问数据库时,比如操作同一张表时,数据库为每一个用户开启的事务,不能被其他事务的操作所干扰,多个并发事务之间要相互隔离。

即:要达到这么一种效果:对于任意两个并发的事务T1和T2,在事务T1看来,T2要么在T1开始之前就已经结束,要么在T1结束之后才开始,这样每个事务都感觉不到有其他事务在并发地执行

4.4 持久性

持久性(Durability):当事务正确完成后,它对于数据的改变时永久性的

相关推荐
0zxm5 分钟前
06 - Django 视图view
网络·后端·python·django
m0_748257185 分钟前
Spring Boot FileUpLoad and Interceptor(文件上传和拦截器,Web入门知识)
前端·spring boot·后端
Yan.love38 分钟前
开发场景中Java 集合的最佳选择
java·数据结构·链表
椰椰椰耶42 分钟前
【文档搜索引擎】搜索模块的完整实现
java·搜索引擎
大G哥42 分钟前
java提高正则处理效率
java·开发语言
小_太_阳1 小时前
Scala_【1】概述
开发语言·后端·scala·intellij-idea
智慧老师1 小时前
Spring基础分析13-Spring Security框架
java·后端·spring
lxyzcm1 小时前
C++23新特性解析:[[assume]]属性
java·c++·spring boot·c++23
V+zmm101342 小时前
基于微信小程序的乡村政务服务系统springboot+论文源码调试讲解
java·微信小程序·小程序·毕业设计·ssm
Oneforlove_twoforjob2 小时前
【Java基础面试题025】什么是Java的Integer缓存池?
java·开发语言·缓存