Spring事务与事务传播

news2024/11/19 9:23:28

在这里插入图片描述

文章目录

  • 一、什么是事务?
  • 二、Spring事务实现
    • 编程式事务
    • 声明式事务
  • 三、@Transactional的使用
    • 参数作用
    • Spring事务的隔离级别
    • 事务失效的场景
    • @Transactional工作原理
  • 四、Spring事务传播机制
    • Spring有哪些事务传播机制?

一、什么是事务?

事务:事务是一组操作的集合,是不可分割的基本单位,要么全部成功,要么全部失败
我们在MySQL中使用事务有三步操作:开启事务,提交事务,回滚事务

-- 开启事务
start transaction;

-- 执行具体业务

-- 提交事务
commit;

-- 回滚事务
rollback

事务的四大特性(ACID): 原子性、一致性、持久性、隔离性
原子性(Atomicity):一个事务的操作,要么全部完成,要么全部不完成
一致性(Consistency):事务开始之前和事务结束之后,数据库的完整性没有被破坏
持久性(Isolation):事务提交后,对数据的修改就是永久的
隔离性(Durability):数据库允许多个并发事务同时对其数据读写和修改的能力,隔离性可以防止多个事务并发执行时导致的数据不一致
隔离级别是可以设置的

事务的隔离级别: 在数据库中,多个事务并发执行时,各个事务之间是相互隔离的,每个事务之间都不能相互干扰。为了保证并发事务的正确性和一致性,数据库管理系统(DBMS)提供了四种事务隔离级别,分别为读未提交、读已提交、可重复读和串行化。

读未提交(Read Uncommitted)
在该隔离级别下,一个事务可以读取另一个事务尚未提交的数据,不仅如此,它可能还会读到一些脏数据(Dirty Read)。在该级别下,数据的一致性和完整性得不到保障,不推荐使用。

读已提交(Read Committed)
在该隔离级别下,一个事务只能读取另一个事务已经提交的数据,避免了脏读的问题,但是可能会出现不可重复读(Non-Repeatable Read)的问题。即同一事务中,多次读取同一数据可能会得到不同的结果,因为其他事务可能在两次读取之间提交了修改。

可重复读(Repeatable Read)
在该隔离级别下,一个事务在执行期间多次读取同一数据时,能够保证所读取的数据一定是事务开始时的状态,避免了不可重复读的问题,但是可能会出现幻读(Phantom Read)问题,即两次查询间新增数据的影响。

串行化(Serializable)
在该隔离级别下,所有事务串行执行,避免了脏读、不可重复读和幻读的问题,但是实际应用中可能会导致性能严重下降,因此该级别一般只在特殊情况下使用。

默认隔离级别为REPEATABLE READ
在这里插入图片描述

我们可以使用以下SQL查询全局事务隔离级别和当前连接的事务隔离级别:

select @@global.tx_isolation,@@tx_isolation;

在这里插入图片描述

二、Spring事务实现

Spring中的事务分为两类:
1.编程式事务(手动操作)
2.声明式事务(自动提交事务)

编程式事务

SpringBoot内置了两个对象,DataSourceTransactionManager用来获取事务(开启事务、提交事务、回滚事务)。TransactionDefinition是事务的属性,在获取事务时,需要将TransactionDefinition传递进去获取一个TransactionStatus

@RestController
@RequestMapping("/user")
public class UserController {

    @Autowired
    private UserService userService;
    @Autowired
    private DataSourceTransactionManager transactionManager;
    @Autowired
    private TransactionDefinition transactionDefinition;

    @RequestMapping("/del")
    public int del(Integer id) {
        if(id != null && id > 0) {
            //开启事务
            TransactionStatus transactionStatus =
                    transactionManager.getTransaction(transactionDefinition);
            //删除用户业务操作
            int result = userService.del(id);
            System.out.println("删除了: " + result);
            // 提交事务/回滚事务
//            transactionManager.commit(transactionStatus); //提交事务
            transactionManager.rollback(transactionStatus); //回滚事务
        }
        return 0;
    }
}

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
数据库原始数据:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
这里显示操作成功,我们来看看我们数据库数据发生变化了没
在这里插入图片描述
我们可以发现,事务成功的进行了回滚,但是这样的方式太繁琐了,我们来学习更简单的声明式事务

