SpringIoc源码(十六)- BeanFactory(五)- getBean(doGetBean下 - doCreateBean前的准备工作)

目录

1、getSingleton

2、createBean

1)、获取真正的Class类型

2)、初始化真正使用的RootBeanDefinition

3)、lookup-method和replace-method的处理

4)、InstantiationAwareBeanPostProcessor处理(resolveBeforeInstantiation)

5)、doCreateBean(真正的创建)


    继续AbstractBeanFactorydoGetBean分析,主要分析是5、6步骤:

    1、判断是否正在创建中

    2、判断父BeanFactory是否存在(一般都不存在,所以不分析了)

    3、调用getMergedLocalBeanDefinition方法获取BeanDefinition,并且调用checkMergedBeanDefinition方法验证    

    4、获取BeanDefinition#getDependsOn,有依赖则遍历,递归调用getBean

    5、根据BeanDefinition的scope按照单利、原型。其他类型进行初始化(当前只考虑单利类型)

    6、过调用的是getBean(A.class)类型,则需要进行转换

 

单利类型的初始化过程如下:

if (mbd.isSingleton()) {
    sharedInstance = getSingleton(beanName, () -> {
        try {
            return createBean(beanName, mbd, args);
        }
        catch (BeansException ex) {
            // Explicitly remove instance from singleton cache: It might have been put there
            // eagerly by the creation process, to allow for circular reference resolution.
            // Also remove any beans that received a temporary reference to the bean.
            destroySingleton(beanName);
            throw ex;
        }
    });
    bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
}

    与一篇博客的缓存中获取一样,先getSingleton,再getObjectForBeanInstance,因为当前不知道需要获取的是FactoryBean本身,还是FactoryBean#getObject,还是正常的Bean。主要的方法依赖于createBean初始化之后,getSingleton根据情况返回。

1、getSingleton

public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) {
    synchronized (this.singletonObjects) {
        Object singletonObject = this.singletonObjects.get(beanName);
        if (singletonObject == null) {
            if (this.singletonsCurrentlyInDestruction) {
                throw new BeanCreationNotAllowedException(beanName,
                        "Singleton bean creation not allowed while singletons of this factory are in destruction " +
                                "(Do not request a bean from a BeanFactory in a destroy method implementation!)");
            }
            if (logger.isDebugEnabled()) {
                logger.debug("Creating shared instance of singleton bean '" + beanName + "'");
            }
            beforeSingletonCreation(beanName);
            boolean newSingleton = false;
            boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
            if (recordSuppressedExceptions) {
                this.suppressedExceptions = new LinkedHashSet<>();
            }
            try {
                singletonObject = singletonFactory.getObject();
                newSingleton = true;
            }
            catch (IllegalStateException ex) {
                // Has the singleton object implicitly appeared in the meantime ->
                // if yes, proceed with it since the exception indicates that state.
                singletonObject = this.singletonObjects.get(beanName);
                if (singletonObject == null) {
                    throw ex;
                }
            }
            catch (BeanCreationException ex) {
                if (recordSuppressedExceptions) {
                    for (Exception suppressedException : this.suppressedExceptions) {
                        ex.addRelatedCause(suppressedException);
                    }
                }
                throw ex;
            }
            finally {
                if (recordSuppressedExceptions) {
                    this.suppressedExceptions = null;
                }
                afterSingletonCreation(beanName);
            }
            if (newSingleton) {
                addSingleton(beanName, singletonObject);
            }
        }
        return singletonObject;
    }
}

    在createBean完成后,会调用DefaultSingletonBeanRegistrygetSingleton方法返回Bean对象。

1、在createBean调用完后new 了Bean的抽象工厂,还是用synchronized锁住singletonObjects,当然第一次获取到的还是null

2、判断是否正在创建中

3、beforeSingletonCreation做一些判断

4、核心方法是singletonFactory.getObject();获取到单利的Bean

5、afterSingletonCreation做一些判断

6、调用addSingleton方法放入缓存中下次就能直接获取了(这里锁了两次singletonObjects对象)

protected void addSingleton(String beanName, Object singletonObject) {
    synchronized (this.singletonObjects) {
        this.singletonObjects.put(beanName, singletonObject);
        this.singletonFactories.remove(beanName);
        this.earlySingletonObjects.remove(beanName);
        this.registeredSingletons.add(beanName);
    }
}

 

2、createBean

