基于AOP,Spring有一个针对@Transactional注解的增强器(拦截器)TransactionInterceptor
,在Bean实例初始化的最后一步对事务方法进行增强
:::info
TransactionInterceptor
:::
在调用被@Transactional 注解的public方法的时候,实际调用的是代理类TransactionInterceptor
中的invoke()方法。TransactionInterceptor
的invoke
源码如下
//TransactionInterceptor和别的拦截器一样,他也有invoke方法
public class TransactionInterceptor extends TransactionAspectSupport implements MethodInterceptor, Serializable {
............
@Override
public Object invoke(final MethodInvocation invocation) throws Throwable {
Class<?> targetClass = (invocation.getThis() != null ? AopUtils.getTargetClass(invocation.getThis()) : null);
// Adapt to TransactionAspectSupport's invokeWithinTransaction...
return invokeWithinTransaction(invocation.getMethod(), targetClass, new InvocationCallback() {
@Override
public Object proceedWithInvocation() throws Throwable {
return invocation.proceed();
}
});
}
..........
}
:::info invokeWithinTransaction ::: 跟一下invokeWithinTransaction 函数,省去不必要的代码,这里可以清晰的看到,该拦截器实现事务的方式和我们在DAO层手动实现事务差不多:
- 在目标方法之前开启事务
- 数据库方法调用,只不过这里把执行的逻辑换成了递归执行拦截链了
- 方法调用完成之后提交事务
- 方法执行过程中如果遇到异常的时候回滚事务。
到这就可以清晰地了解,Spring的事务实现就是一个Spring自带的拦截器protected Object invokeWithinTransaction(Method method, Class<?> targetClass, final InvocationCallback invocation)
throws Throwable {
.............
if (txAttr == null || !(tm instanceof CallbackPreferringPlatformTransactionManager)) {
// 开启事务
TransactionInfo txInfo = createTransactionIfNecessary(tm, txAttr, joinpointIdentification);
Object retVal = null;
try {
//递归执行拦截链
retVal = invocation.proceedWithInvocation();
}
catch (Throwable ex) {
// 出现异常,回滚事务
completeTransactionAfterThrowing(txInfo, ex);
throw ex;
}
finally {
cleanupTransactionInfo(txInfo);
}
//提交事务
commitTransactionAfterReturning(txInfo);
return retVal;
}
.................
}
TransactionInterceptor
加入到拦截链中,该拦截器负责增强实现事务。