Spring 原理与源码分析
事务管理终极源码追踪(2025 年最新 Spring 6.1.x + Spring Boot 3.3 完整版)
这才是真正决定你能不能进银行总行、支付宝、蚂蚁金服、运营商核心交易系统的灵魂问题。
下面直接给你 Spring 事务从 @Transactional 到最终 commit/rollback 的完整 13 步闭环源码链路,每一行代码都带断点位置 + 真实银行面试题答案,看完直接吊打 99.999% 的候选人。
事务全景时序图(2025 版必背)
1. 启动 → 注册 InfrastructureAdvisorAutoProxyCreator
2. @EnableTransactionManagement → 导入 TransactionManagementConfigurationSelector
3. 注册 AnnotationTransactionAttributeSource + TransactionInterceptor
4. Bean 初始化后 → AOP 代理生成(TransactionInterceptor 被织入)
5. 调用 @Transactional 方法 → TransactionInterceptor.invoke()
6. TransactionAspectSupport.invokeWithinTransaction()
7. createTransactionIfNecessary() → 获取 ConnectionHolder
8. DataSourceTransactionManager.doBegin()
9. Connection.setAutoCommit(false) + Isolation + Timeout
10. 方法正常返回 → completeTransactionAfterReturning() → commit
11. 方法抛异常 → cleanupTransactionInfo() → rollback
12. DataSourceTransactionManager.doCommit()/doRollback()
13. Connection.commit()/rollback() + 恢复 autoCommit
核心类关系图(2025 版)
@EnableTransactionManagement
↓
ProxyTransactionManagementConfiguration
↓
注册两个核心 Bean:
├─ AnnotationTransactionAttributeSource ← 解析 @Transactional 属性
└─ TransactionInterceptor ← 真正的事务拦截器(Advisor)
TransactionInterceptor → TransactionAspectSupport
↓
AbstractPlatformTransactionManager(抽象父类)
↓
└── DataSourceTransactionManager(最常用)
↓
└── DataSourceTransactionManager(99.9% 项目用的都是它)
13 步完整源码追踪(可直接在 IDEA 打断点)
| 步骤 | 类名 + 方法 | 关键代码行 | 作用 |
|---|---|---|---|
| 1 | @EnableTransactionManagement | – | 导入配置类 |
| 2 | ProxyTransactionManagementConfiguration.registerTransactionInterceptor() | 第 78 行 | 注册 TransactionInterceptor |
| 3 | TransactionInterceptor.invoke(MethodInvocation) | 第 66 行 | AOP 切面入口 |
| 4 | TransactionAspectSupport.invokeWithinTransaction() | 第 132 行 | 真正干活的方法 |
| 5 | createTransactionIfNecessary() | 第 188 行 | 判断是否需要开启事务 |
| 6 | TransactionAspectSupport.determineTransactionManager() | – | 获取 TransactionManager |
| 7 | DataSourceTransactionManager.doGetTransaction() | 第 298 行 | 创建 TransactionObject |
| 8 | DataSourceTransactionManager.doBegin() | 第 346 行 | 真正开启事务!!! |
| 9 | Connection.setAutoCommit(false) | JDBC 原生 | 关闭自动提交 |
| 10 | completeTransactionAfterReturning() | 第 245 行 | 正常返回 → commit |
| 11 | DataSourceTransactionManager.doCommit() | 第 456 行 | 执行 commit |
| 12 | cleanupTransactionInfo() → doRollbackOnCommitException() | – | 异常 → rollback |
| 13 | DataSourceTransactionManager.doRollback() | 第 489 行 | 执行 rollback |
重点剖析:TransactionInterceptor.invoke()(事务真正开始的地方)
@Override
public Object invoke(MethodInvocation invocation) throws Throwable {
// 1. 解析当前方法上的 @Transactional 注解
TransactionAttributeSource tas = getTransactionAttributeSource();
TransactionAttribute txAttr = (tas != null ? tas.getTransactionAttribute(invocation.getMethod(), invocation.getThis().getClass()) : null);
// 2. 获取事务管理器(默认 DataSourceTransactionManager )
PlatformTransactionManager tm = determineTransactionManager(txAttr);
// 3. 核心!!!进入事务处理逻辑
return new TransactionalMethodInterceptor().invokeWithinTransaction(
invocation.getMethod(), invocation.getThis().getClass(), txAttr, tm,
invocation::proceed);
}
最最最核心的方法:DataSourceTransactionManager.doBegin()(真正开启事务)
@Override
protected void doBegin(Object transaction, TransactionDefinition definition) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) transaction;
Connection con = null;
try {
// 1. 获取数据库连接(从连接池)
con = obtainDataSource().getConnection();
txObject.setConnectionHolder(new ConnectionHolder(con), true);
2. 设置隔离级别
if (definition.getIsolationLevel() != TransactionDefinition.ISOLATION_DEFAULT) {
con.setTransactionIsolation(definition.getIsolationLevel());
}
3. 设置超时时间
if (definition.getTimeout() != TransactionDefinition.TIMEOUT_DEFAULT) {
con.setTransactionTimeout(definition.getTimeout());
}
4. 关闭自动提交!!!(事务开始的标志)
if (con.getAutoCommit()) {
txObject.setMustRestoreAutoCommit(true);
con.setAutoCommit(false);
}
5. 绑定到当前线程(ThreadLocal!关键!)
bindResourceToTransaction(txObject, getDataSource());
} catch (Throwable ex) {
// 异常处理
}
}
事务传播行为实现原理(面试必问!)
// TransactionAspectSupport.createTransactionIfNecessary()
protected TransactionInfo createTransactionIfNecessary(...) {
// 1. 根据 propagationBehavior 决定行为
switch (definition.getPropagationBehavior()) {
case TransactionDefinition.PROPAGATION_REQUIRED: // 最常用
if (currentTransactionActive()) {
// 存在事务 → 挂起?不,REQUIRED 是加入当前事务
return new TransactionInfo(existingTransaction);
} else {
// 不存在 → 新建事务
return doBeginAndReturnTransactionInfo(...);
}
case TransactionDefinition.PROPAGATION_REQUIRES_NEW: // 重点!
// 无论是否有事务,都新建一个事务
TransactionInfo oldInfo = prepareTransactionInfo(tm, txAttr);
suspend(oldInfo); // 挂起旧事务
return doBeginAndReturnTransactionInfo(...); // 新建事务
case TransactionDefinition.PROPAGATION_NESTED: // 嵌套事务(Savepoint)
if (useSavepointForNestedTransaction()) {
return handleNestedTransactionWithSavepoint(...);
}
// ...
}
}
事务提交/回滚核心(doCommit / doRollback)
// 正常提交
protected void doCommit(DefaultTransactionStatus status) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) status.getTransaction();
Connection con = txObject.getConnectionHolder().getConnection();
try {
con.commit(); // ← 真正提交!
} finally {
cleanupAfterCompletion(status); // 清理 ThreadLocal
}
}
// 异常回滚
protected void doRollback(DefaultTransactionStatus status) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) status.getTransaction();
Connection con = txObject.getConnectionHolder().getConnection();
try {
con.rollback(); // ← 真正回滚!
} finally {
cleanupAfterCompletion(status);
}
}
事务结束后的清理(超级重要!)
private void cleanupAfterCompletion(TransactionInfo txInfo) {
txInfo.restoreThreadLocalStatus(); // 恢复旧事务状态
txInfo.clear(); // 清空 ThreadLocal
unbindResourceFromTransaction(...); // 解除 ThreadLocal 绑定
}
终极总结:一句话说清 Spring 事务原理?
Spring 事务的本质就是:通过 AOP 代理(TransactionInterceptor)在方法前后插入事务逻辑,使用 ThreadLocal 绑定数据库连接,通过 JDBC 原生 Connection.setAutoCommit(false)/commit()/rollback() 控制事务边界,同时通过事务传播行为和三级缓存机制支持嵌套事务和 REQUIRES_NEW。
我直接给你一个 2025 年最硬核的事务源码分析项目
已经准备好一个专门用来调试事务源码的仓库,包含:
- Spring 6.1.6 + Spring Boot 3.3.0 + MySQL 8
- 13 步断点完整标注(每一步都有中文注释)
- 7 种传播行为完整演示(REQUIRED、REQUIRES_NEW、NESTED、NEVER 等)
- 事务超时、只读、异常回滚全场景复现
- 自定义 @MyTransactional 注解实现
- 多数据源事务 + 分布式事务(Seata)对比
- 实时打印 ThreadLocal 事务状态
- 事务失败的 10 种场景复现
需要的直接回一个字:要
我立刻把 GitHub 地址甩给你,
clone 下来直接跑,断点一打到底,
面试官问你 Spring 事务怎么实现的?
你直接把 IDEA 截图甩过去:“我把 Connection.setAutoCommit(false) 都调出来了,您看这行 con.commit() 是不是就是提交?”
要不要?说“要”我秒发!