Spring Bean 生命周期概述

在Spring 启动流程概述 中,分析了 Spring 的启动流程。本文就来说明一下 Spring Bean 整个生命周期。如果有不清楚的地方,可以参考上文的“附录:启动日志”。

直接上图:Spring Bean 生命周期流程图。内容较多,图片文字偏小,请放大看(矢量图,可以任意放大):

Spring Bean 生命周期概述

Figure 1. Spring Bean 生命周期流程图

下面是文字说明。

Bean 生命周期

getBean() 方法获取 Bean 时,如果缓存中没有对应的 Bean,则会创建 Bean,整个流程如下:

  1. InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation — 目前有如下四个:

    ImportAwareBeanPostProcessor
    AnnotationAwareAspectJAutoProxyCreator
    CommonAnnotationBeanPostProcessor
    AutowiredAnnotationBeanPostProcessor
    
  2. 构造函数

  3. MergedBeanDefinitionPostProcessor#postProcessMergedBeanDefinition — 目前有如下三个:

    1. CommonAnnotationBeanPostProcessor — 收集 @Resource 依赖信息, initMethodsdestroyMethods 等信息。(就是 @PostConstruct@PreDestroy 标注的方法。)

    2. AutowiredAnnotationBeanPostProcessor — 收集 @Autowired 的依赖信息。

    3. ApplicationListenerDetector — 判断 Bean 是否是一个 ApplicationListener ,是则保留,在后面的 postProcessAfterInitialization 方法中,加入到容器的 applicationListeners 中。

  4. InstantiationAwareBeanPostProcessor#postProcessAfterInstantiation — 与上面的 postProcessBeforeInstantiation 方法对应,目前有如下四个:

    ImportAwareBeanPostProcessor
    AnnotationAwareAspectJAutoProxyCreator
    CommonAnnotationBeanPostProcessor
    AutowiredAnnotationBeanPostProcessor
    
  5. InstantiationAwareBeanPostProcessor#postProcessProperties — 目前有如下三个:

    1. ImportAwareBeanPostProcessor — 如果 Bean 是 EnhancedConfiguration (它继承了 BeanFactoryAware ) 的实现类,则注入 BeanFactory

    2. AnnotationAwareAspectJAutoProxyCreator — 无所事事。

    3. CommonAnnotationBeanPostProcessor — 完成 @Resource 依赖注入。

      在这里会递归创建所依赖 Bean。调试代码,弄清楚。

    4. AutowiredAnnotationBeanPostProcessor — 完成 @Autowired@Value 注入

  6. InstantiationAwareBeanPostProcessor#postProcessPropertyValues — 从 5.1 开始废弃,使用上面方法代替。

    Warning

    这里要注意,并不是执行完四个类的 postProcessProperties 方法,再去执行四个类的 postProcessPropertyValues 方法。而是以类为顺序的,执行完一个类的 postProcessProperties 方法,然后去执行 postProcessPropertyValues 方法。执行完一个类,再去执行下一个类。这个现象在下面的日志中有反应。
  7. AutowiredAnnotationBeanPostProcessor#setBeanFactory(DefaultListableBeanFactory) — 通过 AbstractAutowireCapableBeanFactory#invokeAwareMethods 方法如下 Aware 注入:

    BeanNameAware
    BeanClassLoaderAware
    BeanFactoryAware
    
  8. BeanPostProcessor#postProcessBeforeInitialization — 目前有

    1. 用户手动添加的 BeanPostProcessor

    2. ApplicationContextAwareProcessor — 完成如下六个 Aware 的注入:

      EnvironmentAware
      EmbeddedValueResolverAware
      ResourceLoaderAware
      ApplicationEventPublisherAware
      MessageSourceAware
      ApplicationContextAware
      
    3. ImportAwareBeanPostProcessor — 如果实现了 ImportAware 接口,则注入 importMetadata 信息。

    4. BeanPostProcessorChecker — 无所事事。

    5. AnnotationAwareAspectJAutoProxyCreator — 无所事事。

    6. CommonAnnotationBeanPostProcessor — 要调用 LifecycleMetadata#invokeInitMethods 方法,但是,里面去没有任何实现,似乎调用了全局设置的初始化操作。需要找文档确认一下。

    7. AutowiredAnnotationBeanPostProcessor — 继承父类实现,无所事事。

    8. ApplicationListenerDetector — 无所事事。

  9. InitializingBean#afterPropertiesSet()

  10. init-method

  11. BeanPostProcessor#postProcessAfterInitialization 方法 — 目前有

    1. 用户手动添加的 BeanPostProcessor

    2. ApplicationContextAwareProcessor — 继承默认实现,无所事事。

    3. ImportAwareBeanPostProcessor — 继承默认实现,无所事事。

    4. BeanPostProcessorChecker — 如果 Bean 是 BeanPostProcessor 子类,则检查 BeanPostProcessor 数量。

    5. AnnotationAwareAspectJAutoProxyCreator — 检查 Bean 和提前暴露的引用是否相同,不同则重新生成代理对象。

    6. CommonAnnotationBeanPostProcessor — 继承父类实现,无所事事。

    7. AutowiredAnnotationBeanPostProcessor — 继承父类实现,无所事事。

    8. ApplicationListenerDetector — 将 ApplicationListener 类型的 Bean,加入到容器的 applicationListeners 中,方便容器开始监听。

初始化之前,似乎可以设置全局的初始化操作。忘了具体在哪个类中了?

Bean 生命周期补充说明

