剽达崖 发表于 2025-11-30 22:05:08

Spring BeanDefinitionRegistry 接口

Spring BeanDefinitionRegistry 接口

Registry 登记/注册 顾名思义, 该接口设计的目的是用于保存和管理 Bean定义描述(BeanDefinition)
org.springframework.beans.factory.support.BeanDefinitionRegistry
package org.springframework.beans.factory.support;

import org.springframework.beans.factory.BeanDefinitionStoreException;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.core.AliasRegistry;

/**
* Interface for registries that hold bean definitions, for example RootBeanDefinition
* and ChildBeanDefinition instances. Typically implemented by BeanFactories that
* internally work with the AbstractBeanDefinition hierarchy.
*
* Registry 登记/注册 顾名思义 该接口设计的目的是用于保存和管理 Bean定义描述(BeanDefinition), 例如:RootBeanDefinition 和 ChildBeanDefinition 实例
*
* <p>This is the only interface in Spring's bean factory packages that encapsulates
* <i>registration</i> of bean definitions. The standard BeanFactory interfaces
* only cover access to a <i>fully configured factory instance</i>.
*
* <p>Spring's bean definition readers expect to work on an implementation of this
* interface. Known implementors within the Spring core are DefaultListableBeanFactory
* and GenericApplicationContext.
*
* @author Juergen Hoeller
* @since 26.11.2003
* @see org.springframework.beans.factory.config.BeanDefinition
* @see AbstractBeanDefinition
* @see RootBeanDefinition
* @see ChildBeanDefinition
* @see DefaultListableBeanFactory
* @see org.springframework.context.support.GenericApplicationContext
* @see org.springframework.beans.factory.xml.XmlBeanDefinitionReader
* @see PropertiesBeanDefinitionReader
*/
public interface BeanDefinitionRegistry extends AliasRegistry {

        /**
       * Register a new bean definition with this registry.
       * Must support RootBeanDefinition and ChildBeanDefinition.
       *
       * 根据名称注册一个新的 BeanDefinition
       * @param beanName the name of the bean instance to register
       * @param beanDefinition definition of the bean instance to register
       * @throws BeanDefinitionStoreException if the BeanDefinition is invalid
       * @throws BeanDefinitionOverrideException if there is already a BeanDefinition
       * for the specified bean name and we are not allowed to override it
       * @see GenericBeanDefinition
       * @see RootBeanDefinition
       * @see ChildBeanDefinition
       */
        void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)
                        throws BeanDefinitionStoreException;

        /**
       * Remove the BeanDefinition for the given name.
       *
       * 根据名称移除一个 BeanDefinition
       * @param beanName the name of the bean instance to register
       * @throws NoSuchBeanDefinitionException if there is no such bean definition
       */
        void removeBeanDefinition(String beanName) throws NoSuchBeanDefinitionException;

        /**
       * Return the BeanDefinition for the given bean name.
       *
       * 根据名称获取 BeanDefinition
       * @param beanName name of the bean to find a definition for
       * @return the BeanDefinition for the given name (never {@code null})
       * @throws NoSuchBeanDefinitionException if there is no such bean definition
       */
        BeanDefinition getBeanDefinition(String beanName) throws NoSuchBeanDefinitionException;

        /**
       * Check if this registry contains a bean definition with the given name.
       * 检查给定名称是否已存在
       * @param beanName the name of the bean to look for
       * @return if this registry contains a bean definition with the given name
       */
        boolean containsBeanDefinition(String beanName);

        /**
       * Return the names of all beans defined in this registry.
       * @return the names of all beans defined in this registry,
       * or an empty array if none defined
       */
        String[] getBeanDefinitionNames();

        /**
       * Return the number of beans defined in the registry.
       * @return the number of beans defined in the registry
       */
        int getBeanDefinitionCount();

        /**
       * Determine whether the bean definition for the given name is overridable,
       * i.e. whether {@link #registerBeanDefinition} would successfully return
       * against an existing definition of the same name.
       * <p>The default implementation returns {@code true}.
       *
       *判定给定的名称是否允许覆盖它的 BeanDefinition
       *
       * @param beanName the name to check
       * @return whether the definition for the given bean name is overridable
       * @since 6.1
       */
        default boolean isBeanDefinitionOverridable(String beanName) {
                return true;
        }

        /**
       * Determine whether the given bean name is already in use within this registry,
       * i.e. whether there is a local bean or alias registered under this name.
       * @param beanName the name to check
       * @return whether the given bean name is already in use
       */
        boolean isBeanNameInUse(String beanName);
}DefaultListableBeanFactory 的实现

