本篇将分析bean的初始化过程,难度不大。进入正题。。。
org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#initializeBean
protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {
// 这里有个条件判断,但逻辑都是调用invokeAwareMethods方法,看看里面做了什么
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction
AbstractAutowireCapableBeanFactory#invokeAwareMethods
实现了各类型的aware接口,赋值。
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 = getBeanClassLoader();
if (bcl != null) {
((BeanClassLoaderAware) bean).setBeanClassLoader(bcl);
}
}
if (bean instanceof BeanFactoryAware) {
((BeanFactoryAware) bean).setBeanFactory(AbstractAutowireCapableBeanFactory.this);
}
}
}
第二步:执行初始化前处理器
之后调用了BeanPostProcessor的postProcessBeforeInitialization方法。
Object wrappedBean = bean;
if (mbd == null || !mbd.isSynthetic()) {
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
}
目前容器中有跟多BeanPostProcessor,有两个重要的需要看下
ApplicationContextAwareProcessor#postProcessBeforeInitialization
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
if (!(bean instanceof EnvironmentAware || bean instanceof EmbeddedValueResolverAware ||
bean instanceof ResourceLoaderAware || bean instanceof ApplicationEventPublisherAware ||
bean instanceof MessageSourceAware || bean instanceof ApplicationContextAware ||
bean instanceof ApplicationStartupAware)) {
return bean;
}
AccessControlContext acc = null;
if (System.getSecurityManager() != null) {
acc = this.applicationContext.getBeanFactory().getAccessControlContext();
}
if (acc != null) {
AccessController.doPrivileged((PrivilegedAction
发现拓展了aware接口,同样是赋值。
CommonAnnotationBeanPostProcessor#postProcessBeforeInitialization
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
// 找到声明周期方法即,@PostConstruct,@PreDestroy标注的方法,这里的逻辑不做详细分析了。
LifecycleMetadata metadata = findLifecycleMetadata(bean.getClass());
try {
// 执行注解PostConstruct标注的方法。
metadata.invokeInitMethods(bean, beanName);
}
catch (InvocationTargetException ex) {
throw new BeanCreationException(beanName, "Invocation of init method failed", ex.getTargetException());
}
catch (Throwable ex) {
throw new BeanCreationException(beanName, "Failed to invoke init method", ex);
}
return bean;
}
初始化前处理器主要做两项工作,1.给其他的aware接口赋值;2. 调用注解PostConstruct标注的方法。
第三步:执行初始化方法
try {
invokeInitMethods(beanName, wrappedBean, mbd);
}
catch (Throwable ex) {
throw new BeanCreationException(
(mbd != null ? mbd.getResourceDescription() : null),
beanName, "Invocation of init method failed", ex);
}
protected void invokeInitMethods(String beanName, Object bean, @Nullable RootBeanDefinition mbd)
throws Throwable {
// 如果这个bean实现了InitializingBean,将调用afterPropertiesSet方法
boolean isInitializingBean = (bean instanceof InitializingBean);
if (isInitializingBean && (mbd == null || !mbd.isExternallyManagedInitMethod("afterPropertiesSet"))) {
if (logger.isTraceEnabled()) {
logger.trace("Invoking afterPropertiesSet() on bean with name '" + beanName + "'");
}
if (System.getSecurityManager() != null) {
try {
AccessController.doPrivileged((PrivilegedExceptionAction
主要是调用初始化方法,实现了InitializingBean接口的调用afterPropertiesSet方法,有指定init-method的再调用指定的方法。
第四步:调用初始化后处理器
if (mbd == null || !mbd.isSynthetic()) {
wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
这个比较重要的当属AbstractAutoProxyCreator#postProcessAfterInitialization,用来创建代理的。
总结理清方法执行的顺序
- 先给aware接口赋值
- bean处理器的初始化前处理方法:因为InitDestroyAnnotationBeanPostProcessor实现了PriorityOrdered接口,所以先加载,也就是说现实执行@PostConstruct方法,之后再执行拓展的Aware接口方法
- 执行初始化方法afterPropertiesSet,如果设置了init-method,在执行设置的方法。
- 最后是初始化后处理器的方法
bean的初始化顺序参考Spring Bean的生命周期(非常详细),本篇的分析过程可以涵盖为Bean注入属性之后的过程。
初始化调用顺序:
- @PostConstruct方法
- spring的初始化接口的afterPropertiesSet方法
- xml配置文件bean标签设置的init-method方法
销毁顺序:则是跟上面的相同
- @PreDestroy注解标注的方法
- DisposableBean回调接口定义的destroy()
- xml配置文件的destroy-method方法



