part3-abstract-platform-transaction-manager
约 3536 字大约 12 分钟
2026-05-24
系列文章:《深入Spring事务与数据源:从注解到数据库连接的全链路解析》
第三篇:AbstractPlatformTransactionManager事务管理器详解
基于版本:Spring Framework 5.3.x
前置阅读:第二篇:事务的起点
前言
在上一篇文章中,我们追踪了TransactionInterceptor如何开启事务,最终调用了AbstractPlatformTransactionManager.getTransaction()方法。但这个方法是事务管理的真正核心,它实现了标准的事务生命周期管理。
// AbstractPlatformTransactionManager的模板方法
public final TransactionStatus getTransaction(@Nullable TransactionDefinition definition) {
// 1. 获取事务对象
Object transaction = doGetTransaction();
// 2. 检查是否存在事务
if (isExistingTransaction(transaction)) {
// 处理现有事务(传播行为)
return handleExistingTransaction(def, transaction, debugEnabled);
}
// 3. 创建新事务
return startTransaction(def, transaction, debugEnabled, suspendedResources);
}本文将深入分析AbstractPlatformTransactionManager的完整事务生命周期,包括事务的传播、挂起、恢复、提交和回滚。
一、AbstractPlatformTransactionManager的架构设计
1.1 模板方法模式的应用
AbstractPlatformTransactionManager是Spring事务管理的核心基类,它采用了经典的模板方法模式:
PlatformTransactionManager (接口)
↑
│
AbstractPlatformTransactionManager (抽象类)
│ ← 实现标准事务管理流程
│
├─ DataSourceTransactionManager (JDBC事务)
├─ JpaTransactionManager (JPA事务)
├─ HibernateTransactionManager (Hibernate事务)
└─ JtaTransactionManager (分布式事务)模板方法模式的精髓:
- 父类定义流程:抽象类定义事务管理的标准流程
- 子类实现细节:具体子类实现特定平台的细节操作
1.2 核心模板方法
public abstract class AbstractPlatformTransactionManager
implements PlatformTransactionManager, Serializable {
// ========== 标准流程(父类实现) ==========
@Override
public final TransactionStatus getTransaction(...) {
// 标准的事务获取流程
Object transaction = doGetTransaction(); // ← 子类实现
if (isExistingTransaction(transaction)) { // ← 子类实现
return handleExistingTransaction(...);
}
return startTransaction(...);
}
@Override
public final void commit(TransactionStatus status) {
// 标准的提交流程
if (status.isLocalRollbackOnly()) {
processRollback(...);
} else {
processCommit(...); // ← 调用doCommit(子类实现)
}
}
@Override
public final void rollback(TransactionStatus status) {
// 标准的回滚流程
processRollback(...); // ← 调用doRollback(子类实现)
}
// ========== 抽象方法(子类必须实现) ==========
protected abstract Object doGetTransaction() throws TransactionException;
protected abstract boolean isExistingTransaction(Object transaction);
protected abstract void doBegin(Object transaction, TransactionDefinition definition);
protected abstract void doCommit(DefaultTransactionStatus status);
protected abstract void doRollback(DefaultTransactionStatus status);
protected abstract void doSetRollbackOnly(DefaultTransactionStatus status);
// ========== 可选方法(子类可选择实现) ==========
protected Object doSuspend(Object transaction) { throw new ...; }
protected void doResume(Object transaction, Object suspendedResources) { }
protected void doCleanupAfterCompletion(Object transaction) { }
}设计优势:
- 统一的事务管理逻辑:传播行为、同步机制等在父类统一实现
- 灵活的扩展性:不同数据访问技术只需实现特定方法
- 代码复用:避免每个事务管理器都实现相同的逻辑
二、事务的完整生命周期
2.1 生命周期概览
一个完整的事务生命周期包括:
创建 → 执行业务 → 提交/回滚 → 清理
↑ ↑ ↑ ↑
doBegin 业务方法 doCommit doCleanupAfterCompletion
doRollback2.2 startTransaction:启动新事务
源码位置:spring-tx/src/main/java/org/springframework/transaction/support/AbstractPlatformTransactionManager.java
private TransactionStatus startTransaction(TransactionDefinition definition,
Object transaction,
boolean debugEnabled,
@Nullable SuspendedResourcesHolder suspendedResources) {
// 1. 是否启用事务同步
boolean newSynchronization = (getTransactionSynchronization() != SYNCHRONIZATION_NEVER);
// 2. 创建事务状态对象
DefaultTransactionStatus status = newTransactionStatus(
definition, transaction, true, newSynchronization, debugEnabled, suspendedResources);
// 3. 调用子类的doBegin方法(真正开启事务)
doBegin(transaction, definition);
// 4. 准备事务同步
prepareSynchronization(status, definition);
return status;
}关键步骤:
- 创建
DefaultTransactionStatus记录事务状态 - 调用
doBegin()由子类真正开启事务 - 初始化事务同步机制
2.3 newTransactionStatus:创建事务状态
protected DefaultTransactionStatus newTransactionStatus(
TransactionDefinition definition,
@Nullable Object transaction,
boolean newTransaction,
boolean newSynchronization,
boolean debug,
@Nullable Object suspendedResources) {
// 检查事务激活状态
boolean actualNewSynchronization = newSynchronization &&
!TransactionSynchronizationManager.isSynchronizationActive();
// 如果是新同步,激活同步管理器
if (actualNewSynchronization) {
TransactionSynchronizationManager.setActualTransactionActive(true);
TransactionSynchronizationManager.setCurrentTransactionIsolationLevel(
(definition.getIsolationLevel() != TransactionDefinition.ISOLATION_DEFAULT)
? definition.getIsolationLevel() : null);
TransactionSynchronizationManager.setCurrentTransactionReadOnly(
definition.isReadOnly());
TransactionSynchronizationManager.setCurrentTransactionName(
definition.getName());
TransactionSynchronizationManager.initSynchronization();
}
return new DefaultTransactionStatus(
transaction, newTransaction, newSynchronization,
actualNewSynchronization, debug, suspendedResources);
}设置的事务属性:
actualTransactionActive:标记事务是否活跃currentTransactionIsolationLevel:当前隔离级别currentTransactionReadOnly:只读标记currentTransactionName:事务名称
三、事务传播行为的完整实现
3.1 handleExistingTransaction:处理现有事务
当检测到已存在事务时,根据传播行为采取不同策略:
private TransactionStatus handleExistingTransaction(
TransactionDefinition definition,
Object transaction,
boolean debugEnabled) throws TransactionException {
// ========== PROPAGATION_NEVER:不允许有事务 ==========
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NEVER) {
throw new IllegalTransactionStateException(
"Existing transaction found for transaction marked with propagation 'never'");
}
// ========== PROPAGATION_NOT_SUPPORTED:挂起事务,非事务执行 ==========
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NOT_SUPPORTED) {
if (debugEnabled) {
logger.debug("Suspending current transaction");
}
// 挂起现有事务
Object suspendedResources = suspend(transaction);
try {
// 创建非事务状态
return prepareTransactionStatus(
definition, null, false, newSynchronization, debugEnabled, suspendedResources);
}
catch (RuntimeException | Error ex) {
// 恢复事务
resume(transaction, suspendedResources);
throw ex;
}
}
// ========== PROPAGATION_REQUIRES_NEW:挂起旧事务,创建新事务 ==========
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRES_NEW) {
if (debugEnabled) {
logger.debug("Suspending current transaction, creating new transaction with name [" +
definition.getName() + "]");
}
// 挂起现有事务
SuspendedResourcesHolder suspendedResources = suspend(transaction);
try {
// 启动新事务
return startTransaction(definition, transaction, debugEnabled, suspendedResources);
}
catch (RuntimeException | Error ex) {
// 恢复事务
resume(transaction, suspendedResources);
throw ex;
}
}
// ========== PROPAGATION_NESTED:创建嵌套事务 ==========
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NESTED) {
if (!isNestedTransactionAllowed()) {
throw new NestedTransactionNotSupportedException(
"Transaction manager does not allow nested transactions");
}
if (debugEnabled) {
logger.debug("Creating nested transaction with name [" + definition.getName() + "]");
}
// 创建savepoint
if (useSavepointForNestedTransaction()) {
// 使用JDBC Savepoint
DefaultTransactionStatus status = prepareTransactionStatus(
definition, transaction, false, false, debugEnabled, null);
status.createAndHoldSavepoint();
return status;
}
else {
// 创建完整新事务(嵌套)
return startTransaction(definition, transaction, debugEnabled, null);
}
}
// ========== PROPAGATION_REQUIRED / SUPPORTS / MANDATORY:加入现有事务 ==========
if (debugEnabled) {
logger.debug("Participating in existing transaction");
}
// 检查是否需要验证现有事务
if (isValidateExistingTransaction()) {
// 验证隔离级别和只读设置
// ...
}
// 加入现有事务
boolean newSynchronization = (getTransactionSynchronization() != SYNCHRONIZATION_NEVER);
return prepareTransactionStatus(definition, transaction, false, newSynchronization, debugEnabled, null);
}3.2 事务挂起机制
protected final SuspendedResourcesHolder suspend(@Nullable Object transaction)
throws TransactionException {
// 1. 检查是否有活跃的事务同步
if (TransactionSynchronizationManager.isSynchronizationActive()) {
// 挂起所有同步回调
List<TransactionSynchronization> suspendedSynchronizations =
doSuspendSynchronization();
try {
Object suspendedResources = null;
if (transaction != null) {
// 2. 挂起事务资源(由子类实现)
suspendedResources = doSuspend(transaction);
}
// 3. 解除ThreadLocal绑定
String name = TransactionSynchronizationManager.getCurrentTransactionName();
TransactionSynchronizationManager.setCurrentTransactionName(null);
boolean readOnly = TransactionSynchronizationManager.isCurrentTransactionReadOnly();
TransactionSynchronizationManager.setCurrentTransactionReadOnly(false);
Integer isolationLevel = TransactionSynchronizationManager.getCurrentTransactionIsolationLevel();
TransactionSynchronizationManager.setCurrentTransactionIsolationLevel(null);
boolean wasActive = TransactionSynchronizationManager.isActualTransactionActive();
TransactionSynchronizationManager.setActualTransactionActive(false);
// 4. 返回挂起的资源
return new SuspendedResourcesHolder(
suspendedResources, suspendedSynchronizations, name, readOnly, isolationLevel, wasActive);
}
catch (RuntimeException | Error ex) {
doResumeSynchronization(suspendedSynchronizations);
throw ex;
}
}
else if (transaction != null) {
// 没有同步,但有事务
Object suspendedResources = doSuspend(transaction);
return new SuspendedResourcesHolder(suspendedResources);
}
else {
return null;
}
}3.3 DataSourceTransactionManager的doSuspend实现
源码位置:spring-jdbc/src/main/java/org/springframework/jdbc/datasource/DataSourceTransactionManager.java
@Override
protected Object doSuspend(Object transaction) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) transaction;
// 清空事务对象的ConnectionHolder
txObject.setConnectionHolder(null);
// 从ThreadLocal解绑并返回
return TransactionSynchronizationManager.unbindResource(obtainDataSource());
}关键操作:
- 将
ConnectionHolder从TransactionSynchronizationManager解绑 - 返回解绑的资源,以便后续恢复
3.4 事务恢复机制
protected final void resume(@Nullable Object transaction,
@Nullable SuspendedResourcesHolder resourcesHolder)
throws TransactionException {
if (resourcesHolder != null) {
Object suspendedResources = resourcesHolder.suspendedResources;
if (suspendedResources != null) {
// 恢复事务资源(由子类实现)
doResume(transaction, suspendedResources);
}
// 恢复事务同步
List<TransactionSynchronization> suspendedSynchronizations =
resourcesHolder.suspendedSynchronizations;
if (suspendedSynchronizations != null) {
TransactionSynchronizationManager.setActualTransactionActive(
resourcesHolder.wasActive);
TransactionSynchronizationManager.setCurrentTransactionIsolationLevel(
resourcesHolder.isolationLevel);
TransactionSynchronizationManager.setCurrentTransactionReadOnly(
resourcesHolder.readOnly);
TransactionSynchronizationManager.setCurrentTransactionName(
resourcesHolder.name);
// 重新激活同步
doResumeSynchronization(suspendedSynchronizations);
}
}
}3.5 DataSourceTransactionManager的doResume实现
@Override
protected void doResume(@Nullable Object transaction, Object suspendedResources) {
// 将ConnectionHolder重新绑定到ThreadLocal
TransactionSynchronizationManager.bindResource(obtainDataSource(), suspendedResources);
}四、事务提交机制
4.1 commit方法:标准提交流程
@Override
public final void commit(TransactionStatus status) throws TransactionException {
// 1. 检查事务状态
if (status.isCompleted()) {
throw new IllegalTransactionStateException(
"Transaction is already completed - do not call commit or rollback");
}
DefaultTransactionStatus defStatus = (DefaultTransactionStatus) status;
// 2. 检查是否标记为rollback-only
if (defStatus.isLocalRollbackOnly()) {
if (defStatus.isDebug()) {
logger.debug("Transactional code has requested rollback");
}
// 执行回滚
processRollback(defStatus, false);
return;
}
// 3. 检查是否应该提交
if (!shouldCommitOnGlobalRollbackOnly() && defStatus.isGlobalRollbackOnly()) {
if (defStatus.isDebug()) {
logger.debug("Global transaction is marked as rollback-only");
}
// 执行回滚
processRollback(defStatus, true);
return;
}
// 4. 执行提交
processCommit(defStatus);
}提交条件:
- 事务未完成
- 未标记为
rollback-only
4.2 processCommit:处理提交
private void processCommit(DefaultTransactionStatus status) throws TransactionException {
try {
boolean beforeCompletionInvoked = false;
try {
boolean unexpectedRollback = false;
prepareForCommit(status);
// 1. 提交前回调
doBeginBeforeCompletion(status);
beforeCompletionInvoked = true;
// 2. 触发beforeCommit同步回调
boolean beforeCommitInvoked = false;
if (!status.isNewSynchronization()) {
TriggerBeforeCommitTrigger(status);
}
beforeCommitInvoked = true;
// 3. 调用子类的doCommit(真正提交)
doCommit(status);
// 4. 标记为意外回滚(如果全局标记)
unexpectedRollback = status.isGlobalRollbackOnly();
// 5. 提交后回调
doAfterCommit(status);
// 6. 触发afterCommit同步回调
triggerAfterCommit(status);
// 7. 标记意外回滚
if (unexpectedRollback) {
throw new UnexpectedRollbackException(
"Transaction silently rolled back because it has been marked as rollback-only");
}
}
finally {
// 8. 完成清理
cleanupAfterCompletion(status);
}
}
catch (TransactionSystemException ex) {
// 提交失败,触发回滚
if (isRollbackOnCommitFailure()) {
doRollbackOnCommitException(status, ex);
}
else {
throw ex;
}
}
catch (RuntimeException | Error ex) {
// 其他异常
if (isRollbackOnCommitFailure()) {
doRollbackOnCommitException(status, ex);
}
else {
throw ex;
}
}
}4.3 DataSourceTransactionManager的doCommit实现
@Override
protected void doCommit(DefaultTransactionStatus status) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) status.getTransaction();
Connection con = txObject.getConnectionHolder().getConnection();
if (status.isDebug()) {
logger.debug("Committing JDBC transaction on Connection [" + con + "]");
}
try {
// 调用JDBC的commit方法
con.commit();
}
catch (SQLException ex) {
throw translateException("JDBC commit", ex);
}
}核心操作:直接调用Connection.commit()
五、事务回滚机制
5.1 rollback方法
@Override
public final void rollback(TransactionStatus status) throws TransactionException {
if (status.isCompleted()) {
throw new IllegalTransactionStateException(
"Transaction is already completed - do not call commit or rollback");
}
DefaultTransactionStatus defStatus = (DefaultTransactionStatus) status;
processRollback(defStatus, false);
}5.2 processRollback:处理回滚
private void processRollback(DefaultTransactionStatus status, boolean unexpected) {
try {
boolean unexpectedRollback = unexpected;
try {
// 1. 触发beforeCompletion回调
triggerBeforeCompletion(status);
// 2. 检查是否有savepoint(嵌套事务)
if (status.hasSavepoint()) {
if (status.isDebug()) {
logger.debug("Rolling back transaction to savepoint");
}
// 回滚到savepoint
status.rollbackToHeldSavepoint();
}
// 3. 检查是否是新事务
else if (status.isNewTransaction()) {
if (status.isDebug()) {
logger.debug("Initiating transaction rollback");
}
// 调用子类的doRollback(真正回滚)
doRollback(status);
}
else {
// 参与现有事务,只标记rollback-only
if (status.hasTransaction()) {
if (status.isLocalRollbackOnly()
|| isGlobalRollbackOnParticipationFailure()) {
if (status.isDebug()) {
logger.debug("Participating transaction failed - marking existing transaction as rollback-only");
}
doSetRollbackOnly(status);
}
}
else {
logger.debug("Should roll back transaction but cannot");
}
}
// 检查是否应该在提交失败后回滚
if (!unexpectedRollback) {
doCleanupAfterCompletion(status.getTransaction());
}
}
finally {
// 完成清理
cleanupAfterCompletion(status);
}
}
catch (RuntimeException | Error ex) {
throw ex;
}
}5.3 DataSourceTransactionManager的doRollback实现
@Override
protected void doRollback(DefaultTransactionStatus status) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) status.getTransaction();
Connection con = txObject.getConnectionHolder().getConnection();
if (status.isDebug()) {
logger.debug("Rolling back JDBC transaction on Connection [" + con + "]");
}
try {
// 调用JDBC的rollback方法
con.rollback();
}
catch (SQLException ex) {
throw translateException("JDBC rollback", ex);
}
}核心操作:直接调用Connection.rollback()
六、事务同步机制
6.1 TransactionSynchronization接口
public interface TransactionSynchronization extends Ordered, Flushable {
int STATUS_COMMITTED = 0;
int STATUS_ROLLED_BACK = 1;
int STATUS_UNKNOWN = 2;
// 事务挂起时调用
default void suspend() { }
// 事务恢复时调用
default void resume() { }
// 刷新资源(如Hibernate Session)
@Override
default void flush() { }
// 提交前调用
default void beforeCommit(boolean readOnly) { }
// 完成前调用(提交或回滚前)
default void beforeCompletion() { }
// 提交后调用
default void afterCommit() { }
// 完成后调用(提交或回滚后)
default void afterCompletion(int status) { }
}6.2 同步回调的注册
// 注册同步回调
public static void registerTransactionSynchronization(TransactionSynchronization synchronization) {
synchronizations.get().add(synchronization);
}典型应用:
// MyBatis注册Connection同步回调
TransactionSynchronizationManager.registerSynchronization(
new TransactionSynchronization() {
@Override
public void beforeCompletion() {
// 事务完成前关闭SqlSession
sqlSession.close();
}
}
);6.3 触发同步回调
private void triggerBeforeCommit(DefaultTransactionStatus status) {
if (status.isNewSynchronization()) {
List<TransactionSynchronization> synchronizations =
TransactionSynchronizationManager.getSynchronizations();
TransactionSynchronizationUtils.triggerBeforeCommit(
status.isReadOnly(), synchronizations);
}
}
private void triggerBeforeCompletion(DefaultTransactionStatus status) {
if (status.isNewSynchronization()) {
List<TransactionSynchronization> synchronizations =
TransactionSynchronizationManager.getSynchronizations();
TransactionSynchronizationUtils.triggerBeforeCompletion(synchronizations);
}
}
private void triggerAfterCommit(DefaultTransactionStatus status) {
if (status.isNewSynchronization()) {
List<TransactionSynchronization> synchronizations =
TransactionSynchronizationManager.getSynchronizations();
TransactionSynchronizationUtils.triggerAfterCommit(synchronizations);
}
}
private void triggerAfterCompletion(DefaultTransactionStatus status, int status) {
if (status.isNewSynchronization()) {
List<TransactionSynchronization> synchronizations =
TransactionSynchronizationManager.getSynchronizations();
TransactionSynchronizationUtils.triggerAfterCompletion(synchronizations, status);
}
}七、事务清理机制
7.1 cleanupAfterCompletion
private void cleanupAfterCompletion(DefaultTransactionStatus status) {
// 1. 标记为已完成
status.setCompleted();
// 2. 清理同步
if (status.isNewSynchronization()) {
TransactionSynchronizationManager.clearSynchronization();
TransactionSynchronizationManager.setCurrentTransactionName(null);
TransactionSynchronizationManager.setActualTransactionActive(false);
TransactionSynchronizationManager.setCurrentTransactionReadOnly(false);
TransactionSynchronizationManager.setCurrentTransactionIsolationLevel(
TransactionDefinition.ISOLATION_DEFAULT);
}
// 3. 恢复挂起的事务
if (status.getSuspendedResources() != null) {
Object transaction = (status.hasTransaction() ? status.getTransaction() : null);
resume(transaction, status.getSuspendedResources());
}
// 4. 清理事务资源
if (status.getTransaction() != null) {
doCleanupAfterCompletion(status.getTransaction());
}
}7.2 DataSourceTransactionManager的doCleanupAfterCompletion实现
@Override
protected void doCleanupAfterCompletion(Object transaction) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) transaction;
// 1. 从ThreadLocal移除ConnectionHolder
if (txObject.isNewConnectionHolder()) {
TransactionSynchronizationManager.unbindResource(obtainDataSource());
}
// 2. 重置连接
Connection con = txObject.getConnectionHolder().getConnection();
try {
// 恢复自动提交
if (txObject.isMustRestoreAutoCommit()) {
con.setAutoCommit(true);
}
// 重置隔离级别和只读标记
DataSourceUtils.resetConnectionAfterTransaction(
con, txObject.getPreviousIsolationLevel(), txObject.isReadOnly());
}
catch (Throwable ex) {
logger.debug("Could not reset JDBC Connection after transaction", ex);
}
// 3. 释放连接(返回连接池)
if (txObject.isNewConnectionHolder()) {
if (logger.isDebugEnabled()) {
logger.debug("Releasing JDBC Connection [" + con + "] after transaction");
}
DataSourceUtils.releaseConnection(con, this.dataSource);
}
// 4. 清空ConnectionHolder
txObject.getConnectionHolder().clear();
}关键步骤:
- 从ThreadLocal解绑
- 恢复连接状态(自动提交、隔离级别)
- 释放连接(返回连接池)
- 清空ConnectionHolder
八、完整的事务生命周期时序图
┌─────────────────────────────────────────────────────────────────┐
│ 事务开始 │
└────────────────────┬────────────────────────────────────────────┘
│
↓
┌─────────────────────────────────────────────────────────────────┐
│ AbstractPlatformTransactionManager.getTransaction() │
│ │
│ 1. doGetTransaction() │
│ → DataSourceTransactionManager.doGetTransaction() │
│ → 创建DataSourceTransactionObject │
│ → 从ThreadLocal获取ConnectionHolder │
│ │
│ 2. isExistingTransaction() │
│ → 判断是否有活跃事务 │
│ │
│ 3. 不存在事务 → startTransaction() │
└────────────────────┬────────────────────────────────────────────┘
│
↓
┌─────────────────────────────────────────────────────────────────┐
│ startTransaction() │
│ │
│ 1. newTransactionStatus() │
│ → 创建DefaultTransactionStatus │
│ → 激活TransactionSynchronizationManager │
│ │
│ 2. doBegin(transaction, definition) │
│ → DataSourceTransactionManager.doBegin() │
│ → dataSource.getConnection() ← 从连接池获取连接 │
│ → con.setAutoCommit(false) ← 关闭自动提交 │
│ → 设置隔离级别、只读、超时 │
│ → TransactionSynchronizationManager.bindResource() │
│ 绑定ConnectionHolder到ThreadLocal │
│ │
│ 3. prepareSynchronization() │
│ → 初始化事务同步 │
└────────────────────┬────────────────────────────────────────────┘
│
↓
┌─────────────────────────────────────────────────────────────────┐
│ 执行业务方法 │
│ → userRepository.save(user) │
│ → 使用同一个Connection执行SQL │
└────────────────────┬────────────────────────────────────────────┘
│
↓ (正常完成)
┌─────────────────────────────────────────────────────────────────┐
│ AbstractPlatformTransactionManager.commit() │
│ │
│ 1. 检查是否标记rollback-only │
│ → 否,继续提交 │
│ │
│ 2. processCommit() │
│ → triggerBeforeCommit() ← 触发提交前回调 │
│ → doCommit(status) │
│ → DataSourceTransactionManager.doCommit() │
│ → con.commit() ← JDBC提交 │
│ → triggerAfterCommit() ← 触发提交后回调 │
│ → cleanupAfterCompletion() │
│ → 清理ThreadLocal │
│ → 恢复连接状态 │
│ → 释放连接(返回连接池) │
└─────────────────────────────────────────────────────────────────┘
│
↓ (发生异常)
┌─────────────────────────────────────────────────────────────────┐
│ AbstractPlatformTransactionManager.rollback() │
│ │
│ 1. processRollback() │
│ → triggerBeforeCompletion() ← 触发完成前回调 │
│ │
│ 2. 检查是否有savepoint(嵌套事务) │
│ → 有: rollbackToHeldSavepoint() │
│ → 无:继续 │
│ │
│ 3. 检查是否是新事务 │
│ → 是: doRollback(status) │
│ → DataSourceTransactionManager.doRollback() │
│ → con.rollback() ← JDBC回滚 │
│ → 否: doSetRollbackOnly() ← 标记rollback-only │
│ │
│ 4. cleanupAfterCompletion() │
│ → 清理ThreadLocal │
│ → 恢复连接状态 │
│ → 释放连接(返回连接池) │
└─────────────────────────────────────────────────────────────────┘九、关键问题解答
Q1:嵌套事务是如何实现的?
@Transactional
public void outerMethod() {
// 外层事务
innerMethod(); // 调用嵌套事务方法
}
@Transactional(propagation = Propagation.NESTED)
public void innerMethod() {
// 嵌套事务
// 如果这里抛异常,只会回滚到savepoint
// 外层事务可以选择捕获异常继续执行
}实现机制:
// 创建savepoint
status.createAndHoldSavepoint();
// SavepointManager实现
public void createAndHoldSavepoint() throws TransactionException {
setSavepoint(getSavepointManager().createSavepoint());
}
// JDBC Savepoint
public Object createSavepoint() throws SQLException {
Connection con = getConnection();
return con.setSavepoint(); // JDBC 3.0 Savepoint
}Q2:事务传播行为REQUIRED和REQUIRES_NEW的底层区别?
REQUIRED:
ThreadLocal:
ConnectionHolder → conn1
执行:
outerMethod() → 使用conn1
innerMethod() → 使用conn1 (同一个)REQUIRES_NEW:
外层事务开始:
ThreadLocal:
ConnectionHolder → conn1
内层事务开始(suspend):
1. 解绑conn1
2. 保存到SuspendedResourcesHolder
3. 获取新连接conn2
ThreadLocal:
ConnectionHolder → conn2 (新的)
执行:
outerMethod() → 使用conn1 (挂起)
innerMethod() → 使用conn2 (新的)
内层事务结束(resume):
1. 释放conn2
2. 恢复conn1
ThreadLocal:
ConnectionHolder → conn1 (恢复)Q3:什么情况下事务会失效?
- 同类内部调用:
this.method()不走代理 - 非public方法:
@Transactional只能用于public方法 - 异常被捕获:异常未抛出,事务管理器无法捕获
- 数据库引擎不支持:如MySQL MyISAM不支持事务
- 多数据源未正确配置:使用了错误的事务管理器
十、总结与伏笔
通过本文的深入分析,我们完整理解了AbstractPlatformTransactionManager的事务生命周期:
- 模板方法模式:父类定义流程,子类实现细节
- 事务传播行为:7种传播行为的完整实现
- 事务挂起与恢复:ThreadLocal的绑定与解绑
- 事务提交:
con.commit()的标准流程 - 事务回滚:
con.rollback()的标准流程 - 事务同步:回调机制的设计与应用
- 事务清理:资源释放与状态恢复
但还有一个关键问题:TransactionSynchronizationManager的ThreadLocal机制是如何工作的?
- ThreadLocal的底层数据结构是什么?
ConnectionHolder如何封装数据库连接?- 资源绑定的完整流程是怎样的?
- 多线程环境下如何保证线程安全?
下一篇预告:《JDBC事务的实现:DataSourceTransactionManager与数据源的绑定》,我们将深入分析数据源事务管理器的具体实现,以及它如何与数据源(连接池)协作。
参考资料
- Spring Framework 5.3.x 源码
spring-tx/src/main/java/org/springframework/transaction/support/AbstractPlatformTransactionManager.javaspring-jdbc/src/main/java/org/springframework/jdbc/datasource/DataSourceTransactionManager.java- 《Spring源码深度解析》