@Transactional注解能否与saveAndFlush配合使用?附代码场景疑问
关于@Transactional与saveAndFlush的配合及事务内数据可见性问题
好问题!我来帮你把这两个关键点拆解清楚:
1. @Transactional完全可以和saveAndFlush配合使用
saveAndFlush的核心作用是立即将实体的变更同步到数据库(触发对应的INSERT/UPDATE SQL执行),但它并不会提交事务——事务的提交逻辑依然由@Transactional注解控制:只有当被注解的方法(这里是saveAndGenerateResult)执行完成且没有抛出异常时,Spring才会自动提交事务。
在事务范围内调用saveAndFlush,既可以保证数据及时写入数据库(避免内存中缓存的变更累积),又能享受事务的原子性保障:如果后续操作抛出异常,所有已经flush的变更都会被回滚。
2. callAnAggregatedFunction一定能获取到刚保存的数据
你的场景里,callAnAggregatedFunction和saveDataInTableA、saveDataInTableB处于同一个事务上下文中,所以完全可以读取到刚通过saveAndFlush写入表A、表B的数据,原因有两个:
saveAndFlush已经把数据刷入数据库,虽然事务还未提交,但同一个事务内的数据库操作共享同一个连接,且能看到当前事务内的所有未提交变更(这是数据库事务隔离级别中“读已提交”及以上的默认行为,而Spring默认的事务隔离级别就是读已提交)。- 你的
callAnAggregatedFunction是同一个类中的方法,会被Spring的事务代理包含在当前事务里,不会开启新的事务(除非你额外配置了事务传播行为)。
额外注意事项
- 如果
callAnAggregatedFunction是调用外部独立服务,或者配置了REQUIRES_NEW这类事务传播行为,那它会脱离当前事务,此时就无法读取到未提交的数据(因为数据库隔离级别会阻止其他事务读取未提交的变更)。但你的代码里不存在这种情况。 - 不管是用JPA Repository查询还是原生SQL查询,只要是在同一个事务内,都能看到这些flush后的变更。
内容的提问来源于stack exchange,提问作者Reaz Masud
相关产品推荐
相关产品推荐

