刷到一个说法,建议不要使用@transaction注解。这个说法不太准确,注解可以用,但标注的事务粒度不能太大,这样可能会引起数据库阻塞问题。以下介绍注解事务和编程式事务的两种用法。
关键字:声明式事务,编程式事务,显式事务
文章目录
- 1.反例演示
- 2.事务粒度过大-负面影响
- 3.建议
- (1)编程式事务代码模板
1.反例演示
案例中5,6才是一个原子操作,但是注解标注得太大了,执行外部调用时卡住了,导致事务阻塞会拖垮数据库。
2.事务粒度过大-负面影响
事务粒度过大可能会阻塞数据库并导致性能问题,具体影响如下:
阻塞数据库的主要表现
锁竞争加剧:
大事务持有锁的时间更长
更多数据行/表被锁定
其他事务需要等待这些锁释放
资源占用:
长时间占用数据库连接
未提交事务会占用UNDO日志空间
内存中维护的事务状态数据增多
具体影响
并发性能下降:
其他会话可能被阻塞等待锁释放
系统吞吐量降低
系统资源压力:
内存消耗增加
可能填满数据库的临时表空间或日志空间
风险增加:
死锁概率提高
事务失败时回滚代价高
可能导致连接池耗尽
3.建议
建议把事务粒度控制得更小一些再使用@Transactional注解。或者使用编程式事务,准确处理需要搞成事务的步骤。
(1)编程式事务代码模板
以下是编程式事务代码模板参考:
@Autowiredprivate TransactionTemplate transactionTemplate;transactionTemplate.execute((transactionStatus)->{try {System.out.println("业务逻辑");} catch (Exception e) {transactionStatus.setRollbackOnly();// 标记为回滚log.error("服务异常");}return transactionStatus;});