事务的同步状态通过接口TransactionSynchronization 进行管理
public interface TransactionSynchronization {
// 事务状态
// 已提交
int STATUS_COMMITTED = 0;
// 回滚
int STATUS_ROLLED_BACK = 1;
// 未知状态
int STATUS_UNKNOWN = 2;
// 暂定事务,将线程与事务解绑
default void suspend() {}
// 恢复事务,将暂停的事务与线程重新绑定
default void resume() {}
}
抽象类TransactionSynchronizationManager 负责管理事务与线程的绑定关系
public abstract class TransactionSynchronizationManager {
// 保存连接资源 resource --> connection
private static final ThreadLocal<Map<Object, Object>> resources =
new NamedThreadLocal<>("Transactional resources");
// 保存事务同步器
private static final ThreadLocal<Set<TransactionSynchronization>> synchronizations =
new NamedThreadLocal<>("Transaction synchronizations");
// 保存事务的名称
private static final ThreadLocal<String> currentTransactionName =
new NamedThreadLocal<>("Current transaction name");
// 保存事务是否为只读
private static final ThreadLocal<Boolean> currentTransactionReadOnly =
new NamedThreadLocal<>("Current transaction read-only status");
// 保存事务的隔离级别
private static final ThreadLocal<Integer> currentTransactionIsolationLevel =
new NamedThreadLocal<>("Current transaction isolation level");
// 保存事务的活跃状态
private static final ThreadLocal<Boolean> actualTransactionActive =
new NamedThreadLocal<>("Actual transaction active");
}
事务的执行流程
事务的挂起AbstractPlatformTransactionManager.suspend(),大致做了以下几件事
- 释放持有的资源
- 将当前连接与线程解绑
- 保存当前连接,以便将来恢复
事务的恢复 AbstractPlatformTransactionManager.resume(),大致做了以下几件事
- 从传入的holder中获取暂存的资源
- 将当前线程与资源绑定
- 恢复ThreadLocal中的用于事务同步的数据
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);
}
}
}
声明式事务
声明式事务的使用需要@EnableTransactionManagement注解,该注解import了一个类:TransactionManagementConfigurationSelector,这个类可以帮我们引入事务相关的Bean
TransationAspectSupport.invokeWithinTransaction()是事务AOP的具体实现
@Nullable
protected Object invokeWithinTransaction(Method method, @Nullable Class<?> targetClass,
final InvocationCallback invocation) throws Throwable {
PlatformTransactionManager ptm = asPlatformTransactionManager(tm);
final String joinpointIdentification = methodIdentification(method, targetClass, txAttr);
if (txAttr == null || !(ptm instanceof CallbackPreferringPlatformTransactionManager)) {
// 创建事务,处理事务的传播行为
TransactionInfo txInfo = createTransactionIfNecessary(ptm, txAttr, joinpointIdentification);
Object retVal;
try {
// 环绕式AOP,此为切入点,即被环绕的方法
retVal = invocation.proceedWithInvocation();
}
catch (Throwable ex) {
// target invocation exception
// 发生问题,回滚
completeTransactionAfterThrowing(txInfo, ex);
throw ex;
}
finally {
// 清除事务信息,有挂起事务则恢复挂起事务
cleanupTransactionInfo(txInfo);
}
// 提交事务
commitTransactionAfterReturning(txInfo);
return retVal;
}
}
其中createTransactionIfNecessary()会尝试创建新事务
protected TransactionInfo createTransactionIfNecessary(@Nullable PlatformTransactionManager tm,
@Nullable TransactionAttribute txAttr, final String joinpointIdentification) {
...
TransactionStatus status = null;
if (txAttr != null) {
if (tm != null) {
// 创建事务
status = tm.getTransaction(txAttr);
}
else {
// log
}
}
return prepareTransactionInfo(tm, txAttr, joinpointIdentification, status);
}
其中getTransaction处理事务的传播行为,简而言之,就是根据当前是否存在事务和事务的传播行为,来决定是否挂起当前事务、抛出异常等操作。
public final TransactionStatus getTransaction(@Nullable TransactionDefinition definition)
throws TransactionException {
// 如果传入的事务定义为 null,则使用默认的事务定义
TransactionDefinition def = (definition != null ? definition : TransactionDefinition.withDefaults());
Object transaction = doGetTransaction();
boolean debugEnabled = logger.isDebugEnabled();
// 如果当前存在事务,处理对应事务传播行为
if (isExistingTransaction(transaction)) {
return handleExistingTransaction(def, transaction, debugEnabled);
}
// Check definition settings for new transaction.
if (def.getTimeout() < TransactionDefinition.TIMEOUT_DEFAULT) {
throw new InvalidTimeoutException("Invalid transaction timeout", def.getTimeout());
}
// 如果当前不存在事务,处理对应事务传播行为
if (def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_MANDATORY) {
throw new IllegalTransactionStateException(
"No existing transaction found for transaction marked with propagation 'mandatory'");
}
else if (def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRED ||
def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRES_NEW ||
def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NESTED) {
SuspendedResourcesHolder suspendedResources = suspend(null);
if (debugEnabled) {
logger.debug("Creating new transaction with name [" + def.getName() + "]: " + def);
}
try {
return startTransaction(def, transaction, debugEnabled, suspendedResources);
}
catch (RuntimeException | Error ex) {
resume(null, suspendedResources);
throw ex;
}
}
else {
// Create "empty" transaction: no actual transaction, but potentially synchronization.
if (def.getIsolationLevel() != TransactionDefinition.ISOLATION_DEFAULT && logger.isWarnEnabled()) {
logger.warn("Custom isolation level specified but no actual transaction initiated; " +
"isolation level will effectively be ignored: " + def);
}
boolean newSynchronization = (getTransactionSynchronization() == SYNCHRONIZATION_ALWAYS);
return prepareTransactionStatus(def, null, true, newSynchronization, debugEnabled, null);
}
}