1、Spring源码解析 - getBean

1、启动方法
public static void main(String[] args) {
   
    ClassPathXmlApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");
    Dog dog = (Dog) applicationContext.getBean("wangcai");
}

2、调用getBean方法,从IOC容器中获取对应的Bean实例

org.springframework.context.support.AbstractApplicationContext#getBean(java.lang.String)

@Override
public Object getBean(String name) throws BeansException {
   
   assertBeanFactoryActive();
   // 根据Bean的名称从Bean工厂中获取对应的Bean实例
   // getBeanFactory() => 2.1
   // getBean() => 3
   return getBeanFactory().getBean(name);
}

2.1、获取Bean工厂,这里默认为DefaultListableBeanFactory
org.springframework.context.support.AbstractApplicationContext#getBeanFactory(java.lang.String)
@Override
public final ConfigurableListableBeanFactory getBeanFactory() {
   
    // 此处的beanFactory是DefaultListableBeanFactory实例对象
    DefaultListableBeanFactory beanFactory = this.beanFactory;
    if (beanFactory == null) {
   
        throw new IllegalStateException("BeanFactory not initialized or already closed - " +
                                        "call 'refresh' before accessing beans via the ApplicationContext");
    }
    return beanFactory;
}

3、根据名称从DefaultListableBeanFactory中获取Bean实例

org.springframework.beans.factory.support.AbstractBeanFactory#getBean(java.lang.String)

@Override
public Object getBean(String name) throws BeansException {
   
   // =》4
   return doGetBean(name, null, null, false);
}

4、先从三级缓存中获取是否已经存在该类实例。如果三级缓存中不存在,则尝试从当前Bean工厂的双亲Bean工厂中获取该类实例。如果都不存在,则触发类实例的创建。

org.springframework.beans.factory.support.AbstractBeanFactory#doGetBean

protected <T> T doGetBean(
      String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly)
      throws BeansException {
   

   // 去除工厂类前的&前缀 + 转换别名 => 4.1
   String beanName = transformedBeanName(name);
   Object bean;

   // 从三级缓存中获取对应的Bean实例 => 4.2
   Object sharedInstance = getSingleton(beanName);
   if (sharedInstance != null && args == null) {
   
      if (logger.isTraceEnabled()) {
   
         if (isSingletonCurrentlyInCreation(beanName)) {
   
            logger.trace("Returning eagerly cached instance of singleton bean '" + beanName +
                  "' that is not fully initialized yet - a consequence of a circular reference");
         }
         else {
   
            logger.trace("Returning cached instance of singleton bean '" + beanName + "'");
         }
      }
      
      // 判断是否是工厂类,如果不是工厂类则直接返回传入对象,如果是工厂类则返回其负责生产的对象实例 => 4.3
      bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
   }
   else {
   
      // 判断该Bean是否正在创建中(循环依赖)
      if (isPrototypeCurrentlyInCreation(beanName)) {
   
         throw new BeanCurrentlyInCreationException(beanName);
      }

      // 获取其双亲Bean工厂
      BeanFactory parentBeanFactory = getParentBeanFactory();
      // 如果其双亲Bean工厂存在,且当前Bean工厂中不包含该Bean的定义
      if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {
   
         // 获取Bean实际名称(处理别名、工厂名称),方法内部调用了transformedBeanName => 4.1
         String nameToLookup = originalBeanName(name);
         // 从双亲Bean工厂中获取Bean实例
         if (parentBeanFactory instanceof AbstractBeanFactory) {
   
            return ((AbstractBeanFactory) parentBeanFactory).doGetBean(
                  nameToLookup, requiredType, args, typeCheckOnly);
         }
         else if (args != null) {
   
            return (T) parentBeanFactory.getBean(nameToLookup, args);
         }
         else if (requiredType != null) {
   
            return parentBeanFactory.getBean(nameToLookup, requiredType);
         }
         else {
   
            return (T) parentBeanFactory.getBean(nameToLookup);
         }
      }

      if (!typeCheckOnly) {
   
         // 标记当前Bean正在创建中,避免重复创建
         markBeanAsCreated(beanName);
      }

      StartupStep beanCreation = this.applicationStartup.start("spring.beans.instantiate")
            .tag("beanName", name);
      try {
   
         if (requiredType != null) {
   
            beanCreation.tag("beanType", requiredType::toString);
         }
         
         // 合并Bean定义,并进行验证
         RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
         checkMergedBeanDefinition(mbd, beanName, args);

         // 检查依赖
         String[] dependsOn = mbd.getDependsOn();
         if (dependsOn != null) {
   
            for (String dep : dependsOn) {
   
               // 如果存在循环依赖,则抛出异常
               if (isDependent(beanName, dep)) {
   
                  throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                        "Circular depends-on relationship between '" + beanName + "' and '" + dep + "'");
               }
                
               // 将当前依赖Bean注册到当前Bean上,其底层实现形式: Map<Bean名称, 依赖Bean名称列表>
               registerDependentBean(dep, beanName);
               try {
   
                  // 触发依赖的初始化
                  getBean(dep);
               }
               catch (NoSuchBeanDefinitionException ex) {
   
                  throw new BeanCreationException(mbd.getResourceDescription(), beanName,
                        "'" + beanName + "' depends on missing bean '" + dep + "'", ex);
               }
            }
         }

         // 如果是单例对象,则触发单例对象的创建(重点)
         if (mbd.isSingleton()) {
   
            sharedInstance = getSingleton(beanName, () -> {
   
               try {
   
                  return createBean(beanName, mbd, args);
               }
               catch (BeansException ex) {
   
                  destroySingleton(beanName);
                  throw ex;
               }
            });
            // => 4.3
            bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
         }

         // 如果是多例对象,则直接创建实例对象
         else if (mbd.isPrototype()) {
   
            Object prototypeInstance = null;
            try {
   
               beforePrototypeCreation(beanName);
               prototypeInstance = createBean(beanName, mbd, args);
            }
            finally {
   
               afterPrototypeCreation(beanName);
            }
            bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
         }

         // 如果是非单例、多例对象,则去获取其作用域,查看作用域中是否存在已创建的实例对象,如果不存在则触发创建
         else {
   
            String scopeName = mbd.getScope();
            if (!StringUtils.hasLength(scopeName)) {
   
               throw new IllegalStateException("No scope name defined for bean ´" + beanName + "'");
            }
            Scope scope = this.scopes.get(scopeName);
            if (scope == null) {
   
               throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
            }
            try {
   
               Object scopedInstance = scope.get(beanName, () -> {
   
                  beforePrototypeCreation(beanName);
                  try {
   
                     return createBean(beanName, mbd, args);
                  }
                  finally {
   
                     afterPrototypeCreation(beanName);
                  }
               });
               bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
            }
            catch (IllegalStateException ex) {
   
               throw new ScopeNotActiveException(beanName, scopeName, ex);
            }
         }
      }
      catch (BeansException ex) {
   
         beanCreation.tag("exception", ex.getClass().toString());
         beanCreation.tag("message", String.valueOf(ex.getMessage()));
         cleanupAfterBeanCreationFailure(beanName);</
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值