SpringBoot事务详解

SpringBoot事务详解一、定义  事务(transaction)是指业务逻辑上对数据库进行的一系列持久化操作,要么全部成功,要么全部失败。二、特性和实现  1、事务的四个基本性质(ACID)  1)原子性(Atomicity)     事务的原子性指事务是一个不可分割的工作单位,这组操作要么全部执行,要么全部不发生。     就拿银行转账来说,原子性指的是从A账户…

大家好,又见面了,我是你们的朋友全栈君。

一、定义

    事务(transaction)是指业务逻辑上对数据库进行的一系列持久化操作,要么全部成功,要么全部失败。

二、特性和实现

    1、事务的四个基本性质(ACID)

    1)原子性(Atomicity)

          事务的原子性指事务是一个不可分割的工作单位,这组操作要么全部执行,要么全部不发生。

          就拿银行转账来说,原子性指的是从A账户扣款和转账到B账户两件事一起发生,不能只发生其中一样。

    2)一致性(Consistency)

          在事务开始的前后,被操作的数据的完整性都处于一致性的状态。

          还是银行转账的例子,一致性指的是在转账的前后A和B两个账户的总金额是不变的,始终保持一致。

    3)隔离性(Isolation)

          多个事务并发时,事务之间是隔离的,每个事务都有自己的完整数据空间,不会影响到其他事物的运行效果。

          事务隔离性的四种隔离级别和实现原理这里就不作阐述,感兴趣的可以看以下两篇博客:

                四种隔离级别      https://blog.csdn.net/qq_33290787/article/details/51924963

                实现原理            https://blog.csdn.net/matt8/article/details/53096405

    4)持久性(Durability)

          事务提交后,该事务对数据所做的修改将持久地保存在数据库,并不会回滚。

    事务的原子性、一致性和持久性是通过数据库的redo/undo日志文件实现的。redo log处理系统故障,undo log处理事务回滚。如果在事务提交之后出现数据库崩溃(断电)的情况,在恢复供电时,数据库会根据重写日志对数据进行前滚。

    2、事务的实现

    在Spring中,事务有两种实现方式,分别是编程式事务和声明式事务。

    编程式事务:编程式事务管理使用Transaction Template或者直接使用底层的Platform TransactionManager。对于编程式事务,Spring推荐使用Transaction Template。TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();

    声明式事务:声明式事务基于AOP,其本质是对方法前后进行拦截,在方法开始前创建或加入一个事务,再根据目标方法执行的结果决定提交还是回滚事务。只需要在类、方法加上@Transactional注解就可以使用事务,没有入侵性,简单粗暴。

三、声明式事务的使用技巧

    1、@Transactional可以作用于接口、接口方法、类、类方法上,当作用到类时,该类下所有public方法都将具有该类型的事务属性,同时,也可以在方法级别使用该注解来覆盖类级别的定义。Spring的建议是在具体的实现类和类方法使用@Transactional注解,而不是使用在接口上。因为注解不能继承,不能被基于接口的代理类所识别,注解失效。

    2、声明式事务管理默认只对非检查型异常unchecked Exception进行回滚,也就是对RuntimeException异常以及它的子类进行回滚操作。

SpringBoot事务详解

    如果需要让checked Exception也进行回滚,需加上@Transactional(rollbackFor=Exception.class)、

    如果需要让unchecked Exception不进行回滚,需加上@Transactional(notRollbackFor=Exception.class)

    3、在Springboot使用声明式事务需要在Application启动类加入@EnableTransactionManagement注解,相当于Spring的自动扫描

 

四、声明式事务的常用配置

