面向切面編程AOP[四](java AnnotationAwareAspectJAutoProxyCreator與ioc的聯繫)

前言

拿出上一篇的內容:java

AnnotationAwareAspectJAutoProxyCreator
extends AspectJAwareAdvisorAutoProxyCreator
AspectJAwareAdvisorAutoProxyCreator extends AbstractAdvisorAutoProxyCreator
AbstractAdvisorAutoProxyCreator extends AbstractAutoProxyCreator
AbstractAutoProxyCreator extends ProxyProcessorSupport implements SmartInstantiationAwareBeanPostProcessor, BeanFactoryAware

正文

在這裏和ioc相關的有兩個東西一個是:app

SmartInstantiationAwareBeanPostProcessor,BeanFactoryAware

SmartInstantiationAwareBeanPostProcessor 表示bean 在注入容器先後作些什麼。

那麼聯繫AOP和 IOC 的聯繫,那麼就來分析繼承IOC的東西吧。post

在BeanFactoryAware 中:ui

public interface BeanFactoryAware extends Aware {
    void setBeanFactory(BeanFactory var1) throws BeansException;
}

那麼AbstractAutoProxyCreator 繼承它,確定會實現setBeanFactory。this

找到這個方法:code

public void setBeanFactory(BeanFactory beanFactory) {
        this.beanFactory = beanFactory;
    }

繼續往上看:
AbstractAdvisorAutoProxyCreator 看看是否有覆蓋setBeanFactory的東西。component

public void setBeanFactory(BeanFactory beanFactory) {
	super.setBeanFactory(beanFactory);
	if (!(beanFactory instanceof ConfigurableListableBeanFactory)) {
		throw new IllegalArgumentException("AdvisorAutoProxyCreator requires a ConfigurableListableBeanFactory: " + beanFactory);
	} else {
		this.initBeanFactory((ConfigurableListableBeanFactory)beanFactory);
	}
}

果真上面有覆蓋的東西。blog

異常的先不看,由於異常是細節,而後若是不出問題的話,那麼會執行:繼承

this.initBeanFactory((ConfigurableListableBeanFactory)beanFactory);接口

看下這個:initBeanFactory

protected void initBeanFactory(ConfigurableListableBeanFactory beanFactory) {
        this.advisorRetrievalHelper = new AbstractAdvisorAutoProxyCreator.BeanFactoryAdvisorRetrievalHelperAdapter(beanFactory);
    }

那麼繼續往上AspectJAwareAdvisorAutoProxyCreator ,這下看的就是是否覆蓋了setBeanFactory 或者initBeanFactory:

查到到其並無覆蓋。

繼續到最上層:AnnotationAwareAspectJAutoProxyCreator,發現覆蓋了initBeanFactory:

protected void initBeanFactory(ConfigurableListableBeanFactory beanFactory) {
	super.initBeanFactory(beanFactory);
	if (this.aspectJAdvisorFactory == null) {
		this.aspectJAdvisorFactory = new ReflectiveAspectJAdvisorFactory(beanFactory);
	}

	this.aspectJAdvisorsBuilder = new AnnotationAwareAspectJAutoProxyCreator.BeanFactoryAspectJAdvisorsBuilderAdapter(beanFactory, this.aspectJAdvisorFactory);
}

那麼好的,看斷點。
在AbstractAdvisorAutoProxyCreator:

在這裏不用猜,通常都是set進入的。

那麼看下在setFactory 以前作了什麼。

首先加載config。

AnnotationConfigApplicationContext applicationContext=new AnnotationConfigApplicationContext(MainConfigofAOP.class);

而後註冊組件:

public AnnotationConfigApplicationContext(Class<?>... componentClasses) {
	this();
	this.register(componentClasses);
	this.refresh();
}

this.refresh();
刷新容器。

看下刷新容器作了什麼。

