Spring的bean定义 1 : 基础建模--接口BeanDefinition

简介

对于基于Spring框架开发的一个应用系统,其中每一个bean都来自于一个bean定义:开发人员的某个bean定义,框架自身的某个bean定义,三方库的某个bean定义。这些概念上的bean定义,通过Spring接口BeanDefinition被建模,并且在应用运行时都会以一个BeanDefinition对象的形式被注册到Spring IoC容器中。所以说,bean定义,或者说,BeanDefinition接口,是整个Spring容器的根本概念之一。

一个BeanDefinition描述和定义了创建一个bean需要的所有信息,属性,构造函数参数以及访问它们的方法。还有其他一些信息,比如这些定义来源自哪个类等等。

接口BeanDefinition 简介

Spring框架中的接口BeanDefinition顾名思义,就是"bean定义"的意思,它定义了创建相应的bean 使用如下属性 :

属性名称介绍
parentName双亲bean定义(parent bean definition)的名称.如果没有双亲bean定义,这里为空
beanClassNamebean的类名,在bean factorypost process阶段可能会被修改。注意该属性并不总是运行时被对应bean真正使用的类的名称:比如,bean是通过某个类的静态工厂方法生成的,这里是该类的类名,再比如,bean是通过一个工厂bean生成的,那这里为空。
scope作用域, singleton或者prototype。在bean的作用域尚未决定之前,该属性为null
lazyInit是否懒加载,仅适用于singleton bean。当一个singleton bean被指定lazyInitfalse时,它会在bean factory启动时执行singleton bean初始化的阶段被实例化。
dependsOn所依赖的bean的名称,如果有多个依赖的bean,这里需要都列出来。容器会保证这些被依赖的bean先被初始化。
autowireCandidatebean是否作为自动绑定的候选,仅适用于基于类型的自动绑定。基于名称的绑定不受此属性影响。
primary当前bean定义是否主bean。当某个自动绑定遇到多个候选bean时,primary属性为true的会被使用。
factoryBeanName如果要使用factory bean来创建bean,这里指定了相应的工厂bean的类名称
factoryMethodName工厂方法名称。基于类静态工厂方法的情况下,结合beanClassName使用;基于工厂bean的情况下,结合factoryBeanName使用。如果bean定义的constructorArgumentValues有内容,工厂方法被调用时会使用该属性。
constructorArgumentValuesbean创建时的构造函数参数
propertyValues新建的bean需要设置的属性值
initMethodNamebean的初始化方法
destroyMethodNamebean的析构方法
rolebean的角色:APPLICATION,SUPPORT,INFRASTRUCTURE。提示框架该bean的角色和重要程度。
descriptionbean的描述,human readable
singleton作用域断言,是否singleton
prototype作用域断言,是否prototype
abstract是否抽象bean定义,抽象bean定义的目的不是用于实例化bean,而是有其他目的。
resourceDescription资源描述文本,告知当前bean定义的来源,一般用于错误时显示上下文。
originatingBeanDefinition返回来源bean定义(如果有的话)。通过该属性,可以获取被修饰的bean定义。需要注意的是该属性仅仅返回直接来源bean定义而不是返回最深处的来源bean定义。一个bean定义的originatingBeanDefinition属性隐含了一个来源bean定义链,通过迭代访问该链,可以最终找到最终来自用户的bean定义。

上表中提到的bean的角色,分别是:

  • APPLICATION – 指出该bean是应用程序的主要部分,通常对应用户定义的bean
  • SUPPORT – 应用支持性质的bean,在某些地方比较重要,但从整个应用的返回来看,还没那么重要。
  • INFRASTRUCTURE – 基础设施bean,仅仅用于框架内部工作,跟终端用户无关。

除了上述直接通过BeanDefinition自身进行的定义,,接口BeanDefinition还继承了另外两个接口 : AttributeAccessorBeanMetadataElement

AttributeAccessor接口定义了对一个bean属性的访问 :

方法介绍
setAttribute设置指定的属性为特定值
getAttribute获取指定的属性的值
removeAttribute删除指定的属性
hasAttribute是否拥有指定的属性
attributeNames获取所有属性的名称

BeanMetadataElement接口定义了一个bean定义的配置来源:

方法介绍
getSource获取当前元数据元素的配置来源类

接口BeanDefinition 实现类简介

BeanDefinition 接口有一些实现类,并且这些实现类有一些共同的基础逻辑。这些实现类主要是 : RootBeanDefinition,ChildBeanDefinitionGenericBeanDefinition。它们共同的基础逻辑实现在抽象类AbstractBeanDefinition。这些类之间的层级关系如下:
在这里插入图片描述

各个接口BeanDefinition 实现类使用注意事项

一般建议

一般情况下,建议使用GenericBeanDefinition用于定义用户可见的bean定义。而对于一些父子关系已经确定的情况,使用RootBeanDefinition/ChildBeanDefinition

各个实现类的区别/特点
  • RootBeanDefinition– 不能设置parent bean定义

由此可见,RootBeanDefinition不能用于用于父子bean定义关系中的"子bean定义"

  • ChildBeanDefinition – 必须设置parent bean定义,而且必须是通过构造函数指定

ChildBeanDefinition很适合父子bean定义关系明确的情况下基于双亲bean定义和自身少量设置一些个性化属性从而进行子bean定义。
实际上,真正在创建子bean定义规定的bean对象时,Spring框架内部是将双亲bean定义和孩子bean定义合并形成一个最终使用的RootBeanDefinition,这里孩子bean定义中设置的属性会被优先使用,没有指定的都会继承使用双亲bean定义中的设置。

  • GenericBeanDefinition – 可以动态设置parent bean定义,也可以不设置parent bean定义

由此可见,GenericBeanDefinition既可以替代 RootBeanDefinition,也可以替代ChildBeanDefinition,所以GenericBeanDefinition更一般化(generic)

相关文章

Spring的bean定义 1 : 基础建模–接口BeanDefinition
Spring的bean定义 2 : 通用bean定义逻辑 – AbstractBeanDefinition
Spring的bean定义 3 : BeanDefinition实现类例子演示
Spring的bean定义 4 : 合并了的bean定义–MergedBeanDefinition

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值