SpringIOC之BeanDefinition 相关类型关系

概述

我们知道Spring中Bean的配置来源很多(主要两种方式定义一个 Bean:面向资源(XML、Properties)面向注解),为了收集不同配置源,需要统一起来,所有有必要使用一个对象存储 也就是BeanDefinition,而在使用这些BeanDefinition之前,不同的BeanDefinition直接也会存在不同的依赖层级和引用关系。遵循单一职责、开闭原则 还需要划分增强这些BeanDefinition,最后再统一成功能增强的BeanDefinition,就是合并后的RootBeanDefinition 。

最后将我们的配置信息转换成 Spring Bean,并管理着这些Bean的生命周期

Spring Bean 的生命周期 可以看到,BeanDefinition 可以说是 Bean 的“前身”,首先进入 Bean 的元信息的配置、解析和注册阶段,然后才开始 Bean 的实例化和初始化等工作。

BeanDefinition 是 Spring Framework 中定义 Bean 的配置元信息接口,主要包含一下信息:

  • Bean 的类名

  • Bean 行为配置类,如作用域、自动绑定模式(自动装配模式)、生命周期回调等

  • 其他 Bean 引用,又可称作合作者或者依赖

  • 配置设置,比如 Bean 属性

Bean 的“前身”

Spring中不同BeanDefinition的关系图

分析

BeanDefinition 继承体系结构

AttributeAccessor接口:用于获取元数据,在实现类中通过 LinkedHashMap 集合保存元数据,例如通过 XML 的 <meta /> 标签定义的一些元信息会保存在其中

BeanMetadataElement接口:用于获取定义 Bean 的源对象,在实现类中通过 Object 对象保存,所谓的源对象就是定义这个 Bean 的资源(XML 标签对象或者 .class 文件资源对象)

BeanDefinition接口:定义一个 Bean 的元信息

AbstractBeanDefinition抽象类:实现 BeanDefinition 接口,包含了一个 Bean 几乎所有的元信息:

GenericBeanDefinition:继承 AbstractBeanDefinition 抽象类,多了一个 parentName,表示有继承关系,是一个标准 Bean 元信息对象,通过 XML 定义的 Bean 会解析成该对象

AnnotatedBeanDefinition接口:继承 BeanDefinition 接口,定义注解类的元信息,例如通过 @Component 注解定义的 Bean,那么注解类的元信息中会包含编译后的 .class 文件的所有信息

ScannedGenericBeanDefinition:,继承 GenericBeanDefinition,实现 AnnotatedBeanDefinition 接口,多了一个 AnnotationMetadata 注解类元信息对象,例如通过 @Component 注解定义的 Bean 会解析成该对象

AnnotatedGenericBeanDefinition:继承 GenericBeanDefinition,实现 AnnotatedBeanDefinition 接口,和 ScannedGenericBeanDefinition 类似,通过 @Import 导入的 Configuration Class 会解析成该对象

RootBeanDefinition:继承 AbstractBeanDefinition 抽象类,表示合并后的 BeanDefinition 对象。在 Spring BeanFactory 初始化 Bean 的前阶段,会根据 BeanDefinition 生成一个 RootBeanDefinition(具有层次性则会进行合并),用于后续实例化、属性注入和初始化

ConfigurationClassBeanDefinition:私有静态类,继承 RootBeanDefinition,实现了 AnnotatedBeanDefinition 接口,和 AnnotatedGenericBeanDefinition 类似,没有继承关系(就是没有继承GenericBeanDefinition),通过 @Bean 定义的方法会解析成该对象

BeanDefinitionHolder: 包含 BeanDefinition、Bean 的名称以及别名(支持多个)

BeanDefinition 接口的实现类主要根据 Bean 的定义方式进行区分,如下:

  1. XML 定义 Bean >>>>> GenericBeanDefinition

  1. @Component 以及派生注解定义 Bean >>>>> ScannedGenericBeanDefinition

  1. 借助于 @Import 导入 Bean >>>>> AnnotatedGenericBeanDefinition

  1. @Bean 定义的方法 >>>>> ConfigurationClassBeanDefinition

  1. 在 Spring BeanFactory 初始化 Bean 的前阶段,会根据 BeanDefinition 生成一个合并后的 RootBeanDefinition 对象

在解析出来 BeanDefinition 后都会转换成 BeanDefinitionHolder 对象,然后进行注册,,知道为啥不直接使用BeanDefinition? 留个悬念啊下一篇会分析的

总结

Spring Bean 的“前身”为 BeanDefinition 对象,里面包含了 Bean 的元信息,后续在 Bean 的生命周期中会根据BeanDefinition对象进行实例化、属性注入和初始化等工作

BeanDefinition 接口的实现类主要根据 Bean 的定义方式进行区分,如下:

  1. XML 定义 Bean:GenericBeanDefinition

  1. @Component 以及派生注解定义 Bean:ScannedGenericBeanDefinition

  1. 借助于 @Import 导入 Bean:AnnotatedGenericBeanDefinition

  1. @Bean 定义的方法:ConfigurationClassBeanDefinition 私有静态类(ConfigurationClassBeanDefinitionReader的内部类

上面的 123 三种 BeanDefinition 实现类具有层次性(就是继承实现关系,来自于GenericBeanDefinition具有的功能),在 Spring BeanFactory 初始化 Bean 的前阶段,会根据 BeanDefinition 生成一个合并后的 RootBeanDefinition 对象

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Coder_Boy_

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值