記得在我上一個裏面,我寫道,AOP之因此與IOC 緊密掛鉤是由於,IOC 註冊容器的時候,AOP會監聽到。

那麼來看下refresh作了什麼。

public void refresh() throws BeansException, IllegalStateException {
        synchronized(this.startupShutdownMonitor) {
            this.prepareRefresh();
            ConfigurableListableBeanFactory beanFactory = this.obtainFreshBeanFactory();
            this.prepareBeanFactory(beanFactory);

            try {
                this.postProcessBeanFactory(beanFactory);
                this.invokeBeanFactoryPostProcessors(beanFactory);
                this.registerBeanPostProcessors(beanFactory);

this.registerBeanPostProcessors(beanFactory); 這個就是註冊了容器建立的後置處理器,也就是說在容器建立以前監聽,說白了就是攔截器。

看下里面是怎麼註冊的。

進入registerBeanPostProcessors進行處理:

for(int var10 = 0; var10 < var9; ++var10) {
            ppName = var8[var10];
            if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
                pp = (BeanPostProcessor)beanFactory.getBean(ppName, BeanPostProcessor.class);
                priorityOrderedPostProcessors.add(pp);
                if (pp instanceof MergedBeanDefinitionPostProcessor) {
                    internalPostProcessors.add(pp);
                }
            } else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
                orderedPostProcessorNames.add(ppName);
            } else {
                nonOrderedPostProcessorNames.add(ppName);
            }
        }

把之前註冊過的容器作一個處理:

若是實現接口 PriorityOrdered.class優先註冊。

而後是Ordered.class 註冊容器。

而後是註冊既沒有實現PriorityOrdered.class 和 Ordered.class的註冊容器。

前面把他們分完類以後,那麼就開始去註冊容器了,看下如何註冊容器的。

while(var14.hasNext()) {
            String ppName = (String)var14.next();
            BeanPostProcessor pp = (BeanPostProcessor)beanFactory.getBean(ppName, BeanPostProcessor.class);
            orderedPostProcessors.add(pp);
            if (pp instanceof MergedBeanDefinitionPostProcessor) {
                internalPostProcessors.add(pp);
            }
        }

註冊容器就是去getBean。

而後去執行:

if (mbd.isSingleton()) {
                    sharedInstance = this.getSingleton(beanName, () -> {
                        try {
                            return this.createBean(beanName, mbd, args);
                        } catch (BeansException var5) {
                            this.destroySingleton(beanName);
                            throw var5;
                        }
                    });
                    bean = this.getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
                }

經過createBean 去建立而後註冊到容器中。

createBean 裏面有一個:

beanInstance = this.doCreateBean(beanName, mbdToUse, args);

也就是有一個doCreateBean。

建立完bean 後而後執行:

this.populateBean(beanName, mbd, instanceWrapper);

也就是給屬性賦值。
而後初始化initializeBean:

exposedObject = this.initializeBean(beanName, exposedObject, mbd);

看下如何初始化Bean。
1.this.invokeAwareMethods(beanName, bean);
看下invokeAwareMethods 有什麼。

private void invokeAwareMethods(String beanName, Object bean) {
	if (bean instanceof Aware) {
		if (bean instanceof BeanNameAware) {
			((BeanNameAware)bean).setBeanName(beanName);
		}

		if (bean instanceof BeanClassLoaderAware) {
			ClassLoader bcl = this.getBeanClassLoader();
			if (bcl != null) {
				((BeanClassLoaderAware)bean).setBeanClassLoader(bcl);
			}
		}

		if (bean instanceof BeanFactoryAware) {
			((BeanFactoryAware)bean).setBeanFactory(this);
		}
	}

}

看一下這個註冊的bean 是否有Aware註解,setBeanFactory。而後就來到了,咱們斷點的地方。

當invokeAwareMethods執行完畢後:

wrappedBean = this.applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);

給方法增長監聽器,而後就ok了。

相關文章
相關標籤/搜索