声明式事务

声明式事务我们只需要在方法上@Transactional注解就可以实现,无需手动进行开启事务和提交事务,进入方法自动开启,执行完毕自动提交,发生异常后会自动回滚事务

@RestController
@RequestMapping("/user2")
public class UserController2 {

    @Autowired
    private UserService userService;

    @Transactional
    @RequestMapping("/del")
    public int del(Integer id) {
        if(id == null || id <= 0) {
            return 0;
        }
        return userService.del(id);
    }
}

这种是没有异常的异常,我们会进行commit,我们目前数据库数据:
在这里插入图片描述
在这里插入图片描述

在这里插入图片描述

我们可以发现成功的删除了数据库的一条数据:
在这里插入图片描述
我们来在业务中加上一段异常代码:

@RestController
@RequestMapping("/user2")
public class UserController2 {

    @Autowired
    private UserService userService;

    @Transactional
    @RequestMapping("/del")
    public int del(Integer id) {
        if(id == null || id <= 0) {
            return 0;
        }
        int result = userService.del(id);
        int n = 1 / 0; //异常业务
        return result;
    }
}

我们再来进行删除操作:
在这里插入图片描述

在这里插入图片描述
我们可以看到我们的控制台信息,成功的进行了删除操作
在这里插入图片描述
同时报了一个算术异常
在这里插入图片描述
我们查看数据库信息,发现当发生异常时会自动进行回滚操作。

三、@Transactional的使用

@Transactional的作用范围:@Transactional既可以用来修饰方法也可以用来修饰类
1.修饰方法:只能应用到public方法上,否则不生效,推荐用法
2.修饰类:表明该注解对所有的public方法都生效

参数作用

我们可以通过设置@Transactional的一些参数来决定事务的一些具体的功能
在这里插入图片描述

Spring事务的隔离级别

Spring的事务隔离级别是有以下5种的
在这里插入图片描述
1.DEFAULT:使用底层数据库默认的隔离级别。
2.READ_UNCOMMITTED:允许读取还未提交的数据,会出现脏读、不可重复读和幻读等问题。
3.READ_COMMITTED:只能读取已经提交的数据,避免了脏读的问题,但是可能出现不可重复读和幻读的问题。
4.REPEATABLE_READ:保证同一事务中多次读取同一记录结果是一致的,避免了脏读和不可重复读的问题,但是仍然可能出现幻读的问题。
5.SERIALIZABLE:最高的隔离级别,保证事务串行执行,避免了脏读、不可重复读和幻读等问题,但是影响系统性能。

默认情况下,Spring 会使用底层数据库的默认隔离级别,通常是READ_COMMITTED 级别。可以通过事务管理器的 setDefaultTransactionIsolation() 方法或在事务注解中使用 isolation 属性来设置隔离级别,例如:

@Transactional(isolation = Isolation.DEFAULT)
    @RequestMapping("/del")
    public int del(Integer id) {
    }

在这里插入图片描述

在这里插入图片描述

事务失效的场景

常见的事务失效场景有以下三种:
1.异常捕获处理: @Transactional 在异常被捕获的情况下,不会进行事务自动回滚
在这里插入图片描述
我们进行操作之前的数据库数据,我们进行try,catch处理
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
我们发现程序抛出了异常,但并没有进行回滚操作
在这里插入图片描述
原因:事务通知只有自己捕捉到了目标抛出的异常,才能进行后续的回滚操作,如果目标自己处理掉了异常,事务无法知悉

解决方案: 在catch块中添加throw new RuntimeException(e)抛出
在这里插入图片描述
我们将数据恢复
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
我们来进行操作时,进行了回滚操作

2.抛出检查异常:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
我们的事务未进行回滚操作
原因:Spring默认值只会回滚非检查异常

