BeanDefinitionRegistryPostProcessor
首先BeanDefinitionRegistryPostProcessor ,这个类在动态注册Bean的时候用的很多,实际继承的是一个BeanFactoryPostProcessor接口,是一个Bean工厂的处理器,所以在容器启动时候最先加载。这两个接口一共有两个方法。这两个方法只会被执行一次,这个是容器级别接口,不管多少个Bean,一个实现只会执行一次。
public interface BeanDefinitionRegistryPostProcessor extends BeanFactoryPostProcessor {
void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry var1) throws BeansException;
}
public interface BeanFactoryPostProcessor {
void postProcessBeanFactory(ConfigurableListableBeanFactory var1) throws BeansException;
}
BeanPostProcessor
BeanPostProcessor 可以用来统一处理加载Bean
BeanPostProcessor 接口本身有两个方法,postProcessoBeforeInitialization 和postProcessAfterInitialization,如果是直接实现这个接口,postProcessorBeforeInitialization那么会在Bean属性注入和BeanNameAware、BeanFactoryAware执行之后,且在InitializingBean和init-method初始化方法之前执行;postProcessAfterInitialization在init-method初始化之后执行。在每一个Bean加载的前后都会执行before和after
public interface BeanPostProcessor {
Object postProcessBeforeInitialization(Object var1, String var2) throws BeansException;
Object postProcessAfterInitialization(Object var1, String var2) throws BeansException;
}
同时 BeanPostProcessor 这个接口在spring内部有几个实现类,进行了增强。
- 第一个实现类是 InstantiationAwareBeanPostProcessorAdapter (这个是Bean的后处理器适配器),里面方法主要有下面这几个,主要看前三个postProcessBeforeInstantiation,postProcessAfterInstantiation,postProcessPropertyValues后两个是来自父类顶级接口BeanPostProcessor ,后两个个执行顺序就跟上面一样。
前三个方法的执行顺序如下
实例化BeanFatorypostProcessor–>postProcessBeforeInstantiation --> postProcessPropertyValues -->bean构造方法–>postProcessAfterInstantiation - 第二个是MergedBeanDefinitionPostProcessor,这里面有个方法postProcessMergedBeanDefinition,会在postProcessBeforeInstantiation之后,postProcessPropertyValues 之前执行。
各个方法使用这里先不做介绍,这些方法提供灵活了扩展方法,可以灵活定义Bean生命周期过程中需要处理的事件,比如动态注入Bean,给Bean的参数进行校验
InstantiationAwareBeanPostProcessorAdapter.java
@Override
public Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException {
return null;
}
@Override
public boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
return true;
}
@Override
public PropertyValues postProcessPropertyValues(
PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {
return pvs;
}
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
测试代码:
写一个bean: Account.java
package com.beanpost;
import lombok.Data;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.*;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import javax.annotation.PostConstruct;
public class Account implements InitializingBean , BeanNameAware, BeanFactoryAware, ApplicationContextAware , DisposableBean {
public Account() {
System.out.println("执行 account 构造方法");
}
public void setName(String name) {
this.name = name;
System.out.println("执行===>setName方法");
}
public String getName() {
return name;
}
private String name;
@Override
public void afterPropertiesSet() throws Exception {
System.out.println("执行 InitializingBean");
}
@PostConstruct
public void iniitt(){
System.out.println("执行 PostConstruct");
}
public void init(){
System.out.println("执行 init 方法");
}
@Override
public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
System.out.println("执行 BeanFactoryAware");
}
@Override
public void setBeanName(String s) {
System.out.println("执行 BeanNameAware");
}
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
System.out.println("执行 ApplicationContextAware");
}
@Override
public void destroy() throws Exception {
System.out.println("执行 destroyBean方法");
}
public void destoryMothed(){
System.out.println("执行 destoryMothed 方法");
}
}
再写一个MyProcessor,
package com.beanpost;
import org.springframework.beans.BeansException;
import org.springframework.beans.PropertyValues;
import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.beans.factory.config.InstantiationAwareBeanPostProcessorAdapter;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor;
import org.springframework.beans.factory.support.MergedBeanDefinitionPostProcessor;
import org.springframework.beans.factory.support.RootBeanDefinition;
import java.beans.PropertyDescriptor;
public class MyPostProcessor extends InstantiationAwareBeanPostProcessorAdapter implements MergedBeanDefinitionPostProcessor, BeanDefinitionRegistryPostProcessor {
@Override
public void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry beanDefinitionRegistry) throws BeansException {
System.out.println("执行 postProcessBeanDefinitionRegistry");
}
@Override
public void postProcessBeanFactory(ConfigurableListableBeanFactory configurableListableBeanFactory) throws BeansException {
System.out.println("执行 postProcessBeanFactory ");
}
@Override
public void postProcessMergedBeanDefinition(RootBeanDefinition rootBeanDefinition, Class<?> aClass, String s) {
System.out.println("执行 postProcessMergedBeanDefinition(MergedBean!) ");
}
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
System.out.println("执行 beanPostprocessor before");
return bean;
}
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
System.out.println("执行 beanPostprocessor after");
return bean;
}
@Override
public Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException {
System.out.println("执行postProcessBeforeInstantiation (Before Instantiation) ");
return null;
}
@Override
public boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
System.out.println("执行 postProcessAfterInstantiation ( After Instantiation)");
return true;
}
@Override
public PropertyValues postProcessPropertyValues(PropertyValues pvs, PropertyDescriptor[] pds, Object bean, String beanName) throws BeansException {
System.out.println("执行 ==========》 postProcessPropertyValues");
return pvs;
}
}
启动之后,可以看到Bean生命周期中详细的执行顺序如下(黑色部分为常用的部分):
- 执行 postProcessBeanDefinitionRegistry(实例化BeanFactoryPostProcessor工厂后处理器,只执行一次)
- 执行 postProcessBeanFactory (只执行一次)
- 执行postProcessBeforeInstantiation (Before Instantiation) (来自InstantiationAwareBeanPostProcessorAdapter )
- 执行 account 构造方法(实例化Bean)
- 执行 postProcessMergedBeanDefinition(MergedBean) (来自MergedBeanDefinitionPostProcessor)
- 执行 postProcessAfterInstantiation ( After Instantiation)(来自InstantiationAwareBeanPostProcessorAdapter )
- 执行 ==========》 postProcessPropertyValues(来自InstantiationAwareBeanPostProcessorAdapter )
- (这里如果有属性注入,那么给属性初始化,也即是setter方法)
- 执行 BeanNameAware
- 执行 BeanFactoryAware
- 执行 ApplicationContextAware
- 执行 PostConstruct(PostConstruct本身也是通过BeanPostprocessor 接口实现)
- 执行 beanPostprocessor before (执行与BeanPostProcessor关联的postProcessBeforeInitialization(在属性初始化之后执行))
- 执行 InitializingBean ( 执行InitializingBean 中afterPropertiesSet 方法)
- 执行 init 方法 (执行init-method标记的方法)
- 执行 beanPostprocessor after(执行与BeanPostProcessor关联的postProcessAfterInitialization方法)
- 执行DiposableBean的destroy方法(优雅停机的时候会执行kill,暴力停机不会执行)
- 执行指定的destoryMothed方法
- 注意如果有一个类,是直接实现的是顶级接口BeanPostprocessor,那么这个类的postProcessBeforeInitialization会在PostConstruct之前执行。
个别详细的使用方法可以参考其他博文
autowire 的注入过程
bean的成员属性中,如果使用@autowire注入,那么其中原理是通过AutowiredAnnotationBeanPostProcessor,它实现了接口类MergedBeanDefinitionPostProcessor的方法postProcessMergedBeanDefinition,这个方法是合并我们定义类的信息,比如:一个类集成了其它类,这个方法会把父类属性和信息合并到子类中。
扫描代码,如果带有@Autowired注解,则将依赖注入信息封装到InjectionMetadata中,进一步注入到bean的属性
@Override
public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName) {
//查找类型为autowire注解的元信息,传入了bean的名称、类型
InjectionMetadata metadata = findAutowiringMetadata(beanName, beanType, null);
metadata.checkConfigMembers(beanDefinition);
}