Spring AOP(2)代理类的创建ProxyFactoryBean
在这篇文章中,我们知道如何通过ProxyFactoryBean创建代理对象。
ProxyFactoryBean本身继承了ProxyCreatorSupport所以有能力创建Proxy,只需要提供target真实对象,以及interceptorList通知列表,就能创建target的代理对象。
TransactionProxyFactoryBean继承了AbstractSingletonProxyFactoryBean,跟ProxyFactoryBean稍微有些区别,但是结果一样,就是创建代理类。后面会进行源码分析。
代码示例
//定义DataSource
<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource">
<property name="user" value="root"></property>
<property name="password" value=""></property>
<property name="jdbcUrl" value="jdbc:mysql://localhost:3306/spring?serverTimezone=UTC&useUnicode=true&characterEncoding=utf-8&useSSL=true"></property>
<property name="driverClass" value="com.mysql.cj.jdbc.Driver"></property>
</bean>
//定义transactionManager
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource"/>
</bean>
//定义jdbcTemplate
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
<property name="dataSource" ref="dataSource"></property>
</bean>
//定义dao
<bean id="userDao" class="com.spring.service.UserDao">
<property name="jdbcTemplate" ref="jdbcTemplate"/>
</bean>
//定义Service
<bean id="userService" class="com.spring.service.UserServiceImpl">
<property name="userDao" ref="userDao"/>
</bean>
//定义Service的代理类,类型是TransactionProxyFactoryBean
<bean id="userServiceProxy" class="org.springframework.transaction.interceptor.TransactionProxyFactoryBean">
<property name="transactionManager" ref="transactionManager"/>
<property name="target" ref="userService"/>
<property name="transactionAttributes">
<props>
<prop key="save*">PROPAGATION_REQUIRED</prop>
</props>
</property>
</bean>
我们定义了dataSource, transactionManager, jdbcTemplate, userDao, userService, userServiceProxy这些bean,userServiceProxy是userService的代理类,所以在测试的时候getBean("userServiceProxy"),通过这个bean来启动事务并插入数据。
TransactionProxyFactoryBean里面需要提供target,即真实对象;transactionManager这里使用的是DataSourceTransactionManager;还有transactionAttributes,类似pointCut,定义了哪些方法所拥有的事务属性。
TransactionProxyFactoryBean
TransactionProxyFactoryBean继承了AbstractSingletonProxyFactoryBean,所以本身内容比较少,能看到额外的定义了成员变量TransactionInterceptor,这个是类似增强类,它需要transactionManager和transactionAttribute。
public class TransactionProxyFactoryBean extends AbstractSingletonProxyFactoryBean
implements BeanFactoryAware {
private final TransactionInterceptor transactionInterceptor = new TransactionInterceptor();
@Nullable
private Pointcut pointcut;
//给transactionInterceptor设置transactionManager
public void setTransactionManager(PlatformTransactionManager transactionManager) {
this.transactionInterceptor.setTransactionManager(transactionManager);
}
//给transactionInterceptor设置transactionAttributes
public void setTransactionAttributes(Properties transactionAttributes) {
this.transactionInterceptor.setTransactionAttributes(transactionAttributes);
}
public void setTransactionAttributeSource(TransactionAttributeSource transactionAttributeSource) {
this.transactionInterceptor.setTransactionAttributeSource(transactionAttributeSource);
}
public void setPointcut(Pointcut pointcut) {
this.pointcut = pointcut;
}
@Override
public void setBeanFactory(BeanFactory beanFactory) {
this.transactionInterceptor.setBeanFactory(beanFactory);
}
protected Object createMainInterceptor() {
this.transactionInterceptor.afterPropertiesSet();
if (this.pointcut != null) {
return new DefaultPointcutAdvisor(this.pointcut, this.transactionInterceptor);
}
else {
// Rely on default pointcut.
return new TransactionAttributeSourceAdvisor(this.transactionInterceptor);
}
}
@Override
protected void postProcessProxyFactory(ProxyFactory proxyFactory) {
proxyFactory.addInterface(TransactionalProxy.class);
}
}
AbstractSingletonProxyFactoryBean
AbstractSingletonProxyFactoryBean是提供了创建proxy的核心代码,因为它使一个FactoryBean。
public abstract class AbstractSingletonProxyFactoryBean extends ProxyConfig
implements FactoryBean<Object>, BeanClassLoaderAware, InitializingBean {
@Nullable
private Object target;
@Nullable
private Class<?>[] proxyInterfaces;
@Nullable
private Object[] preInterceptors;
@Nullable
private Object[] postInterceptors;
/** Default is global AdvisorAdapterRegistry. */
private AdvisorAdapterRegistry advisorAdapterRegistry = GlobalAdvisorAdapterRegistry.getInstance();
@Nullable
private transient ClassLoader proxyClassLoader;
@Nullable
private Object proxy;
public void setTarget(Object target) {
this.target = target;
}
public void setProxyInterfaces(Class<?>[] proxyInterfaces) {
this.proxyInterfaces = proxyInterfaces;
}
public void setPreInterceptors(Object[] preInterceptors) {
this.preInterceptors = preInterceptors;
}
public void setPostInterceptors(Object[] postInterceptors) {
this.postInterceptors = postInterceptors;
}
public void setAdvisorAdapterRegistry(AdvisorAdapterRegistry advisorAdapterRegistry) {
this.advisorAdapterRegistry = advisorAdapterRegistry;
}
public void setProxyClassLoader(ClassLoader classLoader) {
this.proxyClassLoader = classLoader;
}
@Override
public void setBeanClassLoader(ClassLoader classLoader) {
if (this.proxyClassLoader == null) {
this.proxyClassLoader = classLoader;
}
}
//核心代码,初始化的时候创建
public void afterPropertiesSet() {
if (this.target == null) {
throw new IllegalArgumentException("Property 'target' is required");
}
if (this.target instanceof String) {
throw new IllegalArgumentException("'target' needs to be a bean reference, not a bean name as value");
}
if (this.proxyClassLoader == null) {
this.proxyClassLoader = ClassUtils.getDefaultClassLoader();
}
//还是通过ProxyFactory来创建Proxy
ProxyFactory proxyFactory = new ProxyFactory();
//将Advice或者MethodInteceptor放到Advisors里
if (this.preInterceptors != null) {
for (Object interceptor : this.preInterceptors) {
proxyFactory.addAdvisor(this.advisorAdapterRegistry.wrap(interceptor));
}
}
// Add the main interceptor (typically an Advisor).
proxyFactory.addAdvisor(this.advisorAdapterRegistry.wrap(createMainInterceptor()));
//添加后置inteceptor
if (this.postInterceptors != null) {
for (Object interceptor : this.postInterceptors) {
proxyFactory.addAdvisor(this.advisorAdapterRegistry.wrap(interceptor));
}
}
proxyFactory.copyFrom(this);
TargetSource targetSource = createTargetSource(this.target);
proxyFactory.setTargetSource(targetSource);
if (this.proxyInterfaces != null) {
proxyFactory.setInterfaces(this.proxyInterfaces);
}
else if (!isProxyTargetClass()) {
// Rely on AOP infrastructure to tell us what interfaces to proxy.
Class<?> targetClass = targetSource.getTargetClass();
if (targetClass != null) {
proxyFactory.setInterfaces(ClassUtils.getAllInterfacesForClass(targetClass, this.proxyClassLoader));
}
}
postProcessProxyFactory(proxyFactory);
//创建代理类
this.proxy = proxyFactory.getProxy(this.proxyClassLoader);
}
protected TargetSource createTargetSource(Object target) {
if (target instanceof TargetSource) {
return (TargetSource) target;
}
else {
return new SingletonTargetSource(target);
}
}
protected void postProcessProxyFactory(ProxyFactory proxyFactory) {
}
@Override
public Object getObject() {
if (this.proxy == null) {
throw new FactoryBeanNotInitializedException();
}
return this.proxy;
}
@Override
@Nullable
public Class<?> getObjectType() {
if (this.proxy != null) {
return this.proxy.getClass();
}
if (this.proxyInterfaces != null && this.proxyInterfaces.length == 1) {
return this.proxyInterfaces[0];
}
if (this.target instanceof TargetSource) {
return ((TargetSource) this.target).getTargetClass();
}
if (this.target != null) {
return this.target.getClass();
}
return null;
}
@Override
public final boolean isSingleton() {
return true;
}
//模板方法,由子类实现
protected abstract Object createMainInterceptor();
}
transactionInterceptor是重点,提供了invoke()方法来开启transaction。
transactionInterceptorTransactionInterceptor
TransactionInterceptor继承了TransactionAspectSupport,所以大部分功能在父类实现,比如invokeWithinTransaction。
TransactionAspectSupport.invokeWithinTransaction()
/实际调用transaction的地方
protected Object invokeWithinTransaction(Method method, @Nullable Class<?> targetClass,
final InvocationCallback invocation) throws Throwable {
// If the transaction attribute is null, the method is non-transactional.
//这里获取transactionAttribute,即方法和对应的transaction的属性
TransactionAttributeSource tas = getTransactionAttributeSource();
//通过method,拿到对应的transaction的属性
final TransactionAttribute txAttr = (tas != null ? tas.getTransactionAttribute(method, targetClass) : null);
//根据transaction的属性,创建不同的PlatformTransactionManager
final PlatformTransactionManager tm = determineTransactionManager(txAttr);
根据method,目标对象和transaction属性,得到被通知增强的方法名
final String joinpointIdentification = methodIdentification(method, targetClass, txAttr);
if (txAttr == null || !(tm instanceof CallbackPreferringPlatformTransactionManager)) {
// Standard transaction demarcation with getTransaction and commit/rollback calls.
通过transactionManager,transaction属性和方法名创建transaction,核心方法通过transactionManager.getTransaction获取transaction
TransactionInfo txInfo = createTransactionIfNecessary(tm, txAttr, joinpointIdentification);
Object retVal = null;
try {
// This is an around advice: Invoke the next interceptor in the chain.
// This will normally result in a target object being invoked.
//调用真实对象的方法
retVal = invocation.proceedWithInvocation();
}
catch (Throwable ex) {
// target invocation exception
//处理抛异常情况
completeTransactionAfterThrowing(txInfo, ex);
throw ex;
}
finally {
//清除TransactionInfo
cleanupTransactionInfo(txInfo);
}
//通过transactionManager来commit,里面涉及到DataSource资源的解绑
commitTransactionAfterReturning(txInfo);
return retVal;
}
else {
final ThrowableHolder throwableHolder = new ThrowableHolder();
// It's a CallbackPreferringPlatformTransactionManager: pass a TransactionCallback in.
try {
Object result = ((CallbackPreferringPlatformTransactionManager) tm).execute(txAttr, status -> {
TransactionInfo txInfo = prepareTransactionInfo(tm, txAttr, joinpointIdentification, status);
try {
return invocation.proceedWithInvocation();
}
catch (Throwable ex) {
if (txAttr.rollbackOn(ex)) {
// A RuntimeException: will lead to a rollback.
if (ex instanceof RuntimeException) {
throw (RuntimeException) ex;
}
else {
throw new ThrowableHolderException(ex);
}
}
else {
// A normal return value: will lead to a commit.
throwableHolder.throwable = ex;
return null;
}
}
finally {
cleanupTransactionInfo(txInfo);
}
});
// Check result state: It might indicate a Throwable to rethrow.
if (throwableHolder.throwable != null) {
throw throwableHolder.throwable;
}
return result;
}
catch (ThrowableHolderException ex) {
throw ex.getCause();
}
catch (TransactionSystemException ex2) {
if (throwableHolder.throwable != null) {
logger.error("Application exception overridden by commit exception", throwableHolder.throwable);
ex2.initApplicationException(throwableHolder.throwable);
}
throw ex2;
}
catch (Throwable ex2) {
if (throwableHolder.throwable != null) {
logger.error("Application exception overridden by commit exception", throwableHolder.throwable);
}
throw ex2;
}
}
}
//创建transaction
protected TransactionInfo createTransactionIfNecessary(@Nullable PlatformTransactionManager tm,
@Nullable TransactionAttribute txAttr, final String joinpointIdentification) {
// If no name specified, apply method identification as transaction name.
//通过DelegatingTransactionAttribute封装transaction的属性
if (txAttr != null && txAttr.getName() == null) {
txAttr = new DelegatingTransactionAttribute(txAttr) {
@Override
public String getName() {
return joinpointIdentification;
}
};
}
TransactionStatus status = null;
if (txAttr != null) {
if (tm != null) {
//通过transactionManager获取transaction
status = tm.getTransaction(txAttr);
}
else {
if (logger.isDebugEnabled()) {
logger.debug("Skipping transactional joinpoint [" + joinpointIdentification +
"] because no transaction manager has been configured");
}
}
}
return prepareTransactionInfo(tm, txAttr, joinpointIdentification, status);
}
创建transaction的时候,是通过transactionManager,这里就是事务处理的设计模式-模板方法模式的核心代码。PlatformTransactionManager --> AbstractPlatformTransactionManager --> 各种不同的Manager实现,基于JPA的,基于Hibernate的,基于DataSource的。
//PlatformTransactionManager定义了三个方法,核心代码都在子类AbstractPlatformTransactionManager中
public interface PlatformTransactionManager {
TransactionStatus getTransaction(@Nullable TransactionDefinition definition) throws TransactionException;
void commit(TransactionStatus status) throws TransactionException;
void rollback(TransactionStatus status) throws TransactionException;
}
//模板方法由AbstractPlatformTransactionManager提供,子类提供doGetTransaction实现
public final TransactionStatus getTransaction(@Nullable TransactionDefinition definition) throws TransactionException {
//由子类实现,获取DataSourceTransactionObject,一开始肯定是空的,没有Transaction
Object transaction = doGetTransaction();
// Cache debug flag to avoid repeated checks.
boolean debugEnabled = logger.isDebugEnabled();
if (definition == null) {
// Use defaults if no transaction definition given.
definition = new DefaultTransactionDefinition();
}
//第一次是没有Transaction的,如果有Transaction,就需要根据transaction的属性判断是不是需要挂起当前事务
if (isExistingTransaction(transaction)) {
// Existing transaction found -> check propagation behavior to find out how to behave.
return handleExistingTransaction(definition, transaction, debugEnabled);
}
//检查是否timeout
// Check definition settings for new transaction.
if (definition.getTimeout() < TransactionDefinition.TIMEOUT_DEFAULT) {
throw new InvalidTimeoutException("Invalid transaction timeout", definition.getTimeout());
}
//如果是PROPAGATION_MANDATORY,到这里没有存在的Transaction,就报错
// No existing transaction found -> check propagation behavior to find out how to proceed.
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_MANDATORY) {
throw new IllegalTransactionStateException(
"No existing transaction found for transaction marked with propagation 'mandatory'");
}
//如果是PROPAGATION_REQUIRED,PROPAGATION_REQUIRES_NEW,PROPAGATION_NESTED
else if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRED ||
definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRES_NEW ||
definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NESTED) {
//走到这就是没有存在的Transaction,就不需要挂起已有的Transaction,而直接创建新的Transaction
SuspendedResourcesHolder suspendedResources = suspend(null);
if (debugEnabled) {
logger.debug("Creating new transaction with name [" + definition.getName() + "]: " + definition);
}
try {
boolean newSynchronization = (getTransactionSynchronization() != SYNCHRONIZATION_NEVER);
DefaultTransactionStatus status = newTransactionStatus(
definition, transaction, true, newSynchronization, debugEnabled, suspendedResources);
//根据transacion去begin,这里面会创建connection,并放到connectionHolder里面
doBegin(transaction, definition);
//再放入TransactionSynchronizationManager里面的ThreadLocal对象中,跟线程绑定起来
prepareSynchronization(status, definition);
return status;
}
catch (RuntimeException | Error ex) {
resume(null, suspendedResources);
throw ex;
}
}
else {
// Create "empty" transaction: no actual transaction, but potentially synchronization.
if (definition.getIsolationLevel() != TransactionDefinition.ISOLATION_DEFAULT && logger.isWarnEnabled()) {
logger.warn("Custom isolation level specified but no actual transaction initiated; " +
"isolation level will effectively be ignored: " + definition);
}
boolean newSynchronization = (getTransactionSynchronization() == SYNCHRONIZATION_ALWAYS);
return prepareTransactionStatus(definition, null, true, newSynchronization, debugEnabled, null);
}
}
像doGetTransaction(), doBegin()这种方法都是由AbstractPlatformTransactionManager的实现类提供,比如DataSourceTransactionManager。
@Override
protected Object doGetTransaction() {
//DataSourceTransactionObject是transaction,里面放了connectionHolder,即connection
DataSourceTransactionObject txObject = new DataSourceTransactionObject();
txObject.setSavepointAllowed(isNestedTransactionAllowed());
ConnectionHolder conHolder =
(ConnectionHolder)
//这里从ThreadLocal对象中获取当前线程关联的connection
TransactionSynchronizationManager.getResource(obtainDataSource());
txObject.setConnectionHolder(conHolder, false);
return txObject;
}
@Override
protected boolean isExistingTransaction(Object transaction) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) transaction;
//如果DataSourceTransactionObject的里面存在connectionHolder,表示当前线程已经存在transaction。
return (txObject.hasConnectionHolder() && txObject.getConnectionHolder().isTransactionActive());
}
/**
* This implementation sets the isolation level but ignores the timeout.
*/
@Override
protected void doBegin(Object transaction, TransactionDefinition definition) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) transaction;
Connection con = null;
try {
//如果不存在connectionHolder,表示是新的
if (!txObject.hasConnectionHolder() ||
txObject.getConnectionHolder().isSynchronizedWithTransaction()) {
//通过DataSource去获取一个新的connection
Connection newCon = obtainDataSource().getConnection();
//并且放到DataSourceTransactionObject里面
txObject.setConnectionHolder(new ConnectionHolder(newCon), true);
}
txObject.getConnectionHolder().setSynchronizedWithTransaction(true);
con = txObject.getConnectionHolder().getConnection();
Integer previousIsolationLevel = DataSourceUtils.prepareConnectionForTransaction(con, definition);
txObject.setPreviousIsolationLevel(previousIsolationLevel);
// Switch to manual commit if necessary. This is very expensive in some JDBC drivers,
// so we don't want to do it unnecessarily (for example if we've explicitly
// configured the connection pool to set it already).
//这里关闭自动提交
if (con.getAutoCommit()) {
txObject.setMustRestoreAutoCommit(true);
if (logger.isDebugEnabled()) {
logger.debug("Switching JDBC Connection [" + con + "] to manual commit");
}
con.setAutoCommit(false);
}
prepareTransactionalConnection(con, definition);
txObject.getConnectionHolder().setTransactionActive(true);
int timeout = determineTimeout(definition);
if (timeout != TransactionDefinition.TIMEOUT_DEFAULT) {
txObject.getConnectionHolder().setTimeoutInSeconds(timeout);
}
// Bind the connection holder to the thread.
//如果是新创建的connection,就将当前DataSource和connection组成一个map放到ThreadLocal对象中,与当前线程绑定。
if (txObject.isNewConnectionHolder()) {
TransactionSynchronizationManager.bindResource(obtainDataSource(), txObject.getConnectionHolder());
}
}
catch (Throwable ex) {
if (txObject.isNewConnectionHolder()) {
DataSourceUtils.releaseConnection(con, obtainDataSource());
txObject.setConnectionHolder(null, false);
}
throw new CannotCreateTransactionException("Could not open JDBC Connection for transaction", ex);
}
}
@Override
protected Object doSuspend(Object transaction) {
DataSourceTransactionObject txObject = (DataSourceTransactionObject) transaction;
//挂起当前线程就是将connectionHolder设置为null,并且将当前线程里的DataSource对应的connection解除绑定并返回当前的connection。
txObject.setConnectionHolder(null);
return TransactionSynchronizationManager.unbindResource(obtainDataSource());
}
//将前面doSuspend返回的被挂起的connection重新跟DataSource绑定关系放入ThreadLocal中
@Override
protected void doResume(@Nullable Object transaction, Object suspendedResources) {
TransactionSynchronizationManager.bindResource(obtainDataSource(), suspendedResources);
}
@Override
//通过connection做commit
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 {
con.commit();
}
catch (SQLException ex) {
throw new TransactionSystemException("Could not commit JDBC transaction", ex);
}
}
//通过connection做rollback
@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 {
con.rollback();
}
catch (SQLException ex) {
throw new TransactionSystemException("Could not roll back JDBC transaction", ex);
}
}
可以看transactionStatus在doBegin()之前和之后的区别:DataSourceTransactionManager会通过DataSource创建新的connection放入DataSourceTransactionObject,即transaction里
doBegin之前 doBegin之后最后TransactionInfo里面包含了Transaction的所有信息,包括TransactionManager,TransactionAttribute,TransactionStatus
TransactionInfo
JdbcTemplate
在JdbcTemplate里面主要是通过connection创建statement,执行sql最后释放connection的过程
public <T> T execute(StatementCallback<T> action) throws DataAccessException {
Assert.notNull(action, "Callback object must not be null");
//这里就是从TransactionSynchronizationManager里的ThreadLocal对象通过DataSource找到并获取connection的
Connection con = DataSourceUtils.getConnection(obtainDataSource());
Statement stmt = null;
try {
stmt = con.createStatement();
applyStatementSettings(stmt);
T result = action.doInStatement(stmt);
handleWarnings(stmt);
return result;
}
catch (SQLException ex) {
// Release Connection early, to avoid potential connection pool deadlock
// in the case when the exception translator hasn't been initialized yet.
String sql = getSql(action);
JdbcUtils.closeStatement(stmt);
stmt = null;
DataSourceUtils.releaseConnection(con, getDataSource());
con = null;
throw translateException("StatementCallback", sql, ex);
}
finally {
JdbcUtils.closeStatement(stmt);
//这里releaseconnection还是要看后面连接池的实现,而不是真正close了
DataSourceUtils.releaseConnection(con, getDataSource());
}
}
在jdbcTemplate做完业务逻辑之后就到了invokeWithinTransaction.commitTransactionAfterReturning(txInfo);来通过TransactionManager来做commit或者rollback,而且还涉及比如挂起的Transaction需要resume回去。
processCommit()里面也涉及很多模板方法,比如triggerAfterCompletion,triggerAfterCommi会invoke AfterCommit方法。
private void processCommit(DefaultTransactionStatus status) throws TransactionException {
try {
boolean beforeCompletionInvoked = false;
try {
boolean unexpectedRollback = false;
prepareForCommit(status);
triggerBeforeCommit(status);
triggerBeforeCompletion(status);
beforeCompletionInvoked = true;
if (status.hasSavepoint()) {
if (status.isDebug()) {
logger.debug("Releasing transaction savepoint");
}
unexpectedRollback = status.isGlobalRollbackOnly();
status.releaseHeldSavepoint();
}
else if (status.isNewTransaction()) {
if (status.isDebug()) {
logger.debug("Initiating transaction commit");
}
unexpectedRollback = status.isGlobalRollbackOnly();
//调用DataSourceTransactionManager的doCommit()方法做提交
doCommit(status);
}
else if (isFailEarlyOnGlobalRollbackOnly()) {
unexpectedRollback = status.isGlobalRollbackOnly();
}
// Throw UnexpectedRollbackException if we have a global rollback-only
// marker but still didn't get a corresponding exception from commit.
if (unexpectedRollback) {
throw new UnexpectedRollbackException(
"Transaction silently rolled back because it has been marked as rollback-only");
}
}
catch (UnexpectedRollbackException ex) {
// can only be caused by doCommit
triggerAfterCompletion(status, TransactionSynchronization.STATUS_ROLLED_BACK);
throw ex;
}
catch (TransactionException ex) {
// can only be caused by doCommit
if (isRollbackOnCommitFailure()) {
doRollbackOnCommitException(status, ex);
}
else {
triggerAfterCompletion(status, TransactionSynchronization.STATUS_UNKNOWN);
}
throw ex;
}
catch (RuntimeException | Error ex) {
if (!beforeCompletionInvoked) {
triggerBeforeCompletion(status);
}
doRollbackOnCommitException(status, ex);
throw ex;
}
// Trigger afterCommit callbacks, with an exception thrown there
// propagated to callers but the transaction still considered as committed.
try {
triggerAfterCommit(status);
}
finally {
triggerAfterCompletion(status, TransactionSynchronization.STATUS_COMMITTED);
}
}
finally {
cleanupAfterCompletion(status);
}
}
//最终的cleanup动作
private void cleanupAfterCompletion(DefaultTransactionStatus status) {
status.setCompleted();
if (status.isNewSynchronization()) {
TransactionSynchronizationManager.clear();
}
if (status.isNewTransaction()) {
doCleanupAfterCompletion(status.getTransaction());
}
if (status.getSuspendedResources() != null) {
if (status.isDebug()) {
logger.debug("Resuming suspended transaction after completion of inner transaction");
}
Object transaction = (status.hasTransaction() ? status.getTransaction() : null);
resume(transaction, (SuspendedResourcesHolder) status.getSuspendedResources());
}
}
网友评论