Spring源码分析三、Bean的后置处理器继承结构简单分析

1,078 阅读3分钟

BeanPostProcessor

/**
 * 最顶层的后置处理器, 可以看到参数是一个bean对象, 表示对一个bean对象的处理, 可以根据方法的名称看
 * 出, 这个后置处理器会在bean对象被创建后调用, 因为这两个方法的入参中是一个bean对象
 */
public interface BeanPostProcessor {
  default Object postProcessBeforeInitialization(Object bean, String beanName) {
		return bean;
	}

  default Object postProcessAfterInitialization(Object bean, String beanName) {
		return bean;
	}
}

InstantiationAwareBeanPostProcessor

/**
 * 该后置处理器继承了顶层的后置处理器, 并增加了几个方法, 可以根据bean的名称看出, 前两个方法分别是
 * 在bean被实例化之前和之后被调用, 而最后一个方法是用来处理属性的, 可以理解为对@Autowired注解的处理
 */
public interface InstantiationAwareBeanPostProcessor extends BeanPostProcessor {
  default Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) {
		return null;
	}

  default boolean postProcessAfterInstantiation(Object bean, String beanName) {
		return true;
	}

  default PropertyValues postProcessProperties(PropertyValues pvs, Object bean, String beanName) {
		return null;
	}
}

简单的总结

BeanPostProcessor的两个方法中before方法一般是用于在bean对象被创建后进行初始化动作的执行, 比如
@PostContructor注解以及InitializeBean接口的方法调用这样的处理, 所以前提是bean对象被创建了, 但是
after方法最为典型的应用就是AOP的实现了, Spring就是在after方法中完成AOP的实现的

InstantiationAwareBeanPostProcessor的前两个接口, 可以看到before方法是以beanClass作为参数的, 可
以认为此时bean对象还没被创建, 之所以提供这个方法是因为Spring提供了一个手段, 在真正创建bean之前会
调用这个before方法, 允许程序员对一个beanClass对象进行代理逻辑的编写, 换句话说, 如果这个方法返回了
一个对象, 说明这个逻辑是程序员自己编写的, 那么Spring就不会再走自己创建bean的逻辑了, 而after方法返
回的是一个boolean类型, 表示bean对象是否已经实例化完了

对于postProcessProperties方法, 是用来处理属性注入的, 比如@Autowired注解的处理

SmartInstantiationAwareBeanPostProcessor

public interface SmartInstantiationAwareBeanPostProcessor
        extends InstantiationAwareBeanPostProcessor {
  default Class<?> predictBeanType(Class<?> beanClass, String beanName) {
		return null;
	}

  default Constructor<?>[] determineCandidateConstructors(Class<?> beanClass, String beanName) {
		return null;
	}

  default Object getEarlyBeanReference(Object bean, String beanName) {
		return bean;
	}
}

分析:
  SmartInstantiationAwareBeanPostProcessor后置处理器继承了InstantiationAwareBeanPostProcessor
  并且提供了三个方法, predictBeanType方法用来预测bean的类型的, 因为一个beanDefinition中创建的bean
  并不一定是该定义中beanClass对应的对象, 比如FactoryBean的情况, determineCandidateConstructors
  方法用来在创建bean对象的时候推断构造方法的, 其实可以很容易的想到, 我们在创建bean对象的时候无非就
  是采用反射的方式来创建的, 那么一个对象可能有很多个构造方法, 在创建bean的时候到底采用哪个构造方法,
  则是由该后置处理器的determineCandidateConstructors方法来决定的, getEarlyBeanReference方法用于
  解决循环依赖的, 这一步的处理可以认为是循环依赖中的二级缓存, 在讲到循环依赖的时候我们会细讲这个实现

总结: bean的后置处理器接口中最为核心的就是这三个了, 当然还有其它的后置处理器接口, 但是那些相对而言 并不是那么的重要, Spring实例化bean主要是依靠这三个接口的实现类来进行的, 提前理解他们之间的关系有助于我们后面对bean实例化以及AOP的讲解