参 数 名 称 功 能 描 述
readOnly 该属性用于设置当前事务是否为只读事务,设置为true表示只读,false则表示可读写,默认值为false。例如:@Transactional(readOnly=true)
rollbackFor 该属性用于设置需要进行回滚的异常类数组,当方法中抛出指定异常数组中的异常时,则进行事务回滚。例如:指定单一异常类:@Transactional(rollbackFor=RuntimeException.class)指定多个异常类:@Transactional(rollbackFor={RuntimeException.class, Exception.class})
rollbackForClassName 该属性用于设置需要进行回滚的异常类名称数组,当方法中抛出指定异常名称数组中的异常时,则进行事务回滚。例如:指定单一异常类名称@Transactional(rollbackForClassName=”RuntimeException”)指定多个异常类名称:@Transactional(rollbackForClassName={“RuntimeException”,”Exception”})
noRollbackFor 该属性用于设置不需要进行回滚的异常类数组,当方法中抛出指定异常数组中的异常时,不进行事务回滚。例如:指定单一异常类:@Transactional(noRollbackFor=RuntimeException.class)指定多个异常类:@Transactional(noRollbackFor={RuntimeException.class, Exception.class})
noRollbackForClassName 该属性用于设置不需要进行回滚的异常类名称数组,当方法中抛出指定异常名称数组中的异常时,不进行事务回滚。例如:指定单一异常类名称:@Transactional(noRollbackForClassName=”RuntimeException”)指定多个异常类名称:@Transactional(noRollbackForClassName={“RuntimeException”,”Exception”})
propagation 该属性用于设置事务的传播行为。例如:@Transactional(propagation=Propagation.NOT_SUPPORTED,readOnly=true)
isolation 该属性用于设置底层数据库的事务隔离级别,事务隔离级别用于处理多事务并发的情况,通常使用数据库的默认隔离级别即可,基本不需要进行设置
timeout 该属性用于设置事务的超时秒数,默认值为-1表示永不超时

 

五、声明式事务的隔离级别

隔离级别是指若干个并发的事务之间的隔离程度。TransactionDefinition 接口中定义了五个表示隔离级别的常量:

TransactionDefinition.ISOLATION_DEFAULT:这是默认值,表示使用底层数据库的默认隔离级别。对大部分数据库而言,通常这值就是TransactionDefinition.ISOLATION_READ_COMMITTED。 
TransactionDefinition.ISOLATION_READ_UNCOMMITTED:该隔离级别表示一个事务可以读取另一个事务修改但还没有提交的数据。该级别不能防止脏读,不可重复读和幻读,因此很少使用该隔离级别。比如PostgreSQL实际上并没有此级别。 
TransactionDefinition.ISOLATION_READ_COMMITTED:该隔离级别表示一个事务只能读取另一个事务已经提交的数据。该级别可以防止脏读,这也是大多数情况下的推荐值。 
TransactionDefinition.ISOLATION_REPEATABLE_READ:该隔离级别表示一个事务在整个过程中可以多次重复执行某个查询,并且每次返回的记录都相同。该级别可以防止脏读和不可重复读。 
TransactionDefinition.ISOLATION_SERIALIZABLE:所有的事务依次逐个执行,这样事务之间就完全不可能产生干扰,也就是说,该级别可以防止脏读、不可重复读以及幻读。但是这将严重影响程序的性能。通常情况下也不会用到该级别。

 

六、声明式事务的传播行为

所谓事务的传播行为是指,如果在开始当前事务之前,一个事务上下文已经存在,此时有若干选项可以指定一个事务性方法的执行行为。在TransactionDefinition定义中包括了如下几个表示传播行为的常量:

