Spring 事务中 REQUIRED、REQUIRES_NEW、NESTED 在异常传播、连接占用和回滚边界上的语义差异是什么?
进阶版来源:meituan高级工程师嵌套事务与保存点数据库连接占用事务回滚边界Spring事务传播行为
草稿
答案解析
这三个传播行为主要区别在于:是否共用外层事务、是否占用新连接,以及回滚边界是不是独立的。
REQUIRED 是默认传播行为。当前如果已经有事务,就加入外层事务;如果没有事务,就新建一个事务。也就是说内外层用的是同一个物理事务,通常也是同一个数据库连接。
在异常传播上,如果内层 REQUIRED 方法抛出运行时异常,即使外层把异常 catch 住了,内层事务也可能已经把整个事务标记成 rollback only,最终外层提交时会回滚,并且可能抛 UnexpectedRollbackException。所以它的回滚边界不是内层方法自己,而是整个外层事务。
REQUIRES NEW 表示不管当前有没有事务,都会新开一个事务。如果外层有事务,会先把外层事务挂起,然后开启一个新的事务执行内层逻辑。它通常会额外占用一个数据库连接,所以在高并发场景下要注意连接池压力,比如外层事务还占着连接,内层又要申请新连接。
在回滚边界上,REQUIRES NEW 是独立事务。内层回滚不会直接导致外层回滚,内层提交了也不会因为外层后续回滚而被回滚。比如写操作日志、审计记录,经常会用
登录后查看完整内容
