搞懂aop二(自動代理基礎)
阿新 • • 發佈:2020-08-20
自動代理抽象:
public abstract class AbstractAutoProxyCreator extends ProxyProcessorSupport implements SmartInstantiationAwareBeanPostProcessor, BeanFactoryAware
這個利用spring 後置處理器來攔截bean建立,在bean的建立過程中,可以通過spring的後置處理器來處理bean的建立過程,SmartInstantiationAwareBeanPostProcessor是InstantiationAwareBeanPostProcessor BeanPostProcessor 的子介面,它的實現類有機會被spring在建立bean例項前後,例項化前後執行指定的方法。
@Override // bean 例項化前的攔截器 public Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) { Object cacheKey = getCacheKey(beanClass, beanName); if (!StringUtils.hasLength(beanName) || !this.targetSourcedBeans.contains(beanName)) { if (this.advisedBeans.containsKey(cacheKey)) {自動代理抽象的部分原始碼return null; } if (isInfrastructureClass(beanClass) || shouldSkip(beanClass, beanName)) { this.advisedBeans.put(cacheKey, Boolean.FALSE); return null; } } // Create proxy here if we have a custom TargetSource. // Suppresses unnecessary default instantiation of the target bean:// The TargetSource will handle target instances in a custom fashion. TargetSource targetSource = getCustomTargetSource(beanClass, beanName); if (targetSource != null) { if (StringUtils.hasLength(beanName)) { this.targetSourcedBeans.add(beanName); } Object[] specificInterceptors = getAdvicesAndAdvisorsForBean(beanClass, beanName, targetSource); Object proxy = createProxy(beanClass, beanName, specificInterceptors, targetSource); this.proxyTypes.put(cacheKey, proxy.getClass()); return proxy; } return null; } @Override // 初始化後的攔截器,可以返回一個新物件代替初始化後的物件 public Object postProcessAfterInitialization(@Nullable Object bean, String beanName) { if (bean != null) { Object cacheKey = getCacheKey(bean.getClass(), beanName); // 這個是判斷是否已經被代理過 if (this.earlyProxyReferences.remove(cacheKey) != bean) { // 這個是判斷是否需要包裝,並返回結果的方法 return wrapIfNecessary(bean, beanName, cacheKey); } } return bean; } // 具體的代理邏輯 protected Object wrapIfNecessary(Object bean, String beanName, Object cacheKey) { if (StringUtils.hasLength(beanName) && this.targetSourcedBeans.contains(beanName)) { return bean; } if (Boolean.FALSE.equals(this.advisedBeans.get(cacheKey))) { return bean; } if (isInfrastructureClass(bean.getClass()) || shouldSkip(bean.getClass(), beanName)) { this.advisedBeans.put(cacheKey, Boolean.FALSE); return bean; } // Create proxy if we have advice. Object[] specificInterceptors = getAdvicesAndAdvisorsForBean(bean.getClass(), beanName, null); if (specificInterceptors != DO_NOT_PROXY) { this.advisedBeans.put(cacheKey, Boolean.TRUE); Object proxy = createProxy( bean.getClass(), beanName, specificInterceptors, new SingletonTargetSource(bean)); this.proxyTypes.put(cacheKey, proxy.getClass()); return proxy; } this.advisedBeans.put(cacheKey, Boolean.FALSE); return bean; }
使用示例:
/** * @author liangjunhui * @date Created in 2020-08-20 9:09 */ @Configuration public class MyBeanNameApc { @Bean public MethodBeforeAdvice methodBeforeAdvice(){ MethodBeforeAdvice beforeAdvice = (method, args, target) -> System.out.println("前置增強"); return beforeAdvice; } @Bean public BeanNameAutoProxyCreator beanNameAutoProxyCreator(){ BeanNameAutoProxyCreator creator = new BeanNameAutoProxyCreator(); creator.setBeanNames("*ultar"); creator.setInterceptorNames("methodBeforeAdvice"); return creator; } @Bean public Mathcalcultar mathcalcultar(){ return new Mathcalcultar(); } public static void main(String[] args) { AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(MyBeanNameApc.class); Mathcalcultar bean = context.getBean(Mathcalcultar.class); bean.div(1,1); } }MyBeanNameApc
1、將AbstractAutoProxyCreator例項注入到容器,這個例項會攔截bean的建立
2、然後看AbstractAutoProxyCreator#getAdvicesAndAdvisorsForBean在子類的實現,按照子類的匹配規則設定一些資料來,然後apc判斷是否需要產生代理