在Sping的整个生命周期中,有9个地方调用后置处理器。这些后置处理器是spring实现自定义功能或者扩展spring的核心所在
一、实例化前
该方法属于InstantiationAwareBeanPostProcessor
后置处理器
public interface InstantiationAwareBeanPostProcessor extends BeanPostProcessor {
@Nullable
default Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException {
return null;
}
default boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
return true;
}
@Nullable
default PropertyValues postProcessProperties(PropertyValues pvs, Object bean, String beanName)
throws BeansException {
return null;
}
@Deprecated
@Nullable
default PropertyValues postProcessPropertyValues(
PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {
return pvs;
}
}
该方法的意思其实也体现到名字上了,就是在实例化之前做些什么。
如果该方法返回非空,代表整个创建流程提前结束,也就是说后面什么属性设置,bean的初始化等等都不会执行了,所以重写该方法一定要谨慎。这个方法一般会和 applyBeanPostProcessorsAfterInitialization
后置结处理器结合使用,这个处理可是实现aop的核心,这个后面在分析。
protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
Object bean = null;
if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
// Make sure bean class is actually resolved at this point.
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
Class<?> targetType = determineTargetType(beanName, mbd);
if (targetType != null) {
bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
if (bean != null) {
bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
}
}
}
mbd.beforeInstantiationResolved = (bean != null);
}
return bean;
}
因为如果你在applyBeanPostProcessorsBeforeInstantiation
中返回非空后,后面spring的流程就不会走了,但是如果你有个切面是想代理这个类,那就没有办法了,所以applyBeanPostProcessorsBeforeInstantiation
返回非空后会调用applyBeanPostProcessorsAfterInitialization
执行aop代理
至于网上说的说法:
如果这里出现了aop的切面类,就会有InstantiationAwareBeanPostProcessor的子处理器进行类的过滤,出现@AspectJ的类标记为不需要代理的类,会被放入map中
我目前不理解,我自己写了一个切面类,结果还是和正常类走相同的流程。
二、实例bean前决定构造器
在createBeanInstance
中的方法determineConstructorsFromBeanPostProcessors
中会调用SmartInstantiationAwareBeanPostProcessor
后置处理器的determineCandidateConstructors
方法。
2.1 SmartInstantiationAwareBeanPostProcessor
该构造器主要就是为了预测最终bean的类型(predicting the eventual type of a processed bean)。
2.2 determineCandidateConstructors
该方法也是此处构造器的真正要做的事情。就是为了决定实例化bean的构造器
private DeptService service;
public DeptController(@Autowired DeptService service){
this.service = service;
}
比如这种情况,肯定不走默认的构造函数,spring就会在determineCandidateConstructors
中决定出这个有参数的构造器,然后创建实例的时候回检查参数是否有@Autowired的,在构造的时候就会把service给创建好
三、刚创建好实例之后
在createBeanInstance
之后,这个时候bean的属性、初始化方法等等都没有创建好,基本属于空白对象。然后在方法applyMergedBeanDefinitionPostProcessors
中执行类MergedBeanDefinitionPostProcessor
的后置处理
3.1 MergedBeanDefinitionPostProcessor
这个类主要用来更改或者丰富bean的定义的元数据信息。
3.2 方法postProcessMergedBeanDefinition
- CommonAnnotationBeanPostProcessor:这个是
MergedBeanDefinitionPostProcessor
一个重要的子类,在这个类中
public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName) {
super.postProcessMergedBeanDefinition(beanDefinition, beanType, beanName);//主要记录生命周期方法
InjectionMetadata metadata = findResourceMetadata(beanName, beanType, null);//记录@Resource metadata
metadata.checkConfigMembers(beanDefinition);
}
可见主要是为了后面的流程进行的一些辅助动作。
- AutowiredAnnotationBeanPostProcessor:另外一个重要的子类。
public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName) {
InjectionMetadata metadata = findAutowiringMetadata(beanName, beanType, null);//记录@AutoWired medata
metadata.checkConfigMembers(beanDefinition);
}
还是为了后面的流程进行的一些辅助动作。
四、解决循环依赖
protected Object getEarlyBeanReference(String beanName, RootBeanDefinition mbd, Object bean) {
Object exposedObject = bean;
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof SmartInstantiationAwareBeanPostProcessor) {
SmartInstantiationAwareBeanPostProcessor ibp = (SmartInstantiationAwareBeanPostProcessor) bp;
exposedObject = ibp.getEarlyBeanReference(exposedObject, beanName);
}
}
}
return exposedObject;
}
上面这段源码是在创建好bean后,如果开启了循环依赖,那么会执行
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
这个时候就来到了主角 getEarlyBeanReference
这里。
可见该后置处理器属于SmartInstantiationAwareBeanPostProcessor
,这里到底是做什么呢?
4.1 AbstractAutoProxyCreator
改具体子类实现了SmartInstantiationAwareBeanPostProcessor
接口。
public Object getEarlyBeanReference(Object bean, String beanName) {
Object cacheKey = getCacheKey(bean.getClass(), beanName);
this.earlyProxyReferences.put(cacheKey, bean);
return wrapIfNecessary(bean, beanName, cacheKey);
}
这个代码就是返回aop代码的代码。 所以该后置处理器有个功能就是返回aop的代理
五、实例化后
在属性填充方法populateBean
中
if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof InstantiationAwareBeanPostProcessor) {
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
continueWithPropertyPopulation = false;
break;
}
}
}
}
改后置处理器来自InstantiationAwareBeanPostProcessor
,调用其中的postProcessAfterInstantiation
改方法功能也简单,就是判断是否进行属性注入。
六 设置属性前
for (BeanPostProcessor bp : getBeanPostProcessors()) {
if (bp instanceof InstantiationAwareBeanPostProcessor) {
InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);
if (pvsToUse == null) {
if (filteredPds == null) {
filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
}
pvsToUse = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
if (pvsToUse == null) {
return;
}
}
pvs = pvsToUse;
}
}
改后置处理器用在 在工厂将给定的属性值应用到给定bean之前,对给定的属性值进行后处理。你可以进行一些检查,比如某个属性是 “required”的,但是这个属性需要的引用却是空,这个时候可以进行一些检查工作。还有dubbo的注解 @DubboReference这个注解,就是在此处 替换需要注入的类来实现的。
七 执行初始化方法前
if (mbd == null || !mbd.isSynthetic()) {
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
}
改代码是在方法initializeBean
中调用的。applyBeanPostProcessorsBeforeInitialization
详细调用是
public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
throws BeansException {
Object result = existingBean;
for (BeanPostProcessor processor : getBeanPostProcessors()) {
Object current = processor.postProcessBeforeInitialization(result, beanName);
if (current == null) {
return result;
}
result = current;
}
return result;
}
可以看到他的引用是接口BeanPostProcessor
这个接口属于顶级接口,他的子类太多了,其中有个出名的是CommonAnnotationBeanPostProcessor
该类的结构图是
其中他的父类InitDestroyAnnotationBeanPostProcessor
是个重点角色,在改类中的postProcessBeforeInitialization
方法中就执行了大名鼎鼎的 @PostConstruct
注解的方法。
八 执行初始化方法后
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
throws BeansException {
Object result = existingBean;
for (BeanPostProcessor processor : getBeanPostProcessors()) {
Object current = processor.postProcessAfterInitialization(result, beanName);
if (current == null) {
return result;
}
result = current;
}
return result;
}
鼎鼎大名的aop就是在这里进行实现的。具体的后置处理器是AbstractAutoProxyCreator
九 销毁bean容器的时候调用
具体后置处理器InitDestroyAnnotationBeanPostProcessor
然后调用的方法是postProcessBeforeDestruction
public void postProcessBeforeDestruction(Object bean, String beanName) throws BeansException {
LifecycleMetadata metadata = findLifecycleMetadata(bean.getClass());
try {
metadata.invokeDestroyMethods(bean, beanName);
}
catch (InvocationTargetException ex) {
String msg = "Destroy method on bean with name '" + beanName + "' threw an exception";
if (logger.isDebugEnabled()) {
logger.warn(msg, ex.getTargetException());
}
else {
logger.warn(msg + ": " + ex.getTargetException());
}
}
catch (Throwable ex) {
logger.warn("Failed to invoke destroy method on bean with name '" + beanName + "'", ex);
}
}
什么是destory方法呢,被javax.annotation.PreDestroy 注解的的方法。