事务的总结

事务的传播行为

当事务方法被另一个事务方法调用时,必须指定事务应该如何传播。比如,方法可能在现有的事务中运行,也可能开启一个新事务,并在自己的事务中运行。
事务的传播行为可以有事务的传播属性来指定,Spring定义了七种类传播行为;

  • REQUIRED:如果有事务在运行,当前的方法就在这个事务中运行,否则,就开启一个事务,并在自己的事务中运行;
  • REQUIRES_NEW:当前的方法必须开启新事务,并在自己的事务中运行,如果已经有事务在运行,必须将其挂起;
  • SUPPORTS:如果有事务正在运行,当前方法可以在其中运行,但是如果没有事务在运行,它也可以不用运行在事务中;
  • NOT_SUPPORTED:当前的方法不能运行在事务中,如果当前有事务在运行,就将它挂起;
  • MANDATORY:当前的方法必须运行在事务中,如果没有运行的事务,就抛出异常;
  • NEVER:当前的方法不应该运行在事务中,如果有运行的事务,就抛出异常;
  • NESTED:如果有事务在运行,当前的方法就在他的嵌套事务中运行,否则,就启动一个新的事务,并在它自己的事务中运行;

事务的传播属性可以在@Transactional注解的propagation属性中定义。

数据库事务的并发问题

假设现在有两个事务并发执行,Transaction01和Transaction02;
1.脏读:某个事务读取了其他事务更新但未提交的数据,这种时候容易发生;
(1)Transaction01将某条记录的数值从20更新为30,但是并没有提交;
(2)这时Transaction02读取了Transaction01更新后的值30;
(3)但是Transaction01由于出现异常,将数据回滚回了数值20;
(4)这种状况下Transaction02读取的数值30就是一个脏的数据
2.不可重复读:
(1)Transaction01第一次读取某个数值时是20;
(2)Transaction02这时也读取了该数值,并且将数值更新为30;
(3)Transaction01第二次在读取该值时,发现该值是30,跟第一次读取的值不一样了,这就叫不可重复读;
3.幻读:
(1)Transaction01刚从表中读取了一部分数据;
(2)Transaction02这时向表中插入了一些数据;
(3)Transaction01再次读取时突然发现多了好多数据,就像出现了幻觉一样,这种就叫幻读;

为了解决事务的并发问题,我们就需要去设置事务的隔离级别。
数据库系统必须具有隔离并发运行各个事务的能力,使他们不会相互影响,避免各种并发问题,一个事务与其他事务隔离的程度被称为隔离级别。

  1. 读未提交(read uncommitted):允许事务读取其他事务未提交已修改的数据;
  2. 读已提交(read committed):事务只能读取其他事务提交之后的数据;这种状况解决了脏读的问题;
  3. 可重复读(repeatable read):确保Transaction01可以多次从一个字段中读取到相同的值,即Transaction01执行期间禁止其他事务对该记录做修改;这种状况解决了脏读,不可重复读的问题;
  4. 串行化(serializable):确保Transaction01可以多次从一个表中读取到相同的行,即在Transaction01执行期间,禁止其他事务对整个表进行添加,更新,删除的操作,可以避免任何的并发问题,但是性能比较差;这种状况解决了脏读,不可重复读,幻读的问题;

事务的传播属性可以在@Transactional注解的isolation属性中定义。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值