TransactionDefinition.PROPAGATION_REQUIRED:如果当前存在事务,则加入该事务;如果当前没有事务,则创建一个新的事务。这是默认值。 
TransactionDefinition.PROPAGATION_REQUIRES_NEW:创建一个新的事务,如果当前存在事务,则把当前事务挂起。 
TransactionDefinition.PROPAGATION_SUPPORTS:如果当前存在事务,则加入该事务;如果当前没有事务,则以非事务的方式继续运行。 
TransactionDefinition.PROPAGATION_NOT_SUPPORTED:以非事务方式运行,如果当前存在事务,则把当前事务挂起。 
TransactionDefinition.PROPAGATION_NEVER:以非事务方式运行,如果当前存在事务,则抛出异常。 
TransactionDefinition.PROPAGATION_MANDATORY:如果当前存在事务,则加入该事务;如果当前没有事务,则抛出异常。 
TransactionDefinition.PROPAGATION_NESTED:如果当前存在事务,则创建一个事务作为当前事务的嵌套事务来运行;如果当前没有事务,则该取值等价于TransactionDefinition.PROPAGATION_REQUIRED。

 

参考博客:

 

SpringBoot事务注解@Transactional    https://blog.csdn.net/wkl305268748/article/details/77619367

事务的四大特征      https://blog.csdn.net/longxingzhiwen/article/details/53912475

理解事务的四种隔离级别     https://blog.csdn.net/qq_33290787/article/details/51924963 

@Transactional(rollbackFor=Exception.class)的使用  https://blog.csdn.net/Mint6/article/details/78363761

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/131191.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)
blank

相关推荐

  • 深入解析数据压缩算法[通俗易懂]

    深入解析数据压缩算法[通俗易懂]1、为什么要做数据压缩?    数据压缩的主要目的还是减少数据传输或者转移过程中的数据量。2、什么是数据压缩?     是指在不丢失信息的前提下,缩减数据量以减少存储空间,提高传输、存储和处理效率的一种技术方法。或者是按照一定的算法对数据进行重新组织,减少数据的冗余和存储的空间。 3、常见的数据压缩算法(1).LZW压缩    LZW压缩是一种无损压缩,应用于gif图片。适用…

    2022年10月24日
  • mysql 获取分区的最大值_MySQL分区表测试「建议收藏」

    mysql 获取分区的最大值_MySQL分区表测试「建议收藏」MYSQL分区表功能测试。1.查看Mysql版本是否支持分区SHOWVARIABLESLIKE’%partition%’;+——————-+——-+|Variable_name|Value|+——————-+——-+|have_partitioning|YES|+——————…

  • phpstorm 2021.9 激活码_在线激活

    (phpstorm 2021.9 激活码)最近有小伙伴私信我,问我这边有没有免费的intellijIdea的激活码,然后我将全栈君台教程分享给他了。激活成功之后他一直表示感谢,哈哈~IntelliJ2021最新激活注册码,破解教程可免费永久激活,亲测有效,下面是详细链接哦~https://javaforall.cn/100143.html…

  • HTML5的Video标签的属性,方法和事件汇总

    HTML5的Video标签的属性,方法和事件汇总

  • 用户态和内核态的简单理解「建议收藏」

    用户态和内核态的简单理解「建议收藏」文章目录linux基础系统调用和库函数的区别什么是用户态和内核态用户态和内核态的相互转换linux基础linux的kernel内核外是系统调用,系统调用外是shell、库函数系统调用和库函数的区别内核:屏蔽了调用各硬件资源的细节系统调用:内核提供给用户调用的接口,但系统调用的可移植性差移植性差的原因:windows、linux内核的系统调用是不同的,比如:同一个功能提供给用户的函数名、参数都不相同,会出现从一个系统移植到另一个系统无法正常运行。库函数:为了解决系统调用移植新差的问题,同时封

  • 2021Eclipse下载与安装教程

    2021Eclipse下载与安装教程2021Eclipse下载与安装教程2021Eclipse下载与安装教程具体步骤如下:1.下载1.1官方下载1.2国内镜像下载【推荐】2.安装3.安装插件2021Eclipse下载与安装教程具体步骤如下:1.下载Eclipse软件下载可以在Eclipse官方下载,也可以在国内镜像地址下载。由于Eclipse官方地址服务器在国外,下载速度比较慢,国内镜像地址下载速度会快很多。1.1官方下载官方下载地址:https://www.eclipse.org/downloads/packages/r

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号