当前位置: 首页 > news >正文

Transaction rolled back because it has been marked as rollback-only问题解决

1、背景

在我们的日常开发中,经常会存在在一个Service层中调用另外一个Service层的方法。比如:我们有一个TaskService,里面有一个execTask方法,且这个方法存在事物,这个方法在执行完之后,需要调用LogService的insertLog方法记录一条日志,这个方法上也有事物,不管日志记录成功还是失败,都不能影响execTask方法的执行。因此我们很容易写出如下代码。

@Transactional
public void execTaskV1(){log.info("开始执行任务");try {logService.insertLogV1();} catch (Exception e) {log.error("添加日志出现错误");}log.info("完成任务执行");
}

思考: 上方的代码,如果insertLogV1跑出了异常,execTaskV1方法的事物可以正常提交吗?

2、异常是如何实现出现的

1、了解Spring事物的传播属性

传播行为描述应用场景行为特点
Propagation.REQUIRED如果当前存在事务,则加入该事务;如果当前没有事务,则启动一个新的事务。大多数场景,如多个方法需要在同一个事务中完成。- 如果当前事务存在,方法执行在当前事务上下文中。
- 如果当前事务不存在,创建新事务。
Propagation.SUPPORTS如果当前存在事务,则加入该事务;如果当前没有事务,则以非事务方式执行。对事务支持没有强制要求的场景,如只读查询。- 如果当前事务存在,方法执行在当前事务上下文中。
- 如果当前事务不存在,以非事务方式执行。
Propagation.MANDATORY如果当前存在事务,则加入该事务;如果当前没有事务,则抛出异常。必须在一个已存在的事务中执行的场景。- 必须在已有事务中执行,否则抛出 IllegalTransactionStateException
Propagation.REQUIRES_NEW每次调用该方法时都会启动一个新的事务。当前事务(如果有)会被挂起。需要独立事务的场景,如日志记录或独立的业务操作。- 总是创建新事务。
- 当前事务(如果有)会被挂起,直到新事务完成。
Propagation.NOT_SUPPORTED总是以非事务方式执行,并且暂停当前事务(如果有)。不需要事务的场景,如简单的查询操作。- 总是以非事务方式执行。
- 暂停当前事务(如果有)。
Propagation.NEVER总是以非事务方式执行,如果当前存在事务,则抛出异常。严格禁止事务的场景,如某些非事务性操作。- 必须在非事务上下文中执行,否则抛出 TransactionException
Propagation.NESTED如果当前存在事务,则在嵌套事务内执行;如果当前没有事务,则启动一个新的事务。需要嵌套事务的场景,如复杂的业务流程中需要独立的回滚点。- 如果当前事务存在,创建一个嵌套事务(依赖于数据库支持)。
- 如果当前事务不存在,创建新事务。

2、模拟异常出现

Transaction rolled back because it has been marked as rollback-only 这个异常在上述的案例中是如何实现的呢?
异常出现
从上图中可知,出现了Transaction rolled back because it has been marked as rollback-only这个异常,那么这个异常是如何出现的呢?

其实这个是和Spring事物的传播属性Propagation有关。

默认情况下@Transaction的传播属性是Propagation.REQUIRED, 即如果当前存在事务,则加入该事务;如果当前没有事务,则启动一个新的事务。 在我们的例子中,事物的隔离级别都是Propagation.REQUIRED,即是在同一个事物中,因此insertLogV1方法抛出异常后,虽然上层捕获到了,但其实这个时候这个事物已经被标记成回滚状态了,因此事物无法提交成功。

如何解决: 只需要修改insertLogV1事物的传播属性为Propagation.REQUIRES_NEW即可。

3、完整代码

完整代码-https://gitee.com/huan1993/spring-cloud-parent/tree/master/springboot/springboot-transaction-v1

http://www.lryc.cn/news/532529.html

相关文章:

  • 深入浅出 DeepSeek V2 高效的MoE语言模型
  • 读书笔记--分布式架构的异步化和缓存技术原理及应用场景
  • 售后板子HDMI无输出分析
  • python3处理表格常用操作
  • AUX接口(Auxiliary Port)
  • 计算机毕业设计Python+Vue.js游戏推荐系统 Steam游戏推荐系统 Django Flask 游 戏可视化 游戏数据分析 游戏大数据 爬虫
  • 【梦想终会实现】Linux驱动学习5
  • Spring 核心技术解析【纯干货版】-Spring 数据访问模块 Spring-Jdbc
  • Docker 安装详细教程(适用于CentOS 7 系统)
  • Mac本地部署DeekSeek-R1下载太慢怎么办?
  • 《Angular之image loading 404》
  • JavaScript前后端交互-AJAX/fetch
  • ZooKeeper单节点详细部署流程
  • 流浪地球发动机启动问题解析与实现
  • Java 注解使用教程
  • 网络安全学习
  • 4 前端前置技术(上):AJAX技术、Axios技术(前端发送请求)
  • 2022年全国职业院校技能大赛网络系统管理赛项模块A:网络构建(样题3)-网络部分解析-附详细代码
  • ASP.NET Core中间件的概念及基本使用
  • 每日Attention学习22——Inverted Residual RWKV
  • 使用jmeter进行压力测试
  • LQB(0)-python-基础知识
  • 每日Attention学习18——Grouped Attention Gate
  • QT 窗口A覆盖窗口B时,窗口B接受不到鼠标事件
  • Unity安装教学与相关问题
  • [Python人工智能] 四十九.PyTorch入门 (4)利用基础模块构建神经网络并实现分类预测
  • 实现一个 LRU 风格的缓存类
  • 【蓝桥杯嵌入式】4_key:单击+长按+双击
  • 深入理解 C# 与.NET 框架
  • 10. 神经网络(二.多层神经网络模型)