文章目录
BeanPostProcessor
,其中定义了两个方法,如下:ublic interface BeanPostProcessor {
/**
* 在Bean初始化之前执行,即是在执行Bean的构造方法之后,在执行InitializingBean的afterPropertiesSet方法之前执行
*/
Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException;
/**
* 在Bean的初始化之后执行,即是在InitializingBean的afterPropertiesSet方法之后执行
*/
Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException;
}
BeanPostProcessor
在Bean初始化之前进行调用set方法设置相应的属性【详情请看ApplicationContextAwareProcessor
源码】@Autowired
的实现依赖注入也是使用的BeanPostProcessor的原理,详情请看AutowiredAnnotationBeanPostProcessor
的源码BeanPostProcessor
接口,实现其中的方法/**
* 实现InitializingBean接口,定义初始化方法,在构造方法之后执行
*/
@Component
public class User implements Serializable, InitializingBean {
private String name;
private Integer age;
public User(){}
public User(String name, Integer age) {
System.out.println("执行构造方法");
this.name = name;
this.age = age;
}
@Override
public void afterPropertiesSet() throws Exception {
System.out.println("执行初始化方法,在构造方法执行之后执行");
}
}
/**
* 1、自定义的后置处理器,实现BeanPostProcessor
* 2、必须注入到容器中才能执行
* 3、后置处理器是每一个Bean实例化前后都会调用的,并不能指定某一个
*/
@Component
public class FirstPostProcessor implements BeanPostProcessor {
/**
* 在Bean初始化之前执行,即是在执行Bean的构造方法之后,在执行InitializingBean的afterPropertiesSet方法之前执行
* @param bean bean的对象
* @param beanName bean的名字,即是在ioc容器中的id
* @return 一定不能null
* @throws BeansException
*/
@Override
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
//如果这个Bean是User类型
if (bean instanceof User){
System.out.println("在User的初始化方法【afterPropertiesSet】之前执行");
//改变属性的值
User user=(User)bean;
user.setName("马云");
user.setAge(40);
}
return bean;
}
/**
* 在Bean的初始化之后执行,即是在InitializingBean的afterPropertiesSet方法之后执行
* @param bean bean的对象
* @param beanName bean的名字,即是在ioc容器中的id
* @return 一定不能null
* @throws BeansException
*/
@Override
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
if (bean instanceof User){
System.out.println("在User的初始化方法【afterPropertiesSet】之后执行");
}
return bean;
}
}
postProcessBeforeInitialization
在构造方法之后,初始化之前调用?postProcessAfterInitialization
在初始化之后调用?public class FirstConfigTest {
public AnnotationConfigApplicationContext applicationContext;
@Before
public void initApplicationContext() {
applicationContext = new AnnotationConfigApplicationContext(FirstConfig.class);
}
}
public AnnotationConfigApplicationContext(Class<?>... annotatedClasses)
: register(annotatedClasses)
:注入指定的配置类FirstConfig
refresh()
:刷新容器,在这个执行结束之后会完成Bean的加载,详情见第2步】org.springframework.context.support.AbstractApplicationContext#refresh
方法:prepareRefresh();
:在刷新容器之前做一些准备工作,比如设置激活状态【activate】,设置启动时间【startupDate】ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
refreshBeanFactory()
:刷新BeanFactory,如果之前存在了就删除创建新的,返回的是ConfigurableListableBeanFactory
类型的Bean工厂prepareBeanFactory(beanFactory);
:对新创建的Bean工厂设置一些属性配置ApplicationContextAwareProcessor
这个后置处理器到org.springframework.beans.factory.support.AbstractBeanFactory#beanPostProcessors
该成员变量中、去除一些不能自动注入的类【ResourceLoaderAware、ApplicationEventPublisherAware、MessageSourceAware、ApplicationContextAware、EnvironmentAware】,因为这些Aware类型的类需要后续自定义实现的@Autowired
直接注入使用ConfigurableEnvironment
、systemProperties(Map<String,Object>
其中存放的是配置参数)】,这些Bean可以直接自动注入使用invokeBeanFactoryPostProcessors(beanFactory)
:调用已经注册在容器中的BeanFactory后置处理器registerBeanPostProcessors(beanFactory)
:向ioc容器中注册BeanFactoryProcessorinitMessageSource()
:初始化MessageSourceinitApplicationEventMulticaster()
:初始化事件分发器registerListeners()
:注册事件监听器,用来监听事件finishBeanFactoryInitialization(beanFactory)
:初始化单例、非懒加载的Bean】,详情见步骤3finishRefresh()
:发布事件org.springframework.context.support.AbstractApplicationContext#finishBeanFactoryInitialization
:LoadTimeWeaverAware
,用于方法织入beanFactory.preInstantiateSingletons()
:初始化Bean,详情请看第4步】org.springframework.beans.factory.support.DefaultListableBeanFactory#preInstantiateSingletons
方法中,用于初始化Bean
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#initializeBean
,如下图所示,将是完整的逻辑,可以看出后置处理器为什么是在初始化之前和之后执行。
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#initializeBean
的方法中,主要的代码逻辑是在初始化之前调用对应的before方法,在之后调用after方法。