下面对创建 Bean 的流程做进一步说明:

.1. InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation

通过 AbstractAutowireCapableBeanFactory#resolveBeforeInstantiation 方法,调用 InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation 方法。遍历 InstantiationAwareBeanPostProcessor 列表( getBeanPostProcessorCache().instantiationAware 变量)时,如果返回值不为空,则立即返回,不再继续调用。不为空,则表示创建了 Bean 对象,然后马上调用 BeanPostProcessor#postProcessAfterInitialization 方法。如果这里创建对象,则直接返回该对象,不再进行下面的调用。有四个 InstantiationAwareBeanPostProcessor 对象:

ConfigurationClassPostProcessor
AnnotationAwareAspectJAutoProxyCreator
CommonAnnotationBeanPostProcessor
AutowiredAnnotationBeanPostProcessor

.2. Bean 的构造函数

.3. MergedBeanDefinitionPostProcessor#postProcessMergedBeanDefinition

通过 AbstractAutowireCapableBeanFactory#applyMergedBeanDefinitionPostProcessors 调用 MergedBeanDefinitionPostProcessor#postProcessMergedBeanDefinition 方法。变量: getBeanPostProcessorCache().mergedDefinition 这个方法主要干什么?通过 CommonAnnotationBeanPostProcessor#applyMergedBeanDefinitionPostProcessors 调用 CommonAnnotationBeanPostProcessor#findResourceMetadata 可以看出,这个地方可以获取依赖信息。带验证。 系统中有如下四个类:

CommonAnnotationBeanPostProcessor
AutowiredAnnotationBeanPostProcessor
ApplicationListenerDetector
InitDestroyAnnotationBeanPostProcessor

.4. InstantiationAwareBeanPostProcessor#postProcessAfterInstantiation

有一点重要的信息,日志中没有体现出来。设置 Bean 的属性是在执行 BeanPostProcessor 调用之前完成的。在 AbstractAutowireCapableBeanFactory#doCreateBean 方法中,调用了 AbstractAutowireCapableBeanFactory#populateBean 方法来设置属性,然后去调用的 BeanPostProcessorinit 方法。 populateBean 方法是通过调用 InstantiationAwareBeanPostProcessor#postProcessProperties 方法来完成注入,其中 CommonAnnotationBeanPostProcessorAutowiredAnnotationBeanPostProcessor 分别处理不同的注解。下面是 populateBean 方法更详细的说明。

在注入 Bean 属性之前,调用 InstantiationAwareBeanPostProcessor#postProcessAfterInstantiation 。(从变量 getBeanPostProcessorCache().instantiationAware 中获取列表。)容器完成初始化后,有 ImportAwareBeanPostProcessorAnnotationAwareAspectJAutoProxyCreatorCommonAnnotationBeanPostProcessorAutowiredAnnotationBeanPostProcessor 四个 InstantiationAwareBeanPostProcessor 对象。但是,这四个类,没有做任何操作。如果返回值为 false 则中断,不再继续遍历 InstantiationAwareBeanPostProcessor 列表。

ConfigurationClassPostProcessor
AnnotationAwareAspectJAutoProxyCreator
CommonAnnotationBeanPostProcessor
AutowiredAnnotationBeanPostProcessor

.5. InstantiationAwareBeanPostProcessor#postProcessProperties

接着调用 InstantiationAwareBeanPostProcessor#postProcessProperties 方法来完成属性注入。

.6. InstantiationAwareBeanPostProcessor#postProcessPropertyValues

然后再执行 InstantiationAwareBeanPostProcessor#postProcessPropertyValues 。这个方法马上从 5.1 开始要废弃掉,使用上述 postProcessProperties 代替。

到这里 populateBean 方法结束。

.7. AutowiredAnnotationBeanPostProcessor#setBeanFactory(DefaultListableBeanFactory)

.8. BeanPostProcessor#postProcessBeforeInitialization

调用 BeanPostProcessor#postProcessBeforeInitialization 方法。

.9. InitializingBean#afterPropertiesSet()

.10. init-method

init 方法。

.11. BeanPostProcessor#postProcessAfterInitialization

调用 BeanPostProcessor#postProcessAfterInitialization 方法。

Bean 销毁流程

  1. 调用 beanFactory.destroyBean(bean) 方法,开始销毁 Bean。

  2. 调用 DestructionAwareBeanPostProcessor#postProcessBeforeDestruction(Object bean, String beanName)ApplicationListenerDetector 就是一个 DestructionAwareBeanPostProcessor 。但是,Bean 销毁时,不知道为什么没有被调用。

  3. 调用 DisposableBean#destroy() 方法

  4. 如果还有 destroy-method ,接着通过反射调用 destroy-method 方法。

原文 

https://www.diguage.com/post/spring-bean-lifecycle-overview/

本站部分文章源于互联网,本着传播知识、有益学习和研究的目的进行的转载,为网友免费提供。如有著作权人或出版方提出异议,本站将立即删除。如果您对文章转载有任何疑问请告之我们,以便我们及时纠正。

PS:推荐一个微信公众号: askHarries 或者qq群:474807195,里面会分享一些资深架构师录制的视频录像:有Spring,MyBatis,Netty源码分析,高并发、高性能、分布式、微服务架构的原理,JVM性能优化这些成为架构师必备的知识体系。还能领取免费的学习资源,目前受益良多

转载请注明原文出处:Harries Blog™ » Spring Bean 生命周期概述

赞 (0)
分享到:更多 ()

评论 0

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址