回顾
在spring源码系列9:事务代理的创建一节, 事务通过定义
- 切点: TransactionAttributeSourcePointcut 、
- 通知(拦截器) TransactionInterceptor
- Advisor: BeanFactoryTransactionAttributeSourceAdvisor
在AOP基础上实现事务代理的功能
在spring源码系列10:AOP代理对象的执行一节。 总结出,不管是AOP-JDK代理还是CGLB动态代理,都会执行Advice完成增强功能。
也就是说:事务的核心功能就在这个TransactionInterceptor
事务执行
TransactionInterceptor
@Override public Object invoke(final MethodInvocation invocation) throws Throwable { // Work out the target class: may be {@code null}. // The TransactionAttributeSource should be passed the target class // as well as the method, which may be from an interface. 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(); } }); }
交给父类TransactionAspectSupport.invokeWithinTransaction()
去执行
TransactionAspectSupport
invokeWithinTransaction方法比较长,我们看前半部分。
protected Object invokeWithinTransaction(Method method, Class<?> targetClass, final InvocationCallback invocation) throws Throwable { // If the transaction attribute is null, the method is non-transactional. 1. final TransactionAttribute txAttr = getTransactionAttributeSource().getTransactionAttribute(method, targetClass); 2. final PlatformTransactionManager tm = determineTransactionManager(txAttr); 3. final String joinpointIdentification = methodIdentification(method, targetClass, txAttr); if (txAttr == null || !(tm instanceof CallbackPreferringPlatformTransactionManager)) { // Standard transaction demarcation with getTransaction and commit/rollback calls. 4. 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. 5. retVal = invocation.proceedWithInvocation(); } catch (Throwable ex) { // target invocation exception 6. completeTransactionAfterThrowing(txInfo, ex); throw ex; } finally { 7. cleanupTransactionInfo(txInfo); } 8. commitTransactionAfterReturning(txInfo); return retVal; } ... }
1.拿到事务属性TransactionAttribute :
我们使用注解@Transactional时,注解元信息会被包装成TransactionAttribute ,此处拿到的就是@Transactional的元数据
2.determineTransactionManager(txAttr)
找到一个合适的事务管理器
protected PlatformTransactionManager determineTransactionManager(TransactionAttribute txAttr) { // Do not attempt to lookup tx manager if no tx attributes are set //未设置事务属性,也没有设置beanFactory ,直接返回 if (txAttr == null || this.beanFactory == null) { return getTransactionManager(); } //如果@Transactional 指定了具体事务管理器,则根据beanname去容器中找到他 String qualifier = txAttr.getQualifier(); if (StringUtils.hasText(qualifier)) { return determineQualifiedTransactionManager(qualifier); } //如果是TransactionAspectSupport.transactionManagerBeanName指定了具体事务管理器, //beanname去容器中找 else if (StringUtils.hasText(this.transactionManagerBeanName)) { return determineQualifiedTransactionManager(this.transactionManagerBeanName); } //没有beanName指定具体的事务管理器Bean。 /** 1.查看transactionManager属性是否设置事务管理器对象 2.查看事务管理器缓存中有没有 3.去容器中寻找,找PlatformTransactionManager接口的实现类。getBean(PlatformTransactionManager), 找到放到事务管理器缓存中。 **/ else { PlatformTransactionManager defaultTransactionManager = getTransactionManager(); if (defaultTransactionManager == null) { defaultTransactionManager = this.transactionManagerCache.get(DEFAULT_TRANSACTION_MANAGER_KEY); if (defaultTransactionManager == null) { defaultTransactionManager = this.beanFactory.getBean(PlatformTransactionManager.class); this.transactionManagerCache.putIfAbsent( DEFAULT_TRANSACTION_MANAGER_KEY, defaultTransactionManager); } } return defaultTransactionManager; } }
以集成了DataSourceTransactionManager为例。determineTransactionManager返回的就是DataSourceTransactionManager对象。
3.methodIdentification方法
获取目标方法全名
4.createTransactionIfNecessary开启事务(重点)
protected TransactionInfo createTransactionIfNecessary( PlatformTransactionManager tm, TransactionAttribute txAttr, final String joinpointIdentification) { // If no name specified, apply method identification as transaction name. 如果事务名称没有指定,则使用方法名作为事务名 if (txAttr != null && txAttr.getName() == null) { txAttr = new DelegatingTransactionAttribute(txAttr) { @Override public String getName() {return joinpointIdentification;} }; } ... TransactionStatus status = tm.getTransaction(txAttr); ... return prepareTransactionInfo(tm, txAttr, joinpointIdentification, status); }
重点在
- getTransaction方法获取TransactionStatus 事务
- prepareTransactionInfo方法上,封装一个TransactionInfo
4.1:getTransaction ()
getTransaction ()是一个模板方法,PlatformTransactionManager定义了getTransaction 方法。抽象类AbstractPlatformTransactionManager实现了getTransaction 方法。因为是模板方法。方法内很多方法都是在具体的PlatformTransactionManager实现的。(本文以DataSourceTransactionManager为例)
public final TransactionStatus getTransaction(TransactionDefinition definition) throws TransactionException { 1.尝试获取事务对象,并封装当前线程中以当前datasource为key的Connection。 Object transaction = doGetTransaction(); 2.没有配置事务属性,则创建一个默认的事务属性 if (definition == null) { // Use defaults if no transaction definition given. definition = new DefaultTransactionDefinition(); } 3.判断是否有已经存在是否:判断条件是当前线程有Connection.并且Connection是活跃的 if (isExistingTransaction(transaction)) { // Existing transaction found -> check propagation behavior to find out how to behave. 已存在事务,则处理传播属性,然后返回。(处理两个事务之间的传播属性关系) return handleExistingTransaction(definition, transaction, debugEnabled); } ===========当前没有事务 // Check definition settings for new transaction. 4.超时时间校验 if (definition.getTimeout() < TransactionDefinition.TIMEOUT_DEFAULT) { throw new InvalidTimeoutException("Invalid transaction timeout", definition.getTimeout()); } 5.开始处理当前事务 // 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'"); } else if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRED || definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRES_NEW || definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NESTED) { 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); doBegin(transaction, definition); prepareSynchronization(status, definition); return status; } catch (RuntimeException ex) { resume(null, suspendedResources); throw ex; } catch (Error err) { resume(null, suspendedResources); throw err; } } 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); } }
下面拆解此方法