解决方案: 配置rollbackFor属性
在这里插入图片描述
在这里插入图片描述
在进行操作时,事务成功的进行了回滚操作

3.非public方法导致的事务失效:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
事务没有进行回滚操作
原因:Spring为方法创建代理,添加事务通知、前提条件都是该方法为public

解决方案: 改为Public

@Transactional工作原理

@Transactional 是基于 AOP 实现的,AOP 又是使用动态代理实现的。如果目标对象实现了接口,默认情况下会采用 JDK 的动态代理,如果目标对象没有实现了接口,会使用 CGLIB 动态代理。
@Transactional 在开始执行业务之前,通过代理先开启事务,在执行成功之后再提交事务。如果中途遇到异常,会进行回滚业务
在这里插入图片描述
@Transactional 具体执行细节如下图所示:
在这里插入图片描述

四、Spring事务传播机制

Spring事务传播机制定义了多个包含事务的方法,相互调用时
为什么需要事务传播机制?事务隔离级别不够用吗?
事务隔离级别是保证多个并发事务执行是可控的,而事务传播机制是保证一个事务在多个调用方法间是可控的。
事务隔离级别是为了解决多个事务同时调用一个数据库的问题:

在这里插入图片描述
事务传播机制是解决一个事务在多个方法中传递的问题:

在这里插入图片描述

Spring有哪些事务传播机制?

Spring 支持以下七种事务传播机制:

1.PROPAGATION_REQUIRED:默认值,如果当前存在一个事务,则加入该事务;否则新建一个事务。这是最常见的传播机制,也是大多数情况下使用的传播机制。如果外围方法已经启动了事务,那么内部方法就会在该事务中运行;如果外围方法尚未启动事务,则内部方法会启动一个新的事务。

2.PROPAGATION_REQUIRES_NEW:将当前事务挂起,开启一个新的事务进行执行。如果当前存在事务,则将当前事务挂起并启动一个新事务;如果当前没有事务,则开启一个新的独立事务。
3.PROPAGATION_SUPPORTS:如果当前存在事务,则加入该事务;否则以非事务方式继续运行。若外围方法有事务,则使用该事务;若外围方法没有事务,则直接执行。
4.PROPAGATION_NOT_SUPPORTED:以非事务方式运行,如果当前存在事务,则将该事务挂起。若外围有事务,则将当前事务挂起,然后以非事务方式执行;若外围没有事务,则直接以非事务方式执行。
5.PROPAGATION_NEVER:表示当前方法不应该执行在事务上下文中。如果当前事务存在,则抛出异常。即表示当前方法不能够在事务环境中运行。
6.PROPAGATION_MANDATORY:当前方法必须在事务上下文中运行,否则抛出异常。要求当前环境中必须存在事务,否则会抛出异常。
7.PROPAGATION_NESTED:如果当前存在事务,则开启一个子事务进行执行;如果当前不存在事务,则新建一个事务进行执行。嵌套事务和普通事务的区别是,嵌套事务可以独立于外围事务进行提交或回滚,而不影响外围事务的状态。如果外围事务已经提交或回滚,则子事务也会被提交或回滚,但如果子事务发生异常而回滚,则外围事务可以选择回滚或不回滚。

事务传播机制可以分为以下三类:
在这里插入图片描述
我们可以更形象的看一下下述图来理解(别的大佬的图):
在这里插入图片描述

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Python十类常见异常类型(附捕获以及异常处理方式)

目录 前言十类异常1.TypeError2.ValueError3.NameError4.IndexError5.KeyError6.ZeroDivisionError7.IOError8.ImportError9.AttributeError10.KeyboardInterrupt 异常捕获以及处理总结 前言 大家好&#xff0c;我是辣条哥&#xff01;今天给大家讲讲我们刚开始写代码是都会出现…

系统学习】Java基础3之反射

