Spring源码解析之BeanDefinition

通过阅读本文你能获得什么

  • 1、什么是BeanDefinition
  • 2、怎么用BeanDefinition定制化开发

为什么要学习BeanDefinition

BeanDefinition看名称可以大致明白是用来描述spring中bean的信息。
如果把spring创建bean类比成工厂生产糖果,工厂生产糖果需要有原材料,没有原材料就没办法生产。那BeanDefinition就是spring创建bean的原材料。可以发现BeanDefinition对整个spring工厂 来说是多么重要,基于这个愿意,给大家分享一下最近学习的BeanDefinition相关的知识

BeanDefinition的定义

上边是类比了一个例子,说BeanDefinition工厂的原材料,但是对于还没有看过Spring源码的人来说,可能还不是很明白。那我这里为大家画一张图,来解释一下。

再来看一下源码中对BD的解释

/**
 * A BeanDefinition describes a bean instance, which has property values,
 * constructor argument values, and further information supplied by
 * concrete implementations.
 */
public interface BeanDefinition extends AttributeAccessor, BeanMetadataElement {
   }

从上边的注视中我们可以看到A BeanDefinition describes a bean instance, which has property values ,constructor argument values, and further information supplied by concrete implementations.这句话 翻译过来就是BeanDefinition描述了一个bean实例,该实例具有属性值,构造函数参数值以及具体实现所提供的更多信息。

AttributeAccessor于BeanMetadataElement 这两个接口会在下边进行介绍

BeanDefinition的类型

先来看一张BeanDefinition的继承关系
BeanDefinition

从上图中我们看到有以下几个主要的BeanDefinition ,每种BD在spring中的作用不同

  1. RootBeanDefinition

这个最简单的解释就是在spring中源码中涉及到合并BeanDefinition的时候返回的值都是使用RootBeanDefinition来接受。所以我们可以先理解为它表示合并后的BeanDefinition信息。

  1. ChildBeanDefinition

看名称我们就能知道这个BeanDefinition应该来表示子的关系,那谁来表示父BD呢?我们可以通过setParentName来手动设置一个父。因为ChildBeanDefinition的构造方法都必须填ParentName所以他只能表示子的概念。
通过javaDoc发现这个类从2.5开始就废弃了推荐使用GenericBeanDefinition

  1. GenericBeanDefinition

GenericBeanDefinition可以理解为一个通用的BD,因为他既可以表示父也可以表示子,并且javadoc中也明确表示推荐使用。但是为什么不能完全替代RootBeanDefinition?还是如上边说的,因为spring源码中写死了

  1. AnnotatedBeanDefinition

这个相当于一个标示入口,通过注解编程的spring项目,会以这个bean为入口解析配置类

  1. AnnotatedGenericBeanDefinition

在解析时是注解的类形成的BeanDefinition

  1. ScannedGenericBeanDefinition

在解析时通过scan扫描出来的类形成的BeanDefinition

  1. ConfigurationClassBeanDefinition

标注了@Bean方法创建的beanDefinition

后边这四种BeanDefinition可以理解为自身带有属性因为的BeanDefinition,因为源码中有的会判断instance of 哪个类型来做不同的逻辑处理

BeanDefinition的属性的意义

因为属性比较多,所以直接当作注视写在代码中

package org.springframework.beans.factory.config;

import org.springframework.beans.BeanMetadataElement;
import org.springframework.beans.MutablePropertyValues;
import org.springframework.beans.factory.support.ChildBeanDefinition;
import org.springframework.beans.factory.support.RootBeanDefinition;
import org.springframework.core.AttributeAccessor;
import org.springframework.lang.Nullable;

/**
 * A BeanDefinition describes a bean instance, which has property values,
 * constructor argument values, and further information supplied by
 * concrete implementations.
 *
 * <p>This is just a minimal interface: The main intention is to allow a
 * {@link BeanFactoryPostProcessor} such as {@link PropertyPlaceholderConfigurer}
 * to introspect and modify property values and other bean metadata.
 *
 * @author Juergen Hoeller
 * @author Rob Harrop
 * @since 19.03.2004
 * @see ConfigurableListableBeanFactory#getBeanDefinition
 * @see org.springframework.beans.factory.support.RootBeanDefinition
 * @see org.springframework.beans.factory.support.ChildBeanDefinition
 */
public interface BeanDefinition extends AttributeAccessor, BeanMetadataElement {
   

	/**
	 * beanDefinition 中的常量值 代表 原型 主要是方便我们程序员在外部调用可以直接使用
	 * Scope identifier for the standard singleton scope: "singleton".
	 * <p>Note that extended bean factories might support further scopes.
	 * @see #setScope
	 */
	String SCOPE_SINGLETON = ConfigurableBeanFactory.SCOPE_SINGLETON;

	/**
	 * beanDefinition 中的常量值 代表 原型 主要是方便我们程序员在外部调用可以直接使用
	 * Scope identifier for the standard prototype scope: "prototype".
	 * <p>Note that extended bean factories might support further scopes.
	 * @see #setScope
	 */
	String SCOPE_PROTOTYPE = ConfigurableBeanFactory.SCOPE_PROTOTYPE;


	/**
	 * 来标示这个BeanDefinition是应用程序的主要部分通常对应于用户定义的bean
	 * Role hint indicating that a {@code BeanDefinition} is a major part
	 * of the application. Typically corresponds to a user-defined bean.
	 */
	int ROLE_APPLICATION = 0;

	/**
	 * 相对于 ROLE_APPLICATION 而言 ROLE_SUPPORT 不是当前应用的主要部分
	 * Role hint indicating that a {@code BeanDefinition} is a supporting
	 * part of some larger configuration, typically an outer
	 * {@link org.springframework.beans.factory.parsing.ComponentDefinition}.
	 * {@code SUPPORT} beans are considered important enough to be aware
	 * of when looking more closely at a particular
	 * {@link org.springframework.beans.factory.parsing.ComponentDefinition},
	 * but not when looking at the overall configuration of an application.
	 */
	int ROLE_SUPPORT = 1;

	/**
	 * BeanDefinition 来表式完全在内部起作用的bean 不为我们外部程序员使用
	 * Role hint indicating that a {@code BeanDefinition} is providing an
	 * entirely background role and has no relevance to the end-user. This hint is
	 * used when registering beans that are completely part of the internal workings
	 * of a {@link org.springframework.beans.factory.parsing.ComponentDefinition}.
	 */
	int ROLE_INFRASTRUCTURE = 2;


	// Modifiable attributes

	/**
	 * 如果需要给当前的设置BD设置父定义 则通过这个方法来设置
	 * 结合abstract 来看
	 * 当前beanDefinition会继承父BD中的信息 子BD有则覆盖
	 * Set the name of the parent definition of this bean definition, if any.
	 */
	void setParentName(@Nullable String parentName);

	/**
	 *	获取设置的父定义的名称
	 * Return the name of the parent definition of this bean definition, if any.
	 */
	@Nullable
	String getParentName();

	/**
	 * 设置bean的class name   实例化的使用使用的类型
	 * Specify the bean class name of th
  • 4
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值