Spring初始化过程到AOP

初始化过程

	public void refresh() throws BeansException, IllegalStateException {
		synchronized (this.startupShutdownMonitor) {
			// Prepare this context for refreshing.
			prepareRefresh();
			// Tell the subclass to refresh the internal bean factory.
			ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
			// Prepare the bean factory for use in this context.
			prepareBeanFactory(beanFactory);
			try {
				// Allows post-processing of the bean factory in context subclasses.
				postProcessBeanFactory(beanFactory);
				// Invoke factory processors registered as beans in the context.
				invokeBeanFactoryPostProcessors(beanFactory);
				// Register bean processors that intercept bean creation.
				registerBeanPostProcessors(beanFactory);
				// Initialize message source for this context.
				initMessageSource();
				// Initialize event multicaster for this context.
				initApplicationEventMulticaster();
				// Initialize other special beans in specific context subclasses.
				onRefresh();
				// Check for listener beans and register them.
				registerListeners();
				// Instantiate all remaining (non-lazy-init) singletons.
				finishBeanFactoryInitialization(beanFactory);
				// Last step: publish corresponding event.
				finishRefresh();
			}
            // ...
	}

ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory()
-> AbstractRefreshableApplicationContext#refreshBeanFactory() get a beanFactory(DefaultListableBeanFactory)
-> loadBeanDefinitions(beanFactory)
-> AbstractXmlApplicationContext#loadBeanDefinitions, XmlBeanDefinitionReader, loadBeanDefinition...(not yet instantiate)

registerBeanPostProcessors(beanFactory)
-> 注册BPP,其中就包含AOP的BPPAbstractAutoProxyCreator,注意BPP是not-lazy-init的

finishBeanFactoryInitialization(beanFactory); 实例化非lazy-init的bean
-> DefaultListableDeanFactory#preInstantiateSingletons() -> getBean(beanName)
-> AbstractBeanFactory#getBean(beanName) -> doGetBean(name, null, null, false) -> getSingleton -> createBean
-> AbstractAutowiredCapableBeanFactory#createBean -> doCreateBean -> populateBean -> initializeBean -> applyBeanPostProcessorsBeforeInitialization -> invokeInitMethods -> applyBeanPostProcessorsAfterInitialization -> getBeanPostProcessors() 然后对每个bean挨个调用bpp的postProcessAfterInitialization方法,对于AOP,在其中就会有判定是否需要包装、是否需要生成代理等操作,最后生成一个代理(这部分就是AOP的代码了)

AOP创建代理

Spring默认会加载AbstractAutoProxyCreator这个Bean(是一个BPP)
AbstractAutoProxyCreator#postProcessAfterInitialization -> wrapIfNecessary

	protected Object wrapIfNecessary(Object bean, String beanName, Object cacheKey) {
		if (beanName != null && 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;
	}

getAdvicesAndAdvisorsForBean方法找到所有的拦截器,调用createProxy方法生成代理。
生成Advisor[]设置到ProxyFactory中,然后调用ProxyFactory#getProxy方法获取代理(JdkDynamicAopProxy和CglibAopProxy)。其中在生成Advisors是一个表复杂的过程,涉及匹配切点、包装生成通知(AspectJPointcutAdvisor.)

ProxyFactor extends ProxyCreatorSupport extends AdvisedSupport

	protected final synchronized AopProxy createAopProxy() {
		if (!this.active) {
			activate();
		}
		return getAopProxyFactory().createAopProxy(this);
	}

ProxyFactory以自身为参数,因为把Advisors设置进去了,生成代理时就可以拿到了。生成AopProxyCglibAopProxy或者JdkDynamicAopProxy的构造参数需要AdvisedSupport)。
对于不需要包装(拦截)的方法,有一个拦截器是ExposeInvocationInterceptor
在代理的invoke方法里,会先从AdvisedSupport中获取到拦截器链,最后包装成一个MethodInvocationReflectiveMethodInvocation)调用其proceed方法。
关键是proceed这个方法,会递归调用其中每一个interceptor,这里的this就是ReflectiveMethodInvocation,然后在interceptor的invoke方法里,有前置/后置/环绕等逻辑,或者没有逻辑(ExposeInvocationInterceptor是第一个拦截器),参数是MethodInvocation,然后再调用mi的proceed方法,回到ReflectiveMethodInvocation中继续处理,拦截器链调完之后就会反射调用返回。此处有点绕,需要多看几遍代码。

return ((MethodInterceptor) interceptorOrInterceptionAdvice).invoke(this);

拦截器接口InvocationInterceptor,前置后置等逻辑都实现了该接口。
AspectJAfterAdvice
MethodBeforeAdviceInterceptor
AspectJAroundAdvice
等等

posted @ 2018-06-24 11:09  鲁大喵  阅读(457)  评论(0)    收藏  举报