Java反射 反射机制概述 Reflection&#xff08;反射&#xff09;是被视为动态语言的关键&#xff0c;反射机制允许程序在执行期借助于Reflection API取得任何类的内部信息&#xff0c;并能直接操作任意对象的内 部属性及方法 加载完类之后&#xff0c;在堆内存的方法区中就产…

美债提高上限的后果

* * * 原创&#xff1a;刘教链 * * * 号外&#xff1a;今天在小号“刘教链Pro”发表了一篇《再论以太坊的自限性》&#xff0c;谈了一下对比特币和以太坊自限性问题的再研讨&#xff0c;欢迎关注“刘教链Pro”并阅读。 * * * 隔夜比特币小幅回落至28k下方。昨日在28k上方遭遇了…

在Centos Stream 9上Docker的实操教程(四) - Docker腾讯云远程仓库和本地私有仓库

在Centos Stream 9上Docker的实操教程 - Docker腾讯云远程仓库和本地私有仓库 本地镜像发布到腾讯云注册开通腾讯云初始化个人版服务创建仓库推送拉取镜像 私有仓库结语 本地镜像发布到腾讯云 由于官方的docker hub访问由于网络原因&#xff0c;可能会比较慢&#xff0c;博主推…

0301依赖使用以及配置优先级-基础-springboot2.7.x系列

文章目录 1 依赖方式1.1 spring-boot-starter-parent依赖1.2 spring-boot-dependencies依赖1.3 对比 2 使用方式2.1 SpringbootApplication2.2 高度定制 3 springboot各种配置优先级顺序4 sprinboot配置文件解析顺序结语 1 依赖方式 这里项目以开源的renren和pig为例&#xff…

Meta发布Megabyte AI模型抗衡Transformer

&#x1f680; Meta发布Megabyte AI模型抗衡Transformer&#xff1a;解决后者已知问题、速度提升4成 摘要&#xff1a;Meta团队开发的Megabyte AI模型可以抗衡当前在自然语言处理领域非常流行的Transformer模型&#xff0c; 解决了Transformer模型所面临的训练速度较慢、难以…

【Java 并发编程】深入理解 AQS - AbstractQueuedSynchronizer

深入理解 AQS - AbstractQueuedSynchronizer 1. AQS1.1 什么是 AQS1.2 AQS 具备的特性 2. AQS 原理解析2.1 AQS 原理概述2.1.1 什么是 CLH 锁2.1.2 AQS 中的队列 2.2 AQS 共享资源的方式&#xff1a;独占式和共享式2.2.1 Exclusive&#xff08;独占式&#xff09;2.2.2 Share&a…

用 GPT-4 来面试,简直开挂啊!

公众号关注 “GitHubDaily” 设为 “星标”&#xff0c;每天带你逛 GitHub&#xff01; 众所周知&#xff0c;ChatGPT 凭其超强的文本生成能力&#xff0c;成为了 2023 年最为火爆的 AI 应用之一。 几个月前&#xff0c;GPT-4 发布&#xff0c;又将 ChatGPT 的能力提升到了一个…

redis为何这么快

文章目录 概述基于内存的操作高效的数据存储结构设计高效的数据结构string底层实现SDS字符串长度处理杜绝缓冲区溢出减少内存重新分配的次数空间预分配惰性空间释放 list底层实现压缩列表(zipList)双端链表(linkList) hsah底层实现ziplist字典 set底层实现 zset底层实现ziplist…

“大厂的人一毕业,讲师就多了起来”——但培训行业,早就卷起来了

“大厂的人一毕业&#xff0c;讲师就多了起来”&#xff0c;很多中年产品经理都把去做培训当成一个后备选项&#xff0c;也许&#xff0c;作为十几年前就淌过路的人&#xff0c;可以给你一些信息。 总体来说&#xff0c;今年有个特别的体感&#xff0c;就是产品经理/产品思维/产…

【分布式应用】ELFK集群部署(Filebeat+ELK)Logstash的过滤模块

一、ELFK集群部署&#xff08;FilebeatELK&#xff09; ELFK ES logstashfilebeatkibana 实验环境 服务器类型系统和IP地址需要安装的组件硬件方面node1节点192.168.126.21JDK、elasticsearch-6.7.2、kibana-6.7.22核4Gnode2节点192.168.126.22JDK、elasticsearch-6.7.22核4…

chatgpt赋能python:Python中的快捷键:提高编程效率的利器

Python中的快捷键&#xff1a;提高编程效率的利器 作为一名有10年Python编程经验的工程师&#xff0c;我深刻体会到快捷键的重要性。在日常编程中&#xff0c;快捷键可以大大提高编程效率&#xff0c;让我们更快地完成工作。本文将介绍Python中一些常用的快捷键&#xff0c;并…

【Git】常用命令

Git命令游戏教程网站&#xff1a;https://learngitbranching.js.org/?localezh_CN 日常使用 命令 git push 1.不省略的写法 适合<本地分支名>和<远程分支名>不一样的情况 将本地的dev分支上的代码推送到远程主机名为origin中test的分支上。如果远程的test分支不存…

Go开发学习 | 如何使用日志记录模块包针对日志按天数、按大小分隔文件示例...

欢迎关注「全栈工程师修炼指南」公众号 点击 &#x1f447; 下方卡片 即可关注我哟! 设为「星标⭐」每天带你 基础入门 到 进阶实践 再到 放弃学习&#xff01; “ 花开堪折直须折&#xff0c;莫待无花空折枝。 ” 作者主页&#xff1a;[ https://www.weiyigeek.top ] 博客&…

比较专业的成体系OJ题库和近期整理的比赛题目

比较专业的成体系OJ题库和近期整理的比赛题目&#xff0c;一个优秀的OJ系统是不断剔除和补充题目的完善过程 &#xff0c;不是越多越好&#xff0c;而是符合孩子们学习阶段的需求&#xff0c; 类似的题目有2-3题就好&#xff0c;方便学生举一反三&#xff0c;另外同一题 要求回…

两个offer:一个996,月薪3万;一个885,月薪2万,怎么选?

找工作时&#xff0c;钱和闲&#xff0c;你选哪个&#xff1f; 一位网友拿到了两个offer&#xff0c;一个996&#xff0c;月薪3万&#xff0c;一个885&#xff0c;月薪2万&#xff0c;怎么选&#xff1f; 一部分网友选择885&#xff0c;因为自己是打工人&#xff0c;不是打工奴…

为什么职场中35岁之后很难找到合适的工作?

(点击即可收听) 为什么职场中35岁之后很难找到合适的工作 无论是初入职场还是,职场多年的老司机,都听过一个35岁危机的一个话题 无论是企业还是一些招聘者,针对35,甚至就是30的人,充满了不是这样,就是那样的偏见的理由 每个公司都喜欢有激情,有想法,有干劲的年轻人,无论哪个公司…

大学四年,因为这8个网站,我成为同学眼中的学霸

「作者简介」&#xff1a;CSDN top100、阿里云博客专家、华为云享专家、网络安全领域优质创作者 「推荐专栏」&#xff1a;对网络安全感兴趣的小伙伴可以关注专栏《网络安全入门到精通》 大学期间&#xff0c;几乎每一个教过我的老师都反应&#xff0c;我的学习态度不好&#x…

设计模式之~观察者模式

观察者模式又叫做发布-订阅&#xff08;Publish/Subscribe&#xff09;模式。 观察者模式observer&#xff1a;定义了一种一对多的依赖关系&#xff0c;让多个观察者对象同时监听某个主题对象。这个主题对象在状态发生变化时&#xff0c;会通知所有观察者对象&#xff0c;使他们…

《计算机组成原理》唐朔飞 第8章 CPU的结构和功能 - 学习笔记

写在前面的话&#xff1a;此系列文章为笔者学习计算机组成原理时的个人笔记&#xff0c;分享出来与大家学习交流。使用教材为唐朔飞第3版&#xff0c;笔记目录大体与教材相同。 网课 计算机组成原理&#xff08;哈工大刘宏伟&#xff09;135讲&#xff08;全&#xff09;高清_…