spring bean的初始化
常用的spring bean的初始化方法有以下四种:
(1)@PostConstruct注解的方法;
(2)类实现了InitializingBean接口,实现了afterPropertiesSet方法;
(3)通过XML配置文件在<bean>标签中的init-method属性指定初始化方法,或者@Bean的initMethod属性指定的方法,如@Bean(initMethod = "init"),其中init是一个方法;
(4)还可以自定义后置处理器实现BeanPostProcessor接口,重写postProcessBeforeInitialization方法实现初始化。
以上这四种初始化方法如果在一个类上同时使用,执行顺序是(4)>(1)>(2)>(3)。
使用@PostConstruct注解的初始化方法是通过CommonAnnotationBeanPostProcessor 后置处理器调用的,其实是通过父类InitDestroyAnnotationBeanPostProcessor的postProcessBeforeInitialization方法调用的,InitDestroyAnnotationBeanPostProcessor类实现了MergedBeanDefinitionPostProcessor接口,MergedBeanDefinitionPostProcessor接口继承了BeanPostProcessor接口。
@PostConstruct注解的方法是在invokeInitMethods方法之前执行的,afterPropertiesSet方法和init-method属性指定的方法都是在invokeInitMethods方法中执行的。
调用AbstractAutowireCapableBeanFactory类的doCreateBean方法创建bean:
protected Object doCreateBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) throws BeanCreationException {
BeanWrapper instanceWrapper = null;
if (mbd.isSingleton()) {
instanceWrapper = (BeanWrapper)this.factoryBeanInstanceCache.remove(beanName);
}
if (instanceWrapper == null) {
//推断出构造函数,通过构造函数反射创建bean实例
instanceWrapper = this.createBeanInstance(beanName, mbd, args);
}
Object bean = instanceWrapper.getWrappedInstance();
Class<?> beanType = instanceWrapper.getWrappedClass();
if (beanType != NullBean.class) {
mbd.resolvedTargetType = beanType;
}
Object var7 = mbd.postProcessingLock;
synchronized(mbd.postProcessingLock) {
if (!mbd.postProcessed) {
try {
//通过不同的后置处理器完成对相应注解的扫描工作,并将相关的可用方法或其它有用信息进行缓存
this.applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
} catch (Throwable var17) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Post-processing of merged bean definition failed", var17);
}
mbd.postProcessed = true;
}
}
//如果是单例、允许循环依赖且正在创建中,则提前暴露一个工厂ObjectFactory<?> singletonFactory
boolean earlySingletonExposure = mbd.isSingleton() && this.allowCircularReferences && this.isSingletonCurrentlyInCreation(beanName);
if (earlySingletonExposure) {
this.addSingletonFactory(beanName, () -> {
return this.getEarlyBeanReference(beanName, mbd, bean);
});
}
Object exposedObject = bean;
try {
//属性注入
this.populateBean(beanName, mbd, instanceWrapper);
//初始化bean
exposedObject = this.initializeBean(beanName, exposedObject, mbd);
} catch (Throwable var18) {
//省略无关代码
}
//省略其他无关代码
}
调用AbstractAutowireCapableBeanFactory类的initializeBean方法完成bean的初始化:
protected Object initializeBean(String beanName, Object bean, @Nullable RootBeanDefinition mbd) {
if (System.getSecurityManager() != null) {
AccessController.doPrivileged(() -> {
this.invokeAwareMethods(beanName, bean);
return null;
}, this.getAccessControlContext());
} else {
this.invokeAwareMethods(beanName, bean);
}
Object wrappedBean = bean;
if (mbd == null || !mbd.isSynthetic()) {
// 1、bean初始化之前调用postProcessBeforeInitialization方法
wrappedBean = this.applyBeanPostProcessorsBeforeInitialization(bean, beanName);
}
try {
// 2、bean的初始化
this.invokeInitMethods(beanName, wrappedBean, mbd);
} catch (Throwable var6) {
throw new BeanCreationException(mbd != null ? mbd.getResourceDescription() : null, beanName, "Invocation of init method failed", var6);
}
if (mbd == null || !mbd.isSynthetic()) {
// 3、bean初始化之后调用postProcessAfterInitialization方法
wrappedBean = this.applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
return wrappedBean;
}
1、bean初始化之前
bean初始化之前调用postProcessBeforeInitialization方法。如果类中有@PostConstruct注解的方法,该方法就是初始化方法。当processor为CommonAnnotationBeanPostProcessor时调用@PostConstruct注解的方法,但是该类未实现postProcessBeforeInitialization回调方法,因此直接调用父类InitDestroyAnnotationBeanPostProcessor的postProcessBeforeInitialization方法。
public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName) throws BeansException {
Object result = existingBean;
Object current;
for(Iterator var4 = this.getBeanPostProcessors().iterator(); var4.hasNext(); result = current) {
BeanPostProcessor processor = (BeanPostProcessor)var4.next();
// 调用父类InitDestroyAnnotationBeanPostProcessor的postProcessBeforeInitialization方法
current = processor.postProcessBeforeInitialization(result, beanName);
if (current == null) {
return result;
}
}
return result;
}
public class CommonAnnotationBeanPostProcessor extends InitDestroyAnnotationBeanPostProcessor
implements InstantiationAwareBeanPostProcessor, BeanFactoryAware, Serializable
InitDestroyAnnotationBeanPostProcessor类实现了MergedBeanDefinitionPostProcessor接口,MergedBeanDefinitionPostProcessor接口继承了BeanPostProcessor接口。
InitDestroyAnnotationBeanPostProcessor类的部分代码如下所示:
public class InitDestroyAnnotationBeanPostProcessor implements DestructionAwareBeanPostProcessor, MergedBeanDefinitionPostProcessor, PriorityOrdered, Serializable {
protected transient Log logger = LogFactory.getLog(this.getClass());
private Class<? extends Annotation> initAnnotationType;
private Class<? extends Annotation> destroyAnnotationType;
private int order = 2147483647;
private final transient Map<Class<?>, InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata> lifecycleMetadataCache = new ConcurrentHashMap(256);
public InitDestroyAnnotationBeanPostProcessor() {
}
public void setInitAnnotationType(Class<? extends Annotation> initAnnotationType) {
this.initAnnotationType = initAnnotationType;
}
public void setDestroyAnnotationType(Class<? extends Annotation> destroyAnnotationType) {
this.destroyAnnotationType = destroyAnnotationType;
}
public void setOrder(int order) {
this.order = order;
}
public int getOrder() {
return this.order;
}
public void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName) {
if (beanType != null) {
InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata metadata = this.findLifecycleMetadata(beanType);
metadata.checkConfigMembers(beanDefinition);
}
}
// 父类InitDestroyAnnotationBeanPostProcessor的postProcessBeforeInitialization方法
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
InitDestroyAnnotationBeanPostProcessor.LifecycleMetadata metadata = this.findLifecycleMetadata(bean.getClass());
try {
// 调用LifecycleMetadata类的invokeInitMethods方法
metadata.invokeInitMethods(bean, beanName);
return bean;
} catch (InvocationTargetException var5) {
throw new BeanCreationException(beanName, "Invocation of init method failed", var5.getTargetException());
} catch (Throwable var6) {
throw new BeanCreationException(beanName, "Failed to invoke init method", var6);
}
}
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
return bean;
}
//省略了其他代码
}
LifecycleMetadata是InitDestroyAnnotationBeanPostProcessor的内部类,LifecycleMetadata类中的invokeInitMethods方法如下所示:
public void invokeInitMethods(Object target, String beanName) throws Throwable {
Collection<InitDestroyAnnotationBeanPostProcessor.LifecycleElement> initMethodsToIterate = this.checkedInitMethods != null ? this.checkedInitMethods : this.initMethods;
if (!((Collection)initMethodsToIterate).isEmpty()) {
boolean debug = InitDestroyAnnotationBeanPostProcessor.this.logger.isDebugEnabled();
InitDestroyAnnotationBeanPostProcessor.LifecycleElement element;
for(Iterator var5 = ((Collection)initMethodsToIterate).iterator(); var5.hasNext(); element.invoke(target)) {
element = (InitDestroyAnnotationBeanPostProcessor.LifecycleElement)var5.next();
if (debug) {
InitDestroyAnnotationBeanPostProcessor.this.logger.debug("Invoking init method on bean '" + beanName + "': " + element.getMethod());
}
}
}
}
LifecycleElement是InitDestroyAnnotationBeanPostProcessor的静态内部类,LifecycleElement类的invoke方法如下所示,通过反射调用@PostConstruct注解的方法。
public void invoke(Object target) throws Throwable {
ReflectionUtils.makeAccessible(this.method);
this.method.invoke(target, (Object[])null);
}
2、bean初始化
调用bean的初始化方法:
protected void invokeInitMethods(String beanName, Object bean, @Nullable RootBeanDefinition mbd) throws Throwable {
boolean isInitializingBean = bean instanceof InitializingBean;
if (isInitializingBean && (mbd == null || !mbd.isExternallyManagedInitMethod("afterPropertiesSet"))) {
if (this.logger.isTraceEnabled()) {
this.logger.trace("Invoking afterPropertiesSet() on bean with name '" + beanName + "'");
}
//如果类实现了InitializingBean接口,重写了afterPropertiesSet初始化方法,则会调用该方法
if (System.getSecurityManager() != null) {
try {
AccessController.doPrivileged(() -> {
((InitializingBean)bean).afterPropertiesSet();
return null;
}, this.getAccessControlContext());
} catch (PrivilegedActionException var6) {
throw var6.getException();
}
} else {
((InitializingBean)bean).afterPropertiesSet();
}
}
//如果通过XML文件指定了init-method初始化方法,则调用invokeCustomInitMethod方法进行初始化
if (mbd != null && bean.getClass() != NullBean.class) {
String initMethodName = mbd.getInitMethodName();
if (StringUtils.hasLength(initMethodName) && (!isInitializingBean || !"afterPropertiesSet".equals(initMethodName)) && !mbd.isExternallyManagedInitMethod(initMethodName)) {
this.invokeCustomInitMethod(beanName, bean, mbd);
}
}
}
3、bean初始化之后
bean初始化之后调用postProcessAfterInitialization方法:
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName) throws BeansException {
Object result = existingBean;
Object current;
for(Iterator var4 = this.getBeanPostProcessors().iterator(); var4.hasNext(); result = current) {
BeanPostProcessor processor = (BeanPostProcessor)var4.next();
current = processor.postProcessAfterInitialization(result, beanName);
if (current == null) {
return result;
}
}
return result;
}