大多数情况下, 我们项目的 BeanFactory 的实例是 DefaultListableBeanFactory, 它也是一个 BeanDefinitionRegistry
org.springframework.beans.factory.support.DefaultListableBeanFactory#registerBeanDefinition
public class DefaultListableBeanFactory extends AbstractAutowireCapableBeanFactory
       implements ConfigurableListableBeanFactory, BeanDefinitionRegistry, Serializable {
      
      
       .........
       
        /**
       * 注册一个 BeanDefinition 的方法
       */
        @Override
        public void registerBeanDefinition(String beanName, BeanDefinition beanDefinition)
                        throws BeanDefinitionStoreException {

                Assert.hasText(beanName, "Bean name must not be empty");
                Assert.notNull(beanDefinition, "BeanDefinition must not be null");

                if (beanDefinition instanceof AbstractBeanDefinition abd) {
                        try {
                                abd.validate();
                        }
                        catch (BeanDefinitionValidationException ex) {
                                throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName,
                                                "Validation of bean definition failed", ex);
                        }
                }
                // 获取一下是否有这个 bean 的 BeanDefinition
                BeanDefinition existingDefinition = this.beanDefinitionMap.get(beanName);
                if (existingDefinition != null) {
                        // 如果有 且 不允许覆盖, 则抛出 BeanDefinitionOverrideException
                        if (!isBeanDefinitionOverridable(beanName)) {
                                throw new BeanDefinitionOverrideException(beanName, beanDefinition, existingDefinition);
                        }
                        else if (existingDefinition.getRole() < beanDefinition.getRole()) {
                                // e.g. was ROLE_APPLICATION, now overriding with ROLE_SUPPORT or ROLE_INFRASTRUCTURE
                                if (logger.isInfoEnabled()) {
                                        logger.info("Overriding user-defined bean definition for bean '" + beanName +
                                                        "' with a framework-generated bean definition: replacing [" +
                                                        existingDefinition + "] with [" + beanDefinition + "]");
                                }
                        }
                        else if (!beanDefinition.equals(existingDefinition)) {
                                if (logger.isDebugEnabled()) {
                                        logger.debug("Overriding bean definition for bean '" + beanName +
                                                        "' with a different definition: replacing [" + existingDefinition +
                                                        "] with [" + beanDefinition + "]");
                                }
                        }
                        else {
                                if (logger.isTraceEnabled()) {
                                        logger.trace("Overriding bean definition for bean '" + beanName +
                                                        "' with an equivalent definition: replacing [" + existingDefinition +
                                                        "] with [" + beanDefinition + "]");
                                }
                        }
                        this.beanDefinitionMap.put(beanName, beanDefinition);
                }
                else {
                        if (isAlias(beanName)) {
                                //判断下, 别名是否覆盖.
                                String aliasedName = canonicalName(beanName);
                                if (!isBeanDefinitionOverridable(aliasedName)) {
                                        if (containsBeanDefinition(aliasedName)) {// alias for existing bean definition
                                                throw new BeanDefinitionOverrideException(
                                                                beanName, beanDefinition, getBeanDefinition(aliasedName));
                                        }
                                        else {// alias pointing to non-existing bean definition
                                                throw new BeanDefinitionStoreException(beanDefinition.getResourceDescription(), beanName,
                                                                "Cannot register bean definition for bean '" + beanName +
                                                                "' since there is already an alias for bean '" + aliasedName + "' bound.");
                                        }
                                }
                                else {
                                        removeAlias(beanName);
                                }
                        }
                        if (hasBeanCreationStarted()) {
                                //bean 是否已经开始创建中. 后面再研究, 不是这个分支
                                // Cannot modify startup-time collection elements anymore (for stable iteration)
                                synchronized (this.beanDefinitionMap) {
                                        this.beanDefinitionMap.put(beanName, beanDefinition);
                                        List<String> updatedDefinitions = new ArrayList<>(this.beanDefinitionNames.size() + 1);
                                        updatedDefinitions.addAll(this.beanDefinitionNames);
                                        updatedDefinitions.add(beanName);
                                        this.beanDefinitionNames = updatedDefinitions;
                                        removeManualSingletonName(beanName);
                                }
                        }
                        else {
                                // 放到 beanDefinitionMap, key 是 beanName; value 是 beanDefinition;
                                // Still in startup registration phase
                                this.beanDefinitionMap.put(beanName, beanDefinition);
                                // 别名 添加到 beanDefinitionNames
                                this.beanDefinitionNames.add(beanName);
                                removeManualSingletonName(beanName);
                        }
                        this.frozenBeanDefinitionNames = null;
                }

                if (existingDefinition != null || containsSingleton(beanName)) {
                        resetBeanDefinition(beanName);
                }
                else if (isConfigurationFrozen()) {
                        clearByTypeCache();
                }
        }
        /**
       * 移除一个 BeanDefinition 的方法
       */
        @Override
        public void removeBeanDefinition(String beanName) throws NoSuchBeanDefinitionException {
                Assert.hasText(beanName, "'beanName' must not be empty");

                //从 beanDefinitionMap 中移除
                BeanDefinition bd = this.beanDefinitionMap.remove(beanName);
                if (bd == null) {
                        if (logger.isTraceEnabled()) {
                                logger.trace("No bean named '" + beanName + "' found in " + this);
                        }
                        throw new NoSuchBeanDefinitionException(beanName);
                }
                //bean 是否已经开始创建中
                if (hasBeanCreationStarted()) {
                        // Cannot modify startup-time collection elements anymore (for stable iteration)
                        synchronized (this.beanDefinitionMap) {
                                List<String> updatedDefinitions = new ArrayList<>(this.beanDefinitionNames);
                                updatedDefinitions.remove(beanName);
                                this.beanDefinitionNames = updatedDefinitions;
                        }
                }
                else {
                        //从 beanDefinitionNames 中移除
                        // Still in startup registration phase
                        this.beanDefinitionNames.remove(beanName);
                }
                this.frozenBeanDefinitionNames = null;

                resetBeanDefinition(beanName);
        }
    ........ 对于 DefaultListableBeanFactory 的实现主要就是使用两个集合存起来:
        /**
       * 这个 Map 存储所有已注册 BeanDefinition, 其中 key是bean主要name, value 是 BeanDefinition
       */
        private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<>(256);

        /**
       * 这个list 存储所有的 bean definition 名称
       */
        private volatile List<String> beanDefinitionNames = new ArrayList<>(256);
       
来源:程序园用户自行投稿发布,如果侵权,请联系站长删除
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!

喳谍 发表于 前天 22:41

新版吗?好像是停更了吧。
页: [1]
查看完整版本: Spring BeanDefinitionRegistry 接口