@Override
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
        throws BeanCreationException {
    // 省略try catch的代码部分,方便清晰的看过程
    RootBeanDefinition mbdToUse = mbd;
    // 获取真正的Class
    Class<?> resolvedClass = resolveBeanClass(mbd, beanName);
    if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) {
        mbdToUse = new RootBeanDefinition(mbd);
        mbdToUse.setBeanClass(resolvedClass);
    }
    // 对Spring定义的lookup-method和replace-method的处理
    mbdToUse.prepareMethodOverrides();
   // 初始化前的InstantiationAwareBeanPostProcessor处理器(可能在这里返回对象)
    Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
    if (bean != null) {
        return bean;
    }
    // 在InstantiationAwareBeanPostProcessor没有获取到对象,则走正常创建过程(这才是真正的初始化过程)
    Object beanInstance = doCreateBean(beanName, mbdToUse, args);
    return beanInstance;
}

1)、获取真正的Class类型

protected Class<?> resolveBeanClass(final RootBeanDefinition mbd, String beanName, 
    final Class<?>... typesToMatch) throws CannotLoadBeanClassException {
    // 省略try catch部分的代码
    if (mbd.hasBeanClass()) {
        return mbd.getBeanClass();
    }
    if (System.getSecurityManager() != null) {
        return AccessController.doPrivileged((PrivilegedExceptionAction<Class<?>>) () ->
                doResolveBeanClass(mbd, typesToMatch), getAccessControlContext());
    }
    else {
        return doResolveBeanClass(mbd, typesToMatch);
    } 
}

    很多时候RootBeanDefinition没有设置beanClass,则需要解析对应的Class(设置了直接返回)。后面分析该过程。

 

2)、初始化真正使用的RootBeanDefinition

    上面解析的Class如果不为null,则需要初始化一个RootBeanDefinition,并将该Class设置进去,否则就使用传入的RootBeanDefinition即可。

3)、lookup-method和replace-method的处理

    对lookup-method和replace-method类型的标记处理而已

public void prepareMethodOverrides() throws BeanDefinitionValidationException {
    if (hasMethodOverrides()) {
        getMethodOverrides().getOverrides().forEach(this::prepareMethodOverride);
    }
}
protected void prepareMethodOverride(MethodOverride mo) 
    throws BeanDefinitionValidationException {

    int count = ClassUtils.getMethodCountForName(getBeanClass(), mo.getMethodName());
    if (count == 0) {
        throw new BeanDefinitionValidationException("省略");
    } else if (count == 1) {
        // Mark override as not overloaded, to avoid the overhead of arg type checking.
        mo.setOverloaded(false);
    }
}

4)、InstantiationAwareBeanPostProcessor处理(resolveBeforeInstantiation)

     在真正的doCreateBean之前允许InstantiationAwareBeanPostProcessor类型的BeanPostProcess,调用postProcessBeforeInstantiation方法。也可以理解,Spring不仅允许FactoryBean的getObject类型初始化Bean,还允许InstantiationAwareBeanPostProcessor返回Bean。

protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
    Object bean = null;
    if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
        // Make sure bean class is actually resolved at this point.
        if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
            Class<?> targetType = determineTargetType(beanName, mbd);
            if (targetType != null) {
                bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
                if (bean != null) {
                    bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
                }
            }
        }
        mbd.beforeInstantiationResolved = (bean != null);
    }
    return bean;
}

    applyBeanPostProcessorsBeforeInstantiation方法如下:

@Nullable
protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
    for (BeanPostProcessor bp : getBeanPostProcessors()) {
        if (bp instanceof InstantiationAwareBeanPostProcessor) {
            InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
            Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
            if (result != null) {
                return result;
            }
        }
    }
    return null;
}

    如果InstantiationAwareBeanPostProcessor处理(返回)过该Class类型的Bean,那么该Bean就没有走正常bean的生命周期(详细可以参见:Spring-Bean的作用域和生命周期),那么允许其调用一次BeanPostProcess的后置处理方法postProcessAfterInitialization,前置处理方法是修改Bean信息的,所以这里没必要回调前置方法了。就拿到所有的BeanPostProcess遍历回调即可,如下:

public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, 
    String beanName) throws BeansException {
    Object result = existingBean;
    for (BeanPostProcessor processor : getBeanPostProcessors()) {
        Object current = processor.postProcessAfterInitialization(result, beanName);
        if (current == null) {
            return result;
        }
        result = current;
    }
    return result;
}

 

5)、doCreateBean(真正的创建)

    完整的Bean的生命周期都会在这里完成,也是最复杂的过程。next专门进行分析。

 

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值