You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

163 lines
7.0 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

# bean生命周期12个环节
1. 阶段1Bean元信息配置阶段
2. 阶段2Bean元信息解析阶段
3. 阶段3将Bean注册到容器中
4. 阶段4BeanDefinition合并阶段
5. 阶段5Bean Class加载阶段
6. 阶段6Bean实例化阶段2个小阶段
+ Bean实例化前阶段
+ Bean实例化阶段
7. 阶段7合并后的BeanDefinition处理
8. 阶段8属性复制阶段3个小阶段
+ Bean实例化后阶段
+ Bean属性赋值前阶段
+ Bean属性赋值阶段
9. 阶段9Bean初始化阶段5个小阶段
+ Bean Aware接口回调阶段
+ Bean初始化前阶段
+ Bean初始化阶段
+ Bean初始化后阶段
10. 阶段10所有单例bean初始化完成后阶段
11. 阶段11Bean使用阶段
12. 阶段12Bean销毁前阶段
13. 阶段13Bean销毁阶段
# 阶段1Bean元信息配置阶段
这个阶段是Bean信息的定义阶段
## Bean信息定义4中方式
+ API方式
+ Xml文件
+ properties文件
+ 注解
## API方式
其他三种方式最后都会转成API方式定义bean配置信息
Spring容器启动过程中会将Bean解析成Spring内部的BeanDefinition对象bean工厂会根据定义信息对bean进行实例化、初始化
![[Snipaste_2023-02-16_14-33-18.png]]
### 例
![[Snipaste_2023-02-16_14-37-20.png]]
![[Snipaste_2023-02-16_14-37-54.png]]
![[Snipaste_2023-02-16_14-38-23.png]]
# 阶段2Bean元信息阶段解析
解析就是将各种方式定义的bean配置信息解析为BeanDefinition对象
## 元信息解析的3种方式
1. xml文件定义Bean的解析
2. properties文件定义bean的解析
3. 注解方式定义bean的解析
### XML方式解析XmlBeanDefinitionReader
将xml中定义的bean解析为BeanDefinition对象
![[Snipaste_2023-02-16_14-38-23 1.png]]
![[Snipaste_2023-02-16_14-45-54.png]]
### 注解方式AnnotatedBeanDefinitionReader
![[Snipaste_2023-02-16_14-49-03.png]]
![[Snipaste_2023-02-16_14-50-33.png]]
# 阶段3Spring Bean注册阶段
bean注册阶段需要用BeanDefinitionRegistry
## Bean注册接口BeanDefinitionRegistry
Spring中BeanDefinitionRegistry接口有一个唯一的实现类
**DefaultListableBeanFactory**
有很多类也实现了 BeanDefinitionRegistry 接口比如我们经常用到AnnotationConfigApplicationContext ,但实际上其内部是转发给了
DefaultListableBeanFactory 进行处理的所以真正实现这个接口的类是DefaultListableBeanFactory
### 例
![[Snipaste_2023-02-16_15-02-43.png]]
# 阶段4BeanDefinition合并阶段
## 合并阶段
定义bean的时候有父子bean关系此时子BeanDefinition中的信息是不完整比如设置属性的适合配置在父BeanDefinition中此时子BeanDefinition中是没有这些信息的需要将子bean的BeanDefinition和父bean的BeanDefinition进行合并得到一个RootBeanDefinition。其包含bean定义的所有信息包含了从父bean中继承过来的所有信息后续的创建工作需要依靠RootBeanDefinition进行
## 例
![[Snipaste_2023-02-16_15-11-35.png]]
![[Snipaste_2023-02-16_15-12-03.png]]
从输出的结果中可以看到合并之前BeanDefinition是不完整的比lesson2和lesson3中的class是null属性信息也不完整但是合并之后这些信息都完整了。
合并之前是 GenericBeanDefinition 类型的,合并之后得到的是 RootBeanDefinition 类型的。
获取lesson3合并的BeanDefinition时内部会递归进行合并先将lesson1和lesson2合并然后将
lesson2再和lesson3合并最后得到合并之后的BeanDefinition。后面的阶段将使用合并产生的RootBeanDefinition。
# 阶段5Bean Class加载阶段
这个阶段就是将bean的class名称转换为class类型的对象
BeanDefinition中有个Object类型的字段beanClass用来表示bean的class对象。这个字段有2种类型一种是bean对应的Class类型的对象另一种是bean对应的Class的完整类名第一种情况不需要解析第二种情况即这个字段是bean的类名的时候就需要通过类加载器将其转换为一个Class对象此时会对阶段4种合并产生的RootBeanDefinition种的beanClass进行解析将bean的类名转换为Class对象然后赋值给beanClass字段
# 阶段6Bean实例化阶段
## 1.Bean实例化前操作
先来看一下 DefaultListableBeanFactory这个类中有个非常非常重要的字段
实际上这个字段是在AbstractBeanFactory中
![[Snipaste_2023-02-16_15-28-45.png]]
BeanPostProcessor是一个接口还有很多子接口这些接口中提供了很多方法spring在bean生命
周期的不同阶段会调用上面这个列表中的BeanPostProcessor中的一些方法来对生命周期进行扩
bean生命周期中的所有扩展点都是依靠这个集合中的BeanPostProcessor来实现的很多以BeanPostProcessor结尾的都实现了BeanPostProcessor接口有些是直接实现的有些是实现了它的子接口。
![[Snipaste_2023-02-16_15-31-05.png]]
## 2.Bean实例化操作
**通过反射调用bean的构造器来创建bean的实例**具体用哪个构造器spring允许开发者自己进行判断。
![[Snipaste_2023-02-16_15-33-47.png]]
# 阶段7合并后的BeanDefinition处理
# 阶段8Bean属性设置阶段
+ 实例化后阶段
+ Bean属性赋值前处理
+ Bean属性赋值
## 1.实例化后阶段
![[Snipaste_2023-02-16_15-44-55.png]]
## 2.Bean属性赋值前处理
![[Snipaste_2023-02-16_15-45-48.png]]
AutowiredAnnotationBeanPostProcessor在这个方法中对@Autowired、@Value标注的字段、方
法注入值。
CommonAnnotationBeanPostProcessor在这个方法中对@Resource标注的字段和方法注入值。
## 3.Bean属性赋值
循环处理 PropertyValues 中的属性值信息通过反射调用set方法将属性的值设置到bean实例中。
PropertyValues中的值是通过bean xml中property元素配置的或者调用MutablePropertyValues中
add方法设置的值。
# 阶段9Bean初始化阶段
+ Bean Aware接口回调
+ Bean初始化前操作
+ Bean初始化操作
+ Bean初始化后操作
+ Bean初始化完成操作
## Bean Aware接口回调
![[Snipaste_2023-02-16_15-45-48 1.png]]
## Bean初始化前操作
![[Snipaste_2023-02-16_15-45-48 2.png]]
![[Snipaste_2023-02-16_15-45-48 3.png]]
## Bean初始化操作
1. 调用InitializingBean接口的afterPropertiesSet方法
2. 调用定义bean时候指定的初始化方法
![[Snipaste_2023-02-16_15-45-48 4.png]]
### 指定Bean的初始化方法
![[Snipaste_2023-02-16_16-02-36.png]]
## Bean初始化后操作
![[Snipaste_2023-02-16_16-04-16.png]]
## Bean初始化完成操作
# 阶段10所有单例bean初始化完成后阶段
![[Snipaste_2023-02-16_16-04-16 1.png]]
# 阶段11Bean使用阶段
# 阶段12Bean销毁阶段
## 触发bean销毁的3种方式
1. 调用org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory#destroyBean
2. 调用org.springframework.beans.factory.config.ConfigurableBeanFactory#destroySingletons
3. 调用bean自定义的销毁方法
![[Snipaste_2023-02-16_16-04-16 2.png]]
![[Snipaste_2023-02-16_16-04-16 3.png]]