关于Mysql事务,你必须知道的几个知识点!
Transaction事务
上期我们讲到了jpa的常用操作,查询、更新、删除等,但是如果在操作数据库事务时发生异常,数据会回滚吗?下面我们来看个例子
UserController新增如下代码:
@GetMapping("save1")
public String save1(){
User user = new User();
user.setDptId(1L);
user.setName("a");
user.setAge(18L);
user.setEmail("a@a.com");
user.setHeadImg("headImg1");
this.userJpa.save(user);
//模拟发生了异常
System.out.println(1/0);
return "ok";
}
使用postman请求
localhost:8080/user/save1
执行之后可以看到java后台报错了,postman前台也报出来错误,但是数据却保存进去了,数据新增了一条记录

说明即使发生了异常,数据还是会保存进去数据库,那应该怎么办呢?试试在save1方法上加一个@Transactional的注解。
我们再执行一次。发现错误也报出来了,但是数据库并没有将新数据插入进去,最新的还是上一次的id为7的记录,那么 Transactional注解是干嘛的呢?
@Transactional是声明式事务管理编程中使用的注解
如下是该注解的属性,我们需要关注重点关注的是rollback-for和propagation两个属性。
| 属性名 | 说明 |
|---|---|
| name | 当在配置文件中有多个 TransactionManager , 可以用该属性指定选择哪个事务管理器。 |
| propagation | 事务的传播行为,默认值为 REQUIRED。 |
| isolation | 事务的隔离度,默认值采用 DEFAULT。 |
| timeout | 事务的超时时间,默认值为-1。如果超过该时间限制但事务还没有完成,则自动回滚事务。 |
| read-only | 指定事务是否为只读事务,默认值为 false;为了忽略那些不需要事务的方法,比如读取数据,可以设置 read-only 为 true。 |
| rollback-for | 用于指定能够触发事务回滚的异常类型,如果有多个异常类型需要指定,各类型之间可以通过逗号分隔。 |
| no-rollback- for | 抛出 no-rollback-for 指定的异常类型,不回滚事务。 |
rollback-for:只有执行的异常才回滚。但是我们刚刚的程序并没有指定异常,那是默认的是遇到什么样的异常会回滚呢?
- 将UserController中的代码稍作修改,手动
throw new Exception("test"),再执行下postman,发现事务提交了,并没有回滚。 - 接着我们将注解修改为
@Transactional(rollbackFor = Exception.class),再执行postman,事务却回滚了,并没有提交,什么原因? - spring的
@Transactional注解可以很方便的开启事务,但是默认只在遇到运行时异常和Error时才会回滚,非运行时异常不回滚,即Exception的子类中,除了RuntimeException及其子类,其他的类默认不回滚。 - 而rollbackFor属性可以解决这个问题,
rollbackFor = Exception.class表示Exception及其子类的异常都会触发回滚,同时不影响Error的回滚。
propagation:这个用得最广的需求就是业务出错了,但是日志必须提交到数据库。怎么处理?来看下面的代码。
新增LogService类
@Service
public class LogService {
@Resource
private UserJpa userJpa;
@Transactional(propagation = Propagation.REQUIRES_NEW)
public void saveLog(){
User user = new User();
user.setDptId(1L);
user.setName("log");
user.setAge(18L);
user.setEmail("log@log.com");
user.setHeadImg("log");
this.userJpa.save(user);
System.out.println("log");
}
}
新增UserService类:
@Service
public class UserService {
@Resource
private UserJpa userJpa;
@Resource
private LogService logService;
@Transactional(rollbackFor = Exception.class)
public void saveBiz() throws Exception {
System.out.println("save2");
User user = new User();
user.setDptId(1L);
user.setName("biz");
user.setAge(18L);
user.setEmail("biz@biz.com");
user.setHeadImg("biz");
this.userJpa.save(user);
//模拟保存日志
this.logService.saveLog();
//模拟发生了异常
throw new Exception("test1");
}
}
UserController新增代码
@GetMapping("save2")
public String save2() throws Exception {
//模拟业务操作
this.userService.saveBiz();
return "ok";
}
postman执行下,是不是只有log的那条记录插入进去了?biz的没有插入进去。
注意:同一个业务类里面 , 即使声明为
Propagation.REQUIRES_NEW也不会新启一个事务。必须调用另一个类的Propagation.REQUIRES_NEW方法才行。所以样例中是使用UserService里面调用另一个类LogService中的saveLog的方法。
更多原创阅读:点击
关于Mysql事务,你必须知道的几个知识点!的更多相关文章
- Mysql事务探索及其在Django中的实践(二)
继上一篇<Mysql事务探索及其在Django中的实践(一)>交代完问题的背景和Mysql事务基础后,这一篇主要想介绍一下事务在Django中的使用以及实际应用给我们带来的效率提升. 首先 ...
- MySQL 事务
MySQL 事务主要用于处理操作量大,复杂度高的数据.比如说,在人员管理系统中,你删除一个人员,你即需要删除人员的基本资料,也要删除和该人员相关的信息,如信箱,文章等等,这样,这些数据库操作语句就构成 ...
- mysql事务和并发控制
谈到事务,首先想到的问题是并发控制.比如两个用户同时操作数据库里面的一张表,一个正在读数据,一个正在删除数据,那么读数据的读出的结果究竟是多少?并发可以提高系统的性能,让多个用户同时操作一份数据,但为 ...
- MySQL事务学习-->隔离级别
MySQL事务学习-->隔离级别 6 事务的隔离级别 设置的目的 在数据库操作中,为了有效保证并发读取数据的正确性,提出的事务隔离级别. 数据库是要被广大客户所共享访问的,那么在数据库操作过程中 ...
- mysql 事务是专门用来管理insert,update,delete语句的,和select语句一点不相干
1.mysql 事务是专门用来管理insert,update,delete语句的,和select语句一点不相干 2.一般来说,事务是必须满足4个条件(ACID): Atomicity(原子性).Con ...
- php mysql事务
这里记录一下php操作mysql事务的一些知识 要知道,MySQL默认的行为是在每条SQL语句执行后执行一个COMMIT语句,从而有效的将每条语句独立为一个事务.但是,在使用事务时,是需要执行多条sq ...
- mysql事务问题
mysql事务: 若mysql 开启事务后START TRANSACTION ,不显示提交commit,则默认自动回滚,而不是默认自动提交.
- MYSQL事务和锁
mysql事务(一)—转载 2012年12月20日 ⁄ Mysql数据库, 技术交流 ⁄ 暂无评论 一. 什么是事务 事务就是一段sql 语句的批处理,但是这个批处理是一个atom(原子) ,不可分割 ...
- MySQL事务内幕与ACID
MySQL的事务实现严格遵循ACID特性,即原子性(atomicity),一致性(consistency),隔离性(isolation),持久性(durability).为了避免一上来就陷入对ACID ...
- 数据库 Mysql事务详解
Mysql事务 mysql的事务默认是自动提交的,也就是你提交一个query,他就直接执行!我们可以通过 禁止自动提交 开启自动提交 //mysql事务 #include <stdio.h> ...
随机推荐
- 墙裂推荐一波mysql学习资源
在日常工作与学习中,无论是开发.运维.测试,还是架构师,数据库是一门必不可少的"必修课", 也是必备的涨薪神器.在互联网公司中,开源数据库用得比较多的当属 MySQL 了. 但my ...
- DataGear 变更部署数据库为SQL Server填坑指南(含转写后的SQL server代码及SQL server配置文件)
1. 引言 2. 配置数据库链接 3. 引入数据库驱动 4. 手动初始化数据库 5. 改写SQL 6. 其他 7. 参考 1. 引言 DataGear默认使用Derby数据库作为系统的元数据库,至于待 ...
- 前端Node的实用方法
Node 一.什么是Node Node是以基于Chrome V8引擎的JavaScript运行环境,使用了一个事件驱动.非阻塞式I/O模型(I/O是 input/output的缩写,即输入输出端口,在 ...
- [刷题] 77 Combinations
要求 给出两个整数n和k,在n个数字中选出k个数字的所有组合 示例 n=4 , k=2 [ [ 1, 2 ] , [ 1, 3 ] , [ 1, 4 ] , [ 2, 3 ] , [ 2, 4 ] , ...
- 搞清楚 硬件环境 os环境 网络环境 搞清楚测试工具 测试步骤 自己搭测试环境 自测
1,遇事的第一反应要从变化情绪转变为做出判断.判断什么?判断这一件事对自己是否重要,是否关乎我的个人利益,是否影响我的人际关系等等等等.如果答案都是否,那就没必要着急忙慌了.如果答案是是 冷静,其实是 ...
- CentOS7配置kdump
CentOS7配置kdump 简单生活,简单爱 2020-10-27 16:29:56 56 收藏 1 分类专栏: Linux实际开发总结 版权 文章目录 1.kdump简介 2.配置kdump ...
- Chm文件阅读软件测试需求
转发: .Chm文件阅读软件测试需求 . xchm问题太多就不考虑了: kchm是问题少一些 windows打开是乱码就不去考虑 必须在windows打开正常的再在龙芯上打开 1windows打开是乱 ...
- Zabbix agent端 配置
Zabbix agent端 配置 agent端环境 zabbix-client:RHEL8 IP:192.168.121.11 一.安装 Zabbix 源 [root@zabbix-client ~] ...
- HC-05底层驱动
INT8U BT_INIT(const char * pNAME, INT32U BAUD, INT8U ROLE, INT32U PSWD) { INT8U OS_ERR = OS_ERR_NONE ...
- 为鸿蒙OS说两句公道话(我对鸿蒙OS的一些看法)
为鸿蒙说两句公道话 今天看了鸿蒙系统的评测,看完后我感觉很欣慰,为什么这么说 ? 不是很多人吐槽鸿蒙是 Android 套壳吗 ?或者叫鸿蒙 UI 吗?说鸿蒙没有自己的核心技术.看了鸿蒙系统的设计,底 ...