Spring之Bean生命周期精简版

2022-07-28,,,

阶段1:Bean元信息配置阶段

这个阶段主要是bean信息的定义阶段。

Bean信息定义4种方式

  • API的方式

  • Xml文件方式

  • properties文件的方式

  • 注解的方式

阶段2:Bean元信息解析阶段

XML方式解析:XmlBeanDefinitionReader

properties文件定义bean的解析:PropertiesBeanDefinitionReader

注解方式:AnnotatedBeanDefinitionReader

阶段3:Spring Bean注册阶段

BeanDefinitionRegistry唯一实现:DefaultListableBeanFactory

大家可能看到有很多类也实现了BeanDefinitionRegistry接口,比如我们经常用到的AnnotationConfigApplicationContext,但实际上其内部是转发给了DefaultListableBeanFactory进行处理的,所以真正实现这个接口的类是DefaultListableBeanFactory

阶段4:BeanDefinition合并阶段

可能我们定义bean的时候有父子bean关系,此时子BeanDefinition中的信息是不完整的,比如设置属性的时候配置在父BeanDefinition中,此时子BeanDefinition中是没有这些信息的,需要将子bean的BeanDefinition和父bean的BeanDefinition进行合并,得到最终的一个RootBeanDefinition,合并之后得到的RootBeanDefinition包含bean定义的所有信息,包含了从父bean中继继承过来的所有信息,后续bean的所有创建工作就是依靠合并之后BeanDefinition来进行的。

阶段5:Bean Class加载阶段

这个阶段就是将bean的class名称转换为Class类型的对象

阶段6:推断构造方法

 

阶段7:Bean实例化前阶段

BeanPostProcessor是一个接口,还有很多子接口,这些接口中提供了很多方法,spring在bean生命周期的不同阶段,会调用上面这个列表中的BeanPostProcessor中的一些方法,来对生命周期进行扩展,bean生命周期中的所有扩展点都是依靠这个集合中的BeanPostProcessor来实现的,所以如果大家想对bean的生命周期进行干预,这块一定要掌握好。

注意:本文中很多以BeanPostProcessor结尾的,都实现了BeanPostProcessor接口,有些是直接实现的,有些是实现了它的子接口。

Bean实例化之前会调用一段代码:

@Nullable
    protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
        for (BeanPostProcessor bp : getBeanPostProcessors()) {
            if (bp instanceof InstantiationAwareBeanPostProcessor) {
                InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
                Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
                if (result != null) {
                    return result;
                }
            }
        }
        return null;
    }

这段代码在bean实例化之前给开发者留了个口子,开发者自己可以在这个地方直接去创建一个对象作为bean实例,而跳过spring内部实例化bean的过程。

上面代码中轮询beanPostProcessors列表,如果类型是InstantiationAwareBeanPostProcessor, 尝试调用InstantiationAwareBeanPostProcessor#postProcessBeforeInstantiation获取bean的实例对象,如果能够获取到,那么将返回值作为当前bean的实例,那么spring自带的实例化bean的过程就被跳过了。

阶段8:Bean实例化

通过反射来调用bean的构造器来创建bean的实例

阶段9:对合并的BeanDefinition对象进行处理

会调用MergedBeanDefinitionPostProcessor接口的postProcessMergedBeanDefinition方法

阶段10:Bean实例化后阶段

会调用InstantiationAwareBeanPostProcessor接口的postProcessAfterInstantiation这个方法

阶段11:Bean属性赋值阶段

循环处理PropertyValues中的属性值信息,通过反射调用set方法将属性的值设置到bean实例中

阶段12:执行Aware接口

如果我们的bean实例实现了上面的接口,会按照下面的顺序依次进行调用:

BeanNameAware:将bean的名称注入进去
BeanClassLoaderAware:将BeanClassLoader注入进去
BeanFactoryAware:将BeanFactory注入进去

 阶段13:BeanProcessor的Before方法

会调用BeanPostProcessor的postProcessBeforeInitialization方法,若返回null,当前方法将结束通常称postProcessBeforeInitialization这个方法为:bean初始化前操作。

这个接口有2个实现类,比较重要:

org.springframework.context.support.ApplicationContextAwareProcessor
org.springframework.context.annotation.CommonAnnotationBeanPostProcessor

ApplicationContextAwareProcessor注入6个Aware接口对象

如果bean实现了下面的接口,在ApplicationContextAwareProcessor#postProcessBeforeInitialization中会依次调用下面接口中的方法,将Aware前缀对应的对象注入到bean实例中。

EnvironmentAware:注入Environment对象
EmbeddedValueResolverAware:注入EmbeddedValueResolver对象
ResourceLoaderAware:注入ResourceLoader对象
ApplicationEventPublisherAware:注入ApplicationEventPublisher对象
MessageSourceAware:注入MessageSource对象
ApplicationContextAware:注入ApplicationContext对象

从名称上可以看出这个类以ApplicationContext开头的,说明这个类只能在ApplicationContext环境中使用。

CommonAnnotationBeanPostProcessor调用@PostConstruct标注的方法

CommonAnnotationBeanPostProcessor#postProcessBeforeInitialization中会调用bean中所有标注@PostConstruct注解的方法

阶段14:Bean初始化方法

调用bean定义的时候指定的初始化方法,顺序是:注解-接口-xml

阶段15:BeanProcessor的After方法

调用BeanPostProcessor接口的postProcessAfterInitialization方法,返回null的时候,会中断上面的操作,通常称postProcessAfterInitialization这个方法为:bean初始化后置操作。

阶段16:Bean初始化完毕

阶段17:Bean使用阶段

这个阶段就不说了,调用getBean方法得到了bean之后,大家可以随意使用,任意发挥。

阶段18:Bean销毁阶段

触发bean销毁的几种方式

  1. 调用org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#destroyBean

  2. 调用org.springframework.beans.factory.config.ConfigurableBeanFactory#destroySingletons

  3. 调用ApplicationContext中的close方法

Bean销毁阶段会依次执行

  1. 轮询beanPostProcessors列表,如果是DestructionAwareBeanPostProcessor这种类型的,会调用其内部的postProcessBeforeDestruction方法

  2. 如果bean实现了org.springframework.beans.factory.DisposableBean接口,会调用这个接口中的destroy方法

  3. 调用bean自定义的销毁方法

本文地址:https://blog.csdn.net/qq_24313635/article/details/109558947

《Spring之Bean生命周期精简版.doc》

下载本文的Word格式文档,以方便收藏与打印。