多彩编程 多彩编程MZPH · CODE BLOG
ARTICLE DETAIL

文章详情

深耕前端与后端开发技术的一线实战笔记与踩坑复盘。

Java面试必问的Spring事务,一张图讲清楚

Java面试必问的Spring事务,一张图讲清楚 面试Java后端Spring事务几乎是必问题。可很多人背了传播行为、隔离级别一到实战就懵。其实Spring事务的核心就一张图一个代理两个核心三大陷阱。搞懂这张图面试和开发都稳了。一张图代理 事务管理器 连接想象一下你的Service方法被一个“代理对象”包裹。调用方法时代理先向PlatformTransactionManager申请事务拿到一个数据库连接开启事务然后执行业务代码成功则提交异常则回滚最后归还连接。这张图的关键是事务的边界在代理层不在方法内部。所以方法内部直接调用另一个Transactional方法代理根本不知道事务自然失效——这就是自调用陷阱。两个核心传播行为与隔离级别传播行为解决“多个事务方法互相调用时事务怎么处理”。面试最爱问REQUIRED和REQUIRES_NEW。REQUIRED是默认有事务就加入没有就新建。REQUIRES_NEW是挂起当前事务另起一个新事务新事务提交或回滚不影响外层。还有NESTED基于保存点外层回滚会带走内层内层回滚不影响外层。记住REQUIRES_NEW会开两个连接容易死锁慎用。隔离级别对应数据库的四种读未提交、读已提交、可重复读、串行化。Spring默认用数据库的默认级别MySQL是REPEATABLE READ。面试常问Transactional(isolation Isolation.READ_COMMITTED)能解决幻读吗答案是看数据库实现MySQL的RR通过MVCC间隙锁解决了大部分幻读但RC不行。三大陷阱失效场景必须背熟第一自调用失效。同类中A方法调B方法B有Transactional但A没走代理B的事务不生效。解法注入自己、用AopContext.currentProxy()、或拆到另一个Service。第二异常类型不对。Spring默认只回滚RuntimeException和Error。如果抛出Checked Exception如IOException事务不回滚。解法Transactional(rollbackFor Exception.class)。第三方法非public。Spring AOP基于代理private、protected、包级方法上的Transactional不生效。解法改成public。还有多线程调用事务绑定在ThreadLocal上子线程拿不到数据库引擎不支持MyISAM没有事务事务未开启比如没配EnableTransactionManagement。一张图延伸事务同步与传播再深入一点Spring事务还有TransactionSynchronization可以在提交前后做钩子比如发消息、清缓存。但注意事务提交前发MQ如果提交失败消息已发出数据不一致。解法用事务消息或本地消息表。面试怎么答被问到Spring事务先画那张图代理→事务管理器→连接。然后说传播行为重点讲REQUIRED和REQUIRES_NEW的区别。接着讲失效场景至少说出自调用、异常类型、非public三个。最后补一句实际开发中我倾向在Service层加事务避免大事务必要时用编程式事务TransactionTemplate更可控。总结Spring事务不复杂一张图就能串起来代理控制边界传播决定嵌套隔离控制并发陷阱决定成败。面试时别只背概念结合场景讲比如“下单扣库存用REQUIRED保证一起回滚发短信通知用REQUIRES_NEW避免短信失败导致订单回滚”。这样答面试官会觉得你真用过。记住事务是手段数据一致才是目的。
返回列表