/** * General delegate for around-advice-based subclasses, delegating to several other template * methods on this class. Able to handle {@link CallbackPreferringPlatformTransactionManager} * as well as regular {@link PlatformTransactionManager} implementations. * @param method the Method being invoked * @param targetClass the target class that we're invoking the method on * @param invocation the callback to use for proceeding with the target invocation * @return the return value of the method, if any * @throws Throwable propagated from the target invocation */ protected Object invokeWithinTransaction(Method method, Class<?> targetClass, final InvocationCallback invocation) throws Throwable {
// If the transaction attribute is null, the method is non-transactional. finalTransactionAttributetxAttr= getTransactionAttributeSource().getTransactionAttribute(method, targetClass); finalPlatformTransactionManagertm= determineTransactionManager(txAttr); finalStringjoinpointIdentification= methodIdentification(method, targetClass, txAttr);
if (txAttr == null || !(tm instanceof CallbackPreferringPlatformTransactionManager)) { // Standard transaction demarcation with getTransaction and commit/rollback calls. TransactionInfotxInfo= createTransactionIfNecessary(tm, txAttr, joinpointIdentification); ObjectretVal=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 { cleanupTransactionInfo(txInfo); } commitTransactionAfterReturning(txInfo); return retVal; }
else { // It's a CallbackPreferringPlatformTransactionManager: pass a TransactionCallback in. try { Objectresult= ((CallbackPreferringPlatformTransactionManager) tm).execute(txAttr, newTransactionCallback<Object>() { @Override public Object doInTransaction(TransactionStatus status) { TransactionInfotxInfo= 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 { thrownewThrowableHolderException(ex); } } else { // A normal return value: will lead to a commit. returnnewThrowableHolder(ex); } } finally { cleanupTransactionInfo(txInfo); } } });
// Check result: It might indicate a Throwable to rethrow. if (result instanceof ThrowableHolder) { throw ((ThrowableHolder) result).getThrowable(); } else { return result; } } catch (ThrowableHolderException ex) { throw ex.getCause(); } } }
获取事务属性,如果此项为空,则以非事务方式运行
根据事务属性获取事务管理器
创建TransactionInfo,后续操作事务时会用到。
调用业务逻辑。
如果捕捉到异常会在catch代码块中根据配置的事务信息继续处理事务。
finally代码块重置TransactionInfo信息。
如果没有异常提交事务。
spring 事务的关键是事务策略。定义在接口:org.springframework.transaction.PlatformTransactionManager