Spring事务粒度优化与传播机制
在Spring事务中,我们通常会为了控制事务粒度,会把它进行拆分,为了避免大事务执行太久,占用资源太多,导致资源利用率低的问题。
我们曾经就遇到老系统因为大事务,把服务打死了。
问题出在一个大事务中有一个Excel文件解析的操作,有用户上传的某个文件,有1百多万个空行数据。
因为,这个事务一致不能结束,直接导致系统崩溃。
但是要拆分事务,是一个麻烦的事情,要考虑事务传播机制。
无事务
我相信很多朋友都遇到过事务不生效的情况,最常见的就是下面这种情况:
public class ServiceA
{public void methodA(){methodB();}@Transactionalpublic void methodB(){}
}
我相信有朋友已经开始笑了。
不要笑,相信很多朋友本能会犯这个错误,因为这种方式最简单。
上面的示例,事务是不会生效的,因为methodB直接被调用,是因为没有通过代理执行。
问题很简单,但是如何快速简单的解决问题呢?
有事务不回滚
有对事务传播机制比较熟悉的朋友,可能要提出下面的方案了:
public class ServiceA
{@Transactional(propagation = Propagation.SUPPORTS)public void methodA(){methodB();}@Transactionalpublic void methodB(){}
}
既然,没有事务,我加上事务不加完了,SUPPORTS机制,没有事务就不创建,有事务就在事务中执行,
然后,methodB默认事务传播机制REQUIRED,没有就会创建事务。
所以,methodA没有事务,methodB直接创建事务执行,真是天才的想法啊。
问题是,实际情况真是这样吗?
比较遗憾,不是。
会有事务吗?会methodA会生成事务。
methodB会生成新的事务吗?不会,因为methodA已经有事务了。
会回滚吗?不会!有事务,但是不会回滚。
和不加@Transactional(propagation = Propagation.SUPPORTS)相比,只是会创建事务了。
为什么会出现这样的情况呢?
开的的时候,我以为是SUPPORTS没有回滚点的造成。
但是,我发现还是存在其他没有回滚点的事务传播机制,并且能够回滚
可以添加下面的代码打印看一下:
System.out.println(TransactionAspectSupport.currentTransactionStatus().hasSavepoint());
还有什么办法吗?
换个姿势调用
很多时候,我们没有得到正确的结果,可能是姿势不对,我们换个姿势试一试。
既然,直接调用不行,那我们通过ApplicationContext来调用,是否就可以触发事务了呢?
@Component
public class ApplicationContextHolder implements ApplicationContextAware {private ApplicationContext applicationContext;@Overridepublic void setApplicationContext(ApplicationContext applicationContext) throws BeansException {this.applicationContext = applicationContext;}public ApplicationContext getApplicationContext(){return this.applicationContext;}public <T> T getService(Class<T> clazz){return applicationContext.getBean(clazz);}
}
public class ServiceA
{@Resourceprivate ApplicationContextHolder applicationContextHolder;public void methodA(){ServiceA service = applicationContextHolder.getService(this.getClass());service.methodB();}@Transactionalpublic void methodB(){}
}
答案是:不行,因为根本没有创建事务
多种姿势结合
public class ServiceA
{@Resourceprivate ApplicationContextHolder applicationContextHolder;@Transactional(propagation = Propagation.SUPPORTS)public void methodA(){ServiceA service = applicationContextHolder.getService(this.getClass());service.methodB();}@Transactionalpublic void methodB(){}
}
这样可以吗?
答案是:可以
事务是methodA的事务,并且也回滚了。
这的确解决了我们的问题,但是也违背了我们的初衷:将事务粒度变小。
因为,绕了一大圈,发现还是相当于methodA上的事务了。
那有没有什么更靠谱的解决方案呢?
大概可以试一试:NESTED和REQUIRES_NEW事务吧
public class ServiceA
{@Transactional(readOnly = true)public void methodA(){ServiceA service = applicationContextHolder.getService(this.getClass());service.methodB();}@Transactional(propagation = Propagation.NESTED)// @Transactional(propagation = Propagation.REQUIRES_NEW)public void methodB(){}
}
可以回滚,但是:
- NESTED、REQUIRES_NEW都没有回滚点
- NESTED、REQUIRES_NEW都使用的是methodA的事务。
感觉和直接调用没有太多的区别
@Service
public class ServiceA
{@Resourceprivate ServiceB serviceB;public void methodA(){serviceB.methodB();}
}@Service
public class ServiceB
{ // @Transactional(propagation = Propagation.NESTED)@Transactional(propagation = Propagation.REQUIRES_NEW)public void methodB(){}
}
上面的方式,也可以回滚:
- 使用NESTED有回滚点,使用methodA的事务
- 使用REQUIRES_NEW,会创建新事务
事务传播机制
相关文章:
Spring事务粒度优化与传播机制
在Spring事务中,我们通常会为了控制事务粒度,会把它进行拆分,为了避免大事务执行太久,占用资源太多,导致资源利用率低的问题。 我们曾经就遇到老系统因为大事务,把服务打死了。 问题出在一个大事务中有一…...
MySQL 基于成本的优化
其实在MySQL中⼀条查询语句的执⾏成本是由下边这两个⽅⾯组成的: I/O成本 我们的表经常使⽤的MyISAM、InnoDB存储引擎都是将数据和索引都存储到磁盘上的,当我们想查询表中的记录时,需要先把数据或者索引加载到内存中 然后再操作。这个从磁盘…...
【maven】【IDEA】idea中使用maven编译项目,报错java: 错误: 找不到符号 【2】
idea中使用maven编译项目,报错java: 错误: 找不到符号 错误状况展示: 如果报这种错,是因为项目中真的找不到报错的方法或者枚举 字段之类的,但实际是 : 点击 File Path...
AIGC,ChatGPT AI绘画 Midjourney 注册流程详细步骤
AI 绘画,Midjourney完成高清图片绘制,轻松掌握AI工具。 前期准备: ① 一个能使用的谷歌账号 ② 可以访问外网 Midjourney注册 1.进入midjourney官网https://www.midjourney.com 点击左下角”Join the Beta”,就可以注册,第一次使用的小伙伴会弹出提示,只需要点击Acc…...
万字解析设计模式之模板方法与解释器模式
一、模板方法模式 1.1概述 定义一个操作中算法的框架,而将一些步骤延迟到子类中,模板方法使得子类可以不改变一个算法的结构即可重定义该算法的某些特定步骤。 例如,去银行办理业务一般要经过以下4个流程:取号、排队、办理具体业…...
apipost接口200状态码,浏览器控制台500状态码
后端 url 登录login方法 login(){this.$refs.loginForm.validate(async valid > {if (!valid) return// 由于data属性是一个json对象,需要进行解构赋值{data:result},进行状态码判断const {data: result} await this.$http.post(/api/doLogin,this.…...
Instant Web API .Net Core Crack
Instant Web API .Net Core 是立即构建即时数据库 Web API,无需编码。在几分钟内生成您的 Web API,以更快地构建应用程序。使用 VS 2022 和 Entity Framework Core 为任何 MS SQL 数据库生成 Web API。 新功能 - 使用 Visual Studio 2022 为 PostgreSQL …...
vue项目使用easyplayer播放m3u8直播推流
官网 青犀视频 代码库 / 示例 / demo EasyPlayer 示例效果: 项目背景如图 后端给了m3u8的直播地址 协议是 hls / flv 市面上很多第三方热门播放库都可以完成该多屏播放方式 如Video.js 问题在于 分多屏时 会存在性能问题 并且关闭播放器后 即便删除Dom或调用停…...
Python报错:AttributeError(类属性、实例属性)
Python报错:AttributeError(类属性、实例属性) Python报错:AttributeError 这个错误就是说python找不到对应的对象的属性,百度后才发现竟然是初始化类的时候函数名写错了 __init__应该有2条下划线,如果只有…...
vue+springboot读取git的markdown文件并展示
前言 最近,在研究一个如何将我们git项目的MARKDOWN文档获取到,并且可以展示到界面通过检索查到,于是经过几天的摸索,成功的研究了出来 本次前端vue使用的是Markdown-it Markdown-it 是一个用于解析和渲染 Markdown 标记语言的 …...
多功能PHP图床源码:Lsky Pro开源版v2.1 – 最新兰空图床
Lsky Pro是一款功能丰富的在线图片上传和管理工具,即兰空图床。它不仅可以作为个人云相册,还可以用作写作贴图库。 该程序的初始版本于2017年10月由ThinkPHP 5开发,经过多个版本的迭代,于2022年3月发布了全新的2.0版本。 Lsky Pro…...
Hive内置表生成函数
Hive内置UDTF 1、UDF、UDAF、UDTF简介2、Hive内置UDTF 1、UDF、UDAF、UDTF简介 在Hive中,所有的运算符和用户定义函数,包括用户定义的和内置的,统称为UDF(User-Defined Functions)。如下图所示: UDF官方文档…...
电源控制系统架构(PCSA)之电源控制框架概览
目录 6 电源控制框架 6.1 电源控制框架概述 6.1.1 电源控制框架低功耗接口 6.1.2 电源控制框架基础设施组件 6 电源控制框架 电源控制框架是标准基础设施组件、接口和相关方法的集合,可用于构建SoC电源管理所需的基础设施。 本章介绍框架的主要组件和低功耗接…...
Sentinel 监控数据持久化(mysql)
Sentinel 实时监控仅存储 5 分钟以内的数据,如果需要持久化,需要通过调用实时监控接口来定制,即自行扩展实现 MetricsRepository 接口(修改 控制台源码)。 本文通过使用Mysql持久化监控数据。 1.构建存储表(…...
基于法医调查算法优化概率神经网络PNN的分类预测 - 附代码
基于法医调查算法优化概率神经网络PNN的分类预测 - 附代码 文章目录 基于法医调查算法优化概率神经网络PNN的分类预测 - 附代码1.PNN网络概述2.变压器故障诊街系统相关背景2.1 模型建立 3.基于法医调查优化的PNN网络5.测试结果6.参考文献7.Matlab代码 摘要:针对PNN神…...
canvas高级动画001:文字瀑布流
canvas实例应用100 专栏提供canvas的基础知识,高级动画,相关应用扩展等信息。 canvas作为html的一部分,是图像图标地图可视化的一个重要的基础,学好了canvas,在其他的一些应用上将会起到非常重要的帮助。 文章目录 示例…...
抽象类, 接口, Object类 ---java
目录 一. 抽象类 1.1 抽象类概念 1.2 抽象类语法 1.3 抽象类特性 1.4 抽象类的作用 二. 接口 2.1 接口的概念 2.2 语法规则 2.3 接口的使用 2.4 接口间的继承 2.5 抽象类和接口的区别 三. Object类 3.1 toString() 方法 3.2 对象比较equals()方法 3.3 hash…...
SOAP 协议和 HTTP 协议:深入解读与对比
SOAP 和 HTTP 协议 SOAP 协议 SOAP( Simple Object Access Protocol)是一种用于在节点之间交换结构化数据的网络协议。它使用XML格式来传输消息。它在 HTML 和 SMTP 等应用层协议的基础上进行标记和传输。SOAP 允许进程在整个平台、语言和操作系统中进…...
Unity发布IOS后,使用xcode打包报错:MapFileParser.sh:Permissiondenied
1.错误提示 使用xcode打包错误提示:/Users/mymac/Desktop/myproject/MapFileParser.sh: Permission denied 2.解决方案 打开控制台输入:chmod ax /Users/mymac/Desktop/myproject/MapFileParser.sh。按回车键执行,然后重新使用xcode发布程序…...
2021年12月 Scratch(三级)真题解析#中国电子学会#全国青少年软件编程等级考试
Scratch等级考试(1~4级)全部真题・点这里 一、单选题(共25题,每题2分,共50分) 第1题 执行下列程序,屏幕上可以看到几只小猫? A:1 B:3 C:4 D:0 答案:B 第2题 下列程序哪个可以实现:按下空格键,播放完音乐后说“你好!”2秒? A: B: C:...
浏览器访问 AWS ECS 上部署的 Docker 容器(监听 80 端口)
✅ 一、ECS 服务配置 Dockerfile 确保监听 80 端口 EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]或 EXPOSE 80 CMD ["python3", "-m", "http.server", "80"]任务定义(Task Definition&…...
Linux 文件类型,目录与路径,文件与目录管理
文件类型 后面的字符表示文件类型标志 普通文件:-(纯文本文件,二进制文件,数据格式文件) 如文本文件、图片、程序文件等。 目录文件:d(directory) 用来存放其他文件或子目录。 设备…...
Admin.Net中的消息通信SignalR解释
定义集线器接口 IOnlineUserHub public interface IOnlineUserHub {/// 在线用户列表Task OnlineUserList(OnlineUserList context);/// 强制下线Task ForceOffline(object context);/// 发布站内消息Task PublicNotice(SysNotice context);/// 接收消息Task ReceiveMessage(…...
Linux云原生安全:零信任架构与机密计算
Linux云原生安全:零信任架构与机密计算 构建坚不可摧的云原生防御体系 引言:云原生安全的范式革命 随着云原生技术的普及,安全边界正在从传统的网络边界向工作负载内部转移。Gartner预测,到2025年,零信任架构将成为超…...
【决胜公务员考试】求职OMG——见面课测验1
2025最新版!!!6.8截至答题,大家注意呀! 博主码字不易点个关注吧,祝期末顺利~~ 1.单选题(2分) 下列说法错误的是:( B ) A.选调生属于公务员系统 B.公务员属于事业编 C.选调生有基层锻炼的要求 D…...
大数据学习(132)-HIve数据分析
🍋🍋大数据学习🍋🍋 🔥系列专栏: 👑哲学语录: 用力所能及,改变世界。 💖如果觉得博主的文章还不错的话,请点赞👍收藏⭐️留言Ǵ…...
「全栈技术解析」推客小程序系统开发:从架构设计到裂变增长的完整解决方案
在移动互联网营销竞争白热化的当下,推客小程序系统凭借其裂变传播、精准营销等特性,成为企业抢占市场的利器。本文将深度解析推客小程序系统开发的核心技术与实现路径,助力开发者打造具有市场竞争力的营销工具。 一、系统核心功能架构&…...
论文阅读:Matting by Generation
今天介绍一篇关于 matting 抠图的文章,抠图也算是计算机视觉里面非常经典的一个任务了。从早期的经典算法到如今的深度学习算法,已经有很多的工作和这个任务相关。这两年 diffusion 模型很火,大家又开始用 diffusion 模型做各种 CV 任务了&am…...
企业大模型服务合规指南:深度解析备案与登记制度
伴随AI技术的爆炸式发展,尤其是大模型(LLM)在各行各业的深度应用和整合,企业利用AI技术提升效率、创新服务的步伐不断加快。无论是像DeepSeek这样的前沿技术提供者,还是积极拥抱AI转型的传统企业,在面向公众…...
高防服务器价格高原因分析
高防服务器的价格较高,主要是由于其特殊的防御机制、硬件配置、运营维护等多方面的综合成本。以下从技术、资源和服务三个维度详细解析高防服务器昂贵的原因: 一、硬件与技术投入 大带宽需求 DDoS攻击通过占用大量带宽资源瘫痪目标服务器,因此…...
