SpringBoot源码解析(九):Bean定义接口体系
SpringBoot源码系列文章
SpringBoot源码解析(一):SpringApplication构造方法
SpringBoot源码解析(二):引导上下文DefaultBootstrapContext
SpringBoot源码解析(三):启动开始阶段
SpringBoot源码解析(四):解析应用参数args
SpringBoot源码解析(五):准备应用环境
SpringBoot源码解析(六):打印Banner
SpringBoot源码解析(七):应用上下文结构体系
SpringBoot源码解析(八):Bean工厂接口体系
SpringBoot源码解析(九):Bean定义接口体系
目录
- 前言
- 一、BeanDefinition类图
- 二、BeanDefinition组件功能解析
- 1、AttributeAccessor(属性访问器)
- 2、BeanDefinition(Bean定义)
- 3、AttributeAccessorSupport(属性访问器支持类)
- 4、BeanMetadataAttributeAccessor(Bean元数据属性访问器)
- 5、AbstractBeanDefinition(抽象Bean定义)
- 6、GenericBeanDefinition(通用Bean定义)
- 7、ChildBeanDefinition(子Bean定义)
- 8、RootBeanDefinition(根Bean定义)
- 9、AnnotatedBeanDefinition(注解Bean定义)
- 10、ScannedGenericBeanDefinition(扫描通用Bean定义)
- 总结
前言
Spring容器的核心在于其对Bean的管理
,而这一切的基础则由BeanDefinition
接口体系所支撑。BeanDefinition作为描述
和定义
Spring容器中Bean的核心接口,它不仅负责存储Bean的元数据,还为容器的实例化、依赖注入和生命周期管理提供了必要的信息。接下来我们将对其主要组件进行介绍。
一、BeanDefinition类图
二、BeanDefinition组件功能解析
1、AttributeAccessor(属性访问器)
AttributeAccessor
是一个用于管理和操作键值对
形式属性的接口,提供设置
、获取
、删除
、检查属性等通用功能,广泛应用于Spring框架中元数据的管理
。
public interface AttributeAccessor {
// 设置属性
void setAttribute(String name, @Nullable Object value);
// 获取指定属性的值
@Nullable
Object getAttribute(String name);
// 如果该键对应的属性值已经存在,则直接返回现有值
// 如果不存在,使用计算函数生成新值(相当于延迟计算,调用时候才计算)
@SuppressWarnings("unchecked")
default <T> T computeAttribute(String name, Function<String, T> computeFunction) {
...
}
// 移除指定键的属性并返回其值
@Nullable
Object removeAttribute(String name);
// 检查指定键的属性是否存在
boolean hasAttribute(String name);
// 返回所有属性的键名称
String[] attributeNames();
}
2、BeanDefinition(Bean定义)
AttributeAccessor
是一个用于管理和操作键值对
形式属性的接口,提供设置
、获取
、删除
、检查属性等通用功能,广泛应用于Spring框架中元数据的管理
。
public interface BeanDefinition extends AttributeAccessor, BeanMetadataElement {
// 单例作用域标识符:`singleton`(表示该 Bean 在整个容器生命周期内只有一个实例)
String SCOPE_SINGLETON = ConfigurableBeanFactory.SCOPE_SINGLETON;
// 原型作用域标识符:`prototype`(表示每次获取该 Bean 时都会创建一个新实例)
String SCOPE_PROTOTYPE = ConfigurableBeanFactory.SCOPE_PROTOTYPE;
// 角色:应用程序 Bean(用于实现具体的业务逻辑)
int ROLE_APPLICATION = 0;
// 角色:支持 Bean(一些配合主逻辑使用的辅助工具或配置类)
int ROLE_SUPPORT = 1;
// 角色:基础设施 Bean(框架内部的实现类,比如事务管理器或事件监听器,这些 Bean 通常由 Spring 自动生成,用户无需关心)
int ROLE_INFRASTRUCTURE = 2;
// ==================== 可修改的属性 ====================
// 设置父定义的名称(如果有)
void setParentName(@Nullable String parentName);
// 返回父定义的名称(如果有)
@Nullable
String getParentName();
// 设置此 Bean 定义的类名
void setBeanClassName(@Nullable String beanClassName);
// 返回当前的 Bean 类名
@Nullable
String getBeanClassName();
// 设置 Bean 的作用域(如 singleton 或 prototype)
void setScope(@Nullable String scope);
// 返回 Bean 当前的作用域
@Nullable
String getScope();
// 设置是否延迟初始化(仅适用于单例 Bean)
void setLazyInit(boolean lazyInit);
// 返回该Bean是否延迟初始化(该Bean实际需要使用时才会被创建)
boolean isLazyInit();
// 设置此Bean依赖的其他 Bean 名称(Spring容器将确保这些依赖的Bean先被初始化)
void setDependsOn(@Nullable String... dependsOn);
// 返回此 Bean 依赖的其他 Bean 名称
@Nullable
String[] getDependsOn();
// 设置此 Bean 是否可以作为自动装配的候选对象
// 即:是否能够被Spring容器在自动装配过程中选中并注入到其他Bean中
void setAutowireCandidate(boolean autowireCandidate);
// 返回此 Bean 是否可以作为自动装配的候选对象
boolean isAutowireCandidate();
// 设置此 Bean 是否为主要的自动装配候选对象(在多个候选对象中优先选择primary候选)
void setPrimary(boolean primary);
// 返回此 Bean 是否为主要的自动装配候选对象
boolean isPrimary();
// 指定用于创建此 Bean 的工厂 Bean 名称(如果有)
void setFactoryBeanName(@Nullable String factoryBeanName);
// 返回用于创建此 Bean 的工厂 Bean 名称(如果有)
@Nullable
String getFactoryBeanName();
// 指定用于创建此 Bean 的工厂方法名称(如果有)
void setFactoryMethodName(@Nullable String factoryMethodName);
// 返回用于创建此 Bean 的工厂方法名称(如果有)
@Nullable
String getFactoryMethodName();
// 返回此 Bean 的构造函数参数值
ConstructorArgumentValues getConstructorArgumentValues();
// 检查是否为此 Bean 定义了构造函数参数值
default boolean hasConstructorArgumentValues() {
return !getConstructorArgumentValues().isEmpty();
}
// 返回当前 Bean 定义中的属性键值对集合,用于描述 Bean 初始化时需要注入的属性
MutablePropertyValues getPropertyValues();
// 检查是否为此 Bean 定义了属性值
default boolean hasPropertyValues() {
return !getPropertyValues().isEmpty();
}
// 设置初始化方法名称
void setInitMethodName(@Nullable String initMethodName);
// 返回初始化方法名称
@Nullable
String getInitMethodName();
// 设置销毁方法名称
void setDestroyMethodName(@Nullable String destroyMethodName);
// 返回销毁方法名称
@Nullable
String getDestroyMethodName();
// 设置此 Bean 定义的角色,上面常量的三种角色
void setRole(int role);
// 返回此 Bean 定义的角色
int getRole();
// 设置此 Bean 定义的人类可读描述
void setDescription(@Nullable String description);
// 返回此 Bean 定义的人类可读描述
@Nullable
String getDescription();
// ==================== 只读属性 ====================
// 解析和返回当前 Bean 定义的具体类型(包括泛型和复杂类型)
ResolvableType getResolvableType();
// 检查此 Bean 是否为单例
boolean isSingleton();
// 检查此 Bean 是否为原型
boolean isPrototype();
// 判断一个 Bean 定义是否为抽象定义,用于区分模板和具体实现
boolean isAbstract();
// 返回 Bean 定义的资源描述(通常是 XML 文件、Java 配置类、注解等)
// 通过返回的描述,开发者可以了解这个 Bean 是从哪里加载的,便于定位问题
@Nullable
String getResourceDescription();
// 它的作用是在Bean定义发生装饰、代理或重新定义时,提供对原始定义的访问
@Nullable
BeanDefinition getOriginatingBeanDefinition();
}
3、AttributeAccessorSupport(属性访问器支持类)
AttributeAccessorSupport
是Spring中的一个抽象类
,用于管理任意键值对属性
,提供添加、获取、移除等操作,常用于存储元数据
或动态属性信息
。。
public abstract class AttributeAccessorSupport implements AttributeAccessor, Serializable {
// 提供了一个内置的Map(attributes)来存储键值对属性
private final Map<String, Object> attributes = new LinkedHashMap<>();
// ...省略AttributeAccessor属性设置获取移除等方法的实现
}
4、BeanMetadataAttributeAccessor(Bean元数据属性访问器)
BeanMetadataAttributeAccessor
是Spring框架中一个常用的工具类。它用于存储和管理与Bean元数据相关的附加属性
,尤其是在Spring容器中扩展Bean定义时,作为元数据的容器。
@SuppressWarnings("serial")
public class BeanMetadataAttributeAccessor extends AttributeAccessorSupport implements BeanMetadataElement {
// 记录元数据元素的来源对象,可以是配置文件路径、注解类等
@Nullable
private Object source;
// 设置此元数据元素的配置来源对象
public void setSource(@Nullable Object source) {
this.source = source;
}
// 获取此元数据元素的配置来源对象
@Override
@Nullable
public Object getSource() {
return this.source;
}
// 将给定的BeanMetadataAttribute添加到此访问器的属性集中
public void addMetadataAttribute(BeanMetadataAttribute attribute) {
// 将属性存储在父类提供的 attributes Map 中
super.setAttribute(attribute.getName(), attribute);
}
// 在此访问器的属性集中查找给定的BeanMetadataAttribute
@Nullable
public BeanMetadataAttribute getMetadataAttribute(String name) {
return (BeanMetadataAttribute) super.getAttribute(name);
}
// 设置属性,将其包装为BeanMetadataAttribute存储
@Override
public void setAttribute(String name, @Nullable Object value) {
// 将属性值包装为 BeanMetadataAttribute
super.setAttribute(name, new BeanMetadataAttribute(name, value));
}
// 获取指定名称的属性值
@Override
@Nullable
public Object getAttribute(String name) {
// 从父类的 attributes Map 获取 BeanMetadataAttribute
BeanMetadataAttribute attribute = (BeanMetadataAttribute) super.getAttribute(name);
// 返回其值
return (attribute != null ? attribute.getValue() : null);
}
// 移除指定名称的属性并返回其值
@Override
@Nullable
public Object removeAttribute(String name) {
// 从父类的 attributes Map 移除 BeanMetadataAttribute
BeanMetadataAttribute attribute = (BeanMetadataAttribute) super.removeAttribute(name);
// 返回其值
return (attribute != null ? attribute.getValue() : null);
}
}
5、AbstractBeanDefinition(抽象Bean定义)
AbstractBeanDefinition
是Spring中Bean定义
的抽象基类
,提供了描述Bean的属性、依赖关系、作用域和生命周期等核心功能。
public abstract class AbstractBeanDefinition extends BeanMetadataAttributeAccessor
implements BeanDefinition, Cloneable {
// ==================== 核心属性 ====================
// Bean的类对象,可以是Class实例或类名字符串
@Nullable
private volatile Object beanClass;
// SCOPE_DEFAULT: 默认的Bean作用域名称为 "",等效于单例状态,除非被父Bean定义覆盖
@Nullable
private String scope = SCOPE_DEFAULT;
// 标记该Bean是否为抽象Bean,抽象Bean不能被实例化
private boolean abstractFlag = false;
// 是否延迟初始化,null表示未明确设置
@Nullable
private Boolean lazyInit;
// 自动装配模式,默认不自动装配
private int autowireMode = AUTOWIRE_NO;
// 依赖检查模式,默认无依赖检查
private int dependencyCheck = DEPENDENCY_CHECK_NONE;
// 该Bean依赖的其他Bean名称
@Nullable
private String[] dependsOn;
// 是否为自动装配候选Bean
private boolean autowireCandidate = true;
// 是否为主要的自动装配候选Bean
private boolean primary = false;
// 工厂Bean的名称,如果通过工厂Bean创建
@Nullable
private String factoryBeanName;
// 工厂方法的名称,用于通过静态方法或工厂Bean的方法创建实例
@Nullable
private String factoryMethodName;
// 构造函数的参数值
@Nullable
private ConstructorArgumentValues constructorArgumentValues;
// Bean的属性值
@Nullable
private MutablePropertyValues propertyValues;
// 初始化方法名称,用于在Bean实例化后调用
@Nullable
private String initMethodName;
// 销毁方法名称,用于在Bean销毁前调用
@Nullable
private String destroyMethodName;
// Bean的角色,默认是应用角色
private int role = BeanDefinition.ROLE_APPLICATION;
// Bean的描述信息
@Nullable
private String description;
// 描述该Bean定义来源的资源,例如XML配置文件的位置
@Nullable
private Resource resource;
// ==================== 核心方法 ====================
// 都是类似的getset方法
@Override
public void setBeanClassName(@Nullable String beanClassName) {
this.beanClass = beanClassName;
}
@Override
@Nullable
public String getBeanClassName() {
Object beanClassObject = this.beanClass;
if (beanClassObject instanceof Class) {
return ((Class<?>) beanClassObject).getName();
}
else {
return (String) beanClassObject;
}
}
// 验证 Bean 定义是否有效,例如检查必须的属性是否已设置
public void validate() throws BeanDefinitionValidationException {
...
}
// 克隆当前 Bean 定义,用于 Bean 配置的复制
public abstract AbstractBeanDefinition cloneBeanDefinition();
}
6、GenericBeanDefinition(通用Bean定义)
GenericBeanDefinition
用于定义普通的Bean配置,适用于没有继承关系的独立Bean(虽然可以指定父 Bean,但通常不表示父子关系),支持配置构造方法、作用域、初始化方法等属性。
@SuppressWarnings("serial")
public class GenericBeanDefinition extends AbstractBeanDefinition {
@Nullable
private String parentName; // 父类名称
// 创建一个新的GenericBeanDefinition
// 可通过其bean属性和配置方法进行配置
public GenericBeanDefinition() {
super();
}
// 创建一个新的GenericBeanDefinition,作为给定bean定义的深拷贝
public GenericBeanDefinition(BeanDefinition original) {
super(original);
}
// 设置父类名称
@Override
public void setParentName(@Nullable String parentName) {
this.parentName = parentName;
}
// 获取父类名称
@Override
@Nullable
public String getParentName() {
return this.parentName;
}
// 克隆 bean 定义
@Override
public AbstractBeanDefinition cloneBeanDefinition() {
return new GenericBeanDefinition(this);
}
// ... 省略重写 equal 和 toString方法
}
7、ChildBeanDefinition(子Bean定义)
ChildBeanDefinition
专门用于表示子Bean的定义,允许子bean继承父bean的属性和方法
,并可以进行扩展或覆盖。
@SuppressWarnings("serial")
public class ChildBeanDefinition extends AbstractBeanDefinition {
@Nullable
private String parentName; // 父类名称
// 为给定的父类创建一个新的 ChildBeanDefinition,提供构造函数参数和属性值
public ChildBeanDefinition(
String parentName, Class<?> beanClass, ConstructorArgumentValues cargs, MutablePropertyValues pvs) {
super(cargs, pvs);
this.parentName = parentName; // 设置父类名称
setBeanClass(beanClass); // 设置 bean 类
}
// ... 省略类似构造方法
// 设置父类名称
@Override
public void setParentName(@Nullable String parentName) {
this.parentName = parentName;
}
// 获取父类名称
@Override
@Nullable
public String getParentName() {
return this.parentName;
}
// 校验父类必须存在,否则报错
@Override
public void validate() throws BeanDefinitionValidationException {
super.validate();
// 校验父类名称是否为空
if (this.parentName == null) {
throw new BeanDefinitionValidationException("'parentName' must be set in ChildBeanDefinition");
}
}
// 克隆当前的 ChildBeanDefinition
@Override
public AbstractBeanDefinition cloneBeanDefinition() {
return new ChildBeanDefinition(this);
}
// ... 省略重写 equal 和 toString方法
}
8、RootBeanDefinition(根Bean定义)
RootBeanDefinition
用于定义容器中的根级Bean
配置,不能继承父Bean,是独立的顶级Bean定义类。
@SuppressWarnings("serial")
public class RootBeanDefinition extends AbstractBeanDefinition {
// 此属性用于保存一个被该bean定义装饰增强的Bean定义
@Nullable
private BeanDefinitionHolder decoratedDefinition;
// Bean定义的注解信息
@Nullable
private AnnotatedElement qualifiedElement;
...
// 目标类型,表示包含泛型的类型
@Nullable
volatile ResolvableType targetType;
// 缓存解析后的目标类型
@Nullable
volatile Class<?> resolvedTargetType;
// 缓存已解析的销毁方法的名称
@Nullable
volatile String resolvedDestroyMethodName;
// 缓存解析后的构造函数或工厂方法
@Nullable
Executable resolvedConstructorOrFactoryMethod;
// 缓存完全解析的构造函数参数
@Nullable
Object[] resolvedConstructorArguments;
...
// 创建一个新的 RootBeanDefinition,通过其 bean 属性和配置方法进行配置
public RootBeanDefinition() {
super();
}
// 创建一个新的RootBeanDefinition用于带有作用域的bean,通过给定的supplier构造每个实例
public <T> RootBeanDefinition(@Nullable Class<T> beanClass, String scope, @Nullable Supplier<T> instanceSupplier) {
super();
setBeanClass(beanClass);
setScope(scope);
setInstanceSupplier(instanceSupplier);
}
// ...省略其他构造方法
// 省略了一些其他注释,以节省篇幅
// 克隆 RootBeanDefinition
@Override
public RootBeanDefinition cloneBeanDefinition() {
return new RootBeanDefinition(this);
}
// ... 省略重写 equal 和 toString方法
}
9、AnnotatedBeanDefinition(注解Bean定义)
AnnotatedBeanDefinition
是一个扩展了BeanDefinition
的接口,用于访问与Bean类相关的注解元数据
,如类级注解和工厂方法的元数据。
public interface AnnotatedBeanDefinition extends BeanDefinition {
// 获取当前Bean类的注解信息,允许在不加载类的情况下访问类级注解元数据
AnnotationMetadata getMetadata();
// 返回当前 Bean 定义的工厂方法的元数据,如果没有工厂方法则返回 null
@Nullable
MethodMetadata getFactoryMethodMetadata();
}
10、ScannedGenericBeanDefinition(扫描通用Bean定义)
ScannedGenericBeanDefinition
是Spring中用于表示通过类路径扫描(如 @ComponentScan
)发现的Bean的定义类,包含了扫描到的Bean类的元数据和配置信息。
// 该类不会在早期加载Bean的Class,而是从 ".class" 文件本身解析所有相关的元数据,
// 使用 ASM ClassReader 进行解析
@SuppressWarnings("serial")
public class ScannedGenericBeanDefinition extends GenericBeanDefinition implements AnnotatedBeanDefinition {
// 存储扫描到的 Bean 类的注解元数据
private final AnnotationMetadata metadata;
// 为给定的 MetadataReader 描述的类创建一个新的 ScannedGenericBeanDefinition。
public ScannedGenericBeanDefinition(MetadataReader metadataReader) {
// 校验 metadataReader 不为 null
Assert.notNull(metadataReader, "MetadataReader must not be null");
// 从 MetadataReader 获取注解元数据
this.metadata = metadataReader.getAnnotationMetadata();
// 设置 Bean 类的名称
setBeanClassName(this.metadata.getClassName());
// 设置扫描到的资源
setResource(metadataReader.getResource());
}
@Override
// 返回 Bean 类的注解元数据
public final AnnotationMetadata getMetadata() {
return this.metadata;
}
@Override
@Nullable
// 返回工厂方法的元数据(这里为 null,表示没有工厂方法)
public MethodMetadata getFactoryMethodMetadata() {
return null;
}
}
总结
本文详细介绍了Spring框架中Bean的定义
及其管理机制,重点阐述了BeanDefinition
接口及其各个实现类的功能,包括属性访问
、Bean元数据管理
、父子Bean关系
、作用域
、依赖注入
等方面的实现,旨在帮助开发者理解Spring容器如何通过这些机制来管理和配置Bean的生命周期。