bean 初始化流程:
- 初始化bean
- 填充屬性
- 處理BeanNameAware接口 (setBeanName)
- 處理BeanClassLoaderAware接口 (setBeanClassLoader)
- 處理BeanFactoryAware接口 (setBeanFactory)
- 處理BeanPostProcessor接口 (postProcessBeforeIntialization)
- 處理InitializingBean接口 (afterPropertiesSet)
- 處理自定義 init-Method
- 處理BeanPostProcessor接口 (postProcessAfterIntialization)
- 執行業務處理, 所謂的邏輯操作
- 處理DisposableBean接口 (distroy)
- 處理單例自定義 destroy-method
AbstractAutowireCapableBeanFactory#createBean()
可以通過源碼分析:org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory 類中的 doCreateBean 方法來分析.
protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final @Nullable Object[] args) throws BeanCreationException {
// 實例化bean
BeanWrapper instanceWrapper = null;
if (mbd.isSingleton()) {
instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
}
if (instanceWrapper == null) {
// 創建bean實例
instanceWrapper = createBeanInstance(beanName, mbd, args); //創建BeanWrapper
}
// 創建的bean對象
final Object bean = instanceWrapper.getWrappedInstance();
// 創建bean的class
Class<?> beanType = instanceWrapper.getWrappedClass();
if (beanType != NullBean.class) {
mbd.resolvedTargetType = beanType;
}
// 允許後處理程序修改合併的bean定義
synchronized (mbd.postProcessingLock) {
if (!mbd.postProcessed) {
try {
// 融合BeanDefinition 後臺處理器
applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
}
catch (Throwable ex) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Post-processing of merged bean definition failed", ex);
}
mbd.postProcessed = true;
}
}
// 是否單對象 & 是否允許早期循環依賴 & 是否正在創建中
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences && isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
if (logger.isTraceEnabled()) {
logger.trace("Eagerly caching bean to allow for resolving potential circular references");
}
// ObjectFactory<T> ==>> getObject() 註冊ObjectFactory工廠
addSingletonFactory(beanName, () -> getEarlyBeanReference(beanName, mbd, bean));
}
// Initialize the bean instance.
Object exposedObject = bean;
try {
populateBean(beanName, mbd, instanceWrapper); //創建bean並填充bean屬性
exposedObject = initializeBean(beanName, exposedObject, mbd); //初始化bean
}
catch (Throwable ex) {
if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
throw (BeanCreationException) ex;
}
else {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
}
}
if (earlySingletonExposure) {
Object earlySingletonReference = getSingleton(beanName, false);
if (earlySingletonReference != null) {
if (exposedObject == bean) {
exposedObject = earlySingletonReference;
}
else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
String[] dependentBeans = getDependentBeans(beanName);
Set<String> actualDependentBeans = new LinkedHashSet<>(dependentBeans.length);
for (String dependentBean : dependentBeans) {
if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
actualDependentBeans.add(dependentBean);
}
}
if (!actualDependentBeans.isEmpty()) {
throw new BeanCurrentlyInCreationException(beanName,
"Bean with name '" + beanName + "' has been injected into other beans [" +
StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
"] in its raw version as part of a circular reference, but has eventually been " +
"wrapped. This means that said other beans do not use the final version of the " +
"bean. This is often the result of over-eager type matching - consider using " +
"'getBeanNamesOfType' with the 'allowEagerInit' flag turned off, for example.");
}
}
}
}
// Register bean as disposable.
try {
registerDisposableBeanIfNecessary(beanName, bean, mbd);
}
catch (BeanDefinitionValidationException ex) {
throw new BeanCreationException(mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
}
return exposedObject;
}
可以發現, 在填充完屬性之後調用 initializeBean() 初始化方法, 在初始化時會先執行Aware 接口的方法, 順序 BeanNameAware 接口、 BeanClassLoaderAware 接口、BeanFactoryAware 接口
protected Object initializeBean(final String beanName, final Object bean, @Nullable RootBeanDefinition mbd) {
if (System.getSecurityManager() != null) {
AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
invokeAwareMethods(beanName, bean);
return null;
}, getAccessControlContext());
}
else {
invokeAwareMethods(beanName, bean);//調用默認方法 如: BeanFactoryAware # setBeanFactory(this)
}
Object wrappedBean = bean;
if (mbd == null || !mbd.isSynthetic()) {
//前置處理器
wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName); //在初始化之前使用處理器
}
try {
invokeInitMethods(beanName, wrappedBean, mbd);//調用初始化方法 如:InitializingBean # afterPropertiesSet()
}
catch (Throwable ex) {
throw new BeanCreationException("Invocation of init method failed", ex);
}
if (mbd == null || !mbd.isSynthetic()) {
//後置處理器, 在初始化之後使用處理器
wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
}
return wrappedBean;
}
執行Aware 擴展接口的方法
//執行默認方法
private void invokeAwareMethods(final String beanName, final 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);
}
}
}
在 initializeBean() 方法中調用 applyBeanPostProcessorsBeforeInitialization() 方法執行處理器接口初始化bean , 先獲取所有的BeanPostProcessor 接口的實現類, 然後遍歷執行 postProcessBeforeInitialization 前置處理方法初始化 bean.
@Override
public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName) throws BeansException {
Object result = existingBean;
// 遍歷, 前處理bean操作
for (BeanPostProcessor processor : getBeanPostProcessors()) {
Object current = processor.postProcessBeforeInitialization(result, beanName);
if (current == null) {
return result;
}
result = current;
}
return result;
}
執行完處理器,調用初始化 afterPropertiesSet() 方法, 和自定義 init-method 的方法
/**
* 現在,bean的所有屬性都設置好了,並有機會了解它所擁有的bean工廠(此對象)
*/
protected void invokeInitMethods(String beanName, final Object bean, @Nullable RootBeanDefinition mbd) throws Throwable {
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<Object>) () -> {
((InitializingBean) bean).afterPropertiesSet();
return null;
}, getAccessControlContext());
}
catch (PrivilegedActionException pae) {
throw pae.getException();
}
}
else {
// 執行InitializingBean 接口的afterPropertiesSet 方法
((InitializingBean) bean).afterPropertiesSet();
}
}
// 如果定義了init-method 方法, 執行方法
if (mbd != null && bean.getClass() != NullBean.class) {
String initMethodName = mbd.getInitMethodName();
if (StringUtils.hasLength(initMethodName) && !(isInitializingBean && "afterPropertiesSet".equals(initMethodName)) && !mbd.isExternallyManagedInitMethod(initMethodName)) {
// 執行自定義名稱的方法
invokeCustomInitMethod(beanName, bean, mbd);
}
}
}
然後繼續處理 BeanPostProcessor 接口的實現類, 遍歷執行 postProcessAfterInitialization() 後置方法處理
public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName) throws BeansException {
Object result = existingBean;
// 遍歷, 執行後處理方法
for (BeanPostProcessor processor : getBeanPostProcessors()) {
Object current = processor.postProcessAfterInitialization(result, beanName);
if (current == null) {
return result;
}
result = current;
}
return result;
}
之後就是處理銷燬方法, 銷燬方法跟創建bean 方法不是在同一個類操作(DisposableBeanAdapter)。 有興趣的可以去研究下
核心方法:org.springframework.context.support.AbstractApplicationContext 類的 refresh() 方法