在该步SpringApplication完成了 非单例 非懒加载(通过FactoryBean定义的Bean,并且是懒加载的如果没人使用,就先不会实例化。只会到使用的时候才实例化) Bean的加载工作.并在加载前提前加入了为AOP功能切入点织入通知的类以及设置标志位告知应用不许修改BeanDefinition
这里会跑回到AbstractAutowireCapableBeanFactory.doCreateBean方法上.又复习了一次Bean生命周期
protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) { // 加载初始化类型转换Bean.这里未加载 // 已经在run方法prepareContext步加载过了(postProcessApplicationContext方法中) if (beanFactory.containsBean(CONVERSION_SERVICE_BEAN_NAME) && beanFactory.isTypeMatch(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)) { beanFactory.setConversionService( beanFactory.getBean(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)); } // Register a default embedded value resolver if no bean post-processor // (such as a PropertyPlaceholderConfigurer bean) registered any before: // at this point, primarily for resolution in annotation attribute values. if (!beanFactory.hasEmbeddedValueResolver()) { beanFactory.addEmbeddedValueResolver(strVal -> getEnvironment().resolvePlaceholders(strVal)); } // 实例化LoadTimeWeaverAware接口的bean,用于ApsectJ的类加载期织入的处理,提前加载是为了AOP功能,能为切入点织入通知.创建动态代理类 String[] weaverAwareNames = beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class, false, false); for (String weaverAwareName : weaverAwareNames) { getBean(weaverAwareName); } // 临时加载器置空,前期用临时加载器进行类型匹配工作 beanFactory.setTempClassLoader(null); // beanDefinition冻结标志位设置为True.保存beanDefinition名称快照,因为马上要加载Bean了不希望这些beanDefinition被修改 beanFactory.freezeConfiguration(); // 实例化所有非懒加载单例Bean beanFactory.preInstantiateSingletons(); }
1. DefaultListableBeanFactory.preInstantiateSingletons
获取所有的Bean名称,对单例、非懒加载的Bean进行加载(通过AbstractBeanFactory.getBean()方法).其中特别对实现SmartFactoryBean的工厂Bean做了特殊校验,如果该工厂Bean要加载的Bean是非懒加载的则立即加载出来.
public void preInstantiateSingletons() throws BeansException { if (logger.isTraceEnabled()) { logger.trace("Pre-instantiating singletons in " + this); } // 获取所有Bean名称,迭代进行Bean加载.原来的作为缓存 List<String> beanNames = new ArrayList<>(this.beanDefinitionNames); // Bean加载步骤 for (String beanName : beanNames) { // 获取该Bean的Bean定义,只能是单例、非懒加载的Bean能被加载 RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName); if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) { // 如果是工厂Bean是SmartFactoryBean类型判断该工厂要创建的单例Bean是否是懒加载 // 不是懒加载则立即加载出来.否则等需要时再加载 if (isFactoryBean(beanName)) { Object bean = getBean(FACTORY_BEAN_PREFIX + beanName); if (bean instanceof FactoryBean) { FactoryBean<?> factory = (FactoryBean<?>) bean; boolean isEagerInit; if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) { isEagerInit = AccessController.doPrivileged( (PrivilegedAction<Boolean>) ((SmartFactoryBean<?>) factory)::isEagerInit, getAccessControlContext()); } else { isEagerInit = (factory instanceof SmartFactoryBean && ((SmartFactoryBean<?>) factory).isEagerInit()); } if (isEagerInit) { getBean(beanName); } } } else { // 如果不是工厂Bean则直接加载 getBean(beanName); } } } // 执行SmartInitializingSingleton类型单例Bean的回调.类似于ContextRefreshedEvent事件监听器.但实现方便 // 所有单例非懒加载Bean加载完后调用执行. for (String beanName : beanNames) { Object singletonInstance = getSingleton(beanName); if (singletonInstance instanceof SmartInitializingSingleton) { StartupStep smartInitialize = this.getApplicationStartup().start("spring.beans.smart-initialize") .tag("beanName", beanName); SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton) singletonInstance; if (System.getSecurityManager() != null) { AccessController.doPrivileged((PrivilegedAction<Object>) () -> { smartSingleton.afterSingletonsInstantiated(); return null; }, getAccessControlContext()); } else { smartSingleton.afterSingletonsInstantiated(); } smartInitialize.end(); } } }
2. AbstractBeanFactory.getBean()方法
该方法在工厂中负责获取容器中的Bean以及当Bean不存在时去加载Bean到容器中.这里getSingleton又涉及到了循环依赖,三级缓存相关知识.
public Object getBean(String name) throws BeansException { return doGetBean(name, null, null, false); } protected <T> T doGetBean( String name, @Nullable Class<T> requiredType, @Nullable Object[] args, boolean typeCheckOnly) throws BeansException { // 获取Bean原始名称,比如工厂Bean哪里加了&则会去除,多层别名则会获取最原始的名称 String beanName = transformedBeanName(name); Object beanInstance; // 这里从容器缓存中找是否已经创建过/正在创建中(循环依赖),没有创建过则从else中执行重载方法进行对象创建. Object sharedInstance = getSingleton(beanName); if (sharedInstance != null && args == null) { if (logger.isTraceEnabled()) { // 日志说明: 如果在singletonsCurrentlyInCreation容器中找到了则表示是未完全初始化的Bean,它只是循环引用的结果 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 + "'"); } } // 获取完整Bean对象,如果不是FactoryBean则会返回本身.否则则通过工厂Bean创建Bean // 执行PostProcessorsAfterInitialization方法 beanInstance = getObjectForBeanInstance(sharedInstance, name, beanName, null); } // 如果在上面缓存中没有,也没有该它的BeanFactory,就自行创建 else { // 原型对象不允许循环创建,检查下是否是原型对象并且正在创建,是则抛出异常 if (isPrototypeCurrentlyInCreation(beanName)) { throw new BeanCurrentlyInCreationException(beanName); } // 检查是否该BeanDefinition存在于父容器中/如果父级容器存在则交由父级容器尝试加载 // 这步就是套娃检查,父容器能加载就让父容器加载了 BeanFactory parentBeanFactory = getParentBeanFactory(); if (parentBeanFactory != null && !containsBeanDefinition(beanName)) { // Not found -> check parent. String nameToLookup = originalBeanName(name); if (parentBeanFactory instanceof AbstractBeanFactory) { return ((AbstractBeanFactory) parentBeanFactory).doGetBean( nameToLookup, requiredType, args, typeCheckOnly); } else if (args != null) { // Delegation to parent with explicit args. return (T) parentBeanFactory.getBean(nameToLookup, args); } else if (requiredType != null) { // No args -> delegate to standard getBean method. return parentBeanFactory.getBean(nameToLookup, requiredType); } else { return (T) parentBeanFactory.getBean(nameToLookup); } } // 仅类型检查标志位被修改过后,则标记下该Bean已经被创建过了 if (!typeCheckOnly) { markBeanAsCreated(beanName); } StartupStep beanCreation = this.applicationStartup.start("spring.beans.instantiate") .tag("beanName", name); try { if (requiredType != null) { beanCreation.tag("beanType", requiredType::toString); } // 获取BeanDefinition.准备自己创建 RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName); // 查看该类是否是抽象类,是的话就抛出异常 checkMergedBeanDefinition(mbd, beanName, args); // 处理预先加载@DependsOn标记的依赖Bean,如果在这里有循环依赖则直接抛出异常 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 + "'"); } registerDependentBean(dep, beanName); try { getBean(dep); } catch (NoSuchBeanDefinitionException ex) { throw new BeanCreationException(mbd.getResourceDescription(), beanName, "'" + beanName + "' depends on missing bean '" + dep + "'", ex); } } } // 创建单例Bean,这里lambda表达式中createBean是调用到AbstractAutowireCapableBeanFactory.doCreateBean方法.执行Bean创建的生命周期 // AbstractBeanFactory是它的父类.所以直接使用createBean没有毛病.本身就是它自己定义的方法.执行时也是子类在执行 // 判断该Bean是单例还是多例,单例则执行doCreateBean方法.获取单例Bean并进行Bean工厂注册 // 如果是多例则调用beforePrototypeCreation和afterPrototypeCreation来记录在创建的状态,防止循环引用 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; } }); beanInstance = getObjectForBeanInstance(sharedInstance, name, beanName, mbd); } else if (mbd.isPrototype()) { // It's a prototype -> create a new instance. Object prototypeInstance = null; try { beforePrototypeCreation(beanName); prototypeInstance = createBean(beanName, mbd, args); } finally { afterPrototypeCreation(beanName); } beanInstance = 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); } }); beanInstance = 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); throw ex; } finally { beanCreation.end(); } } // 最后对Bean类型做一个适配,不符合的类型则做一下转换. return adaptBeanInstance(name, beanInstance, requiredType); }
getMergedLocalBeanDefinition(String beanName)方法
Bean定义公共的抽象类是AbstractBeanDefinition,普通的Bean在Spring加载Bean定义的时候,实例化出来的是GenericBeanDefinition,而Spring上下文包括实例化所有Bean用的AbstractBeanDefinition是RootBeanDefinition,这时候就使用getMergedLocalBeanDefinition方法做了一次转化,将非RootBeanDefinition转换为RootBeanDefinition以供后续操作
getMergedLocalBeanDefinition方法的作用就是获取缓存的BeanDefinition对象并合并其父类和本身的属性
3. DefaultSingletonBeanRegistry.getSingleton
该方法主要是做了bean创建的重复校验,Bean添加到容器中前后都判断是否重复创建了,如果有重复创建则抛出异常
beforeSingletonCreation(beanName);
,afterSingletonCreation(beanName);
.如果容器中还是没有则进行创建该Bean的操作(Bean生命周期),创建完后加入容器中.上面lambda函数就是singletonFactory.getObject();方法
public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) { Assert.notNull(beanName, "Bean name must not be null"); 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 { // 把这个实例生成出来,并且标志位设为true. 上面lambda表达式就是实现的这个方法. singletonObject = singletonFactory.getObject(); newSingleton = true; } catch (IllegalStateException ex) { // 创建异常了则判断是否已经有人加入过该Bean了 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); } // !最后将这个已经创建好的Bean加入一级缓存容器中,删除二三级缓存中对该Bean的缓存 if (newSingleton) { addSingleton(beanName, singletonObject); } } return singletonObject; } }
AbstractAutowireCapableBeanFactory.createBean
他会去调用doCreateBean方法,来实现整个Bean的实例化、初始化的生命周期流程
.所以这里可以跳过.直接看doCreateBean
protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) throws BeanCreationException { RootBeanDefinition mbdToUse = mbd; // 确认对应bean的Class已经加载解析过了 // 做一份副本用来进行类动态解析 Class<?> resolvedClass = resolveBeanClass(mbd, beanName); if (resolvedClass != null && !mbd.hasBeanClass() && mbd.getBeanClassName() != null) { mbdToUse = new RootBeanDefinition(mbd); mbdToUse.setBeanClass(resolvedClass); } // Prepare method overrides. try { // 可不看,通过配置文件进行方法重写,实现注入 mbdToUse.prepareMethodOverrides(); } catch (BeanDefinitionValidationException ex) { throw new BeanDefinitionStoreException(mbdToUse.getResourceDescription(), beanName, "Validation of method overrides failed", ex); } try { // 通过BeanPostProcessors来创建Bean的代理对象 // 该步执行InstantiationAwareBeanPostProcessor接口的Bean实例化前方法 // 具体逻辑是判断当前Spring容器是否注册了实现了InstantiationAwareBeanPostProcessor接口的后置处理器如果有 // 则依次调用其中的applyBeanPostProcessorsBeforeInstantiation方法 // 如果中间任意一个方法返回不为null,直接结束调用 Object bean = resolveBeforeInstantiation(beanName, mbdToUse); // 如果不为空,说明提前生成了实例,直接返回 if (bean != null) { return bean; } } catch (Throwable ex) { throw new BeanCreationException(mbdToUse.getResourceDescription(), beanName, "BeanPostProcessor before instantiation of bean failed", ex); } try { // Bean创建以及生命周期在这个方法中.新开一个文章介绍 Object beanInstance = doCreateBean(beanName, mbdToUse, args); if (logger.isTraceEnabled()) { logger.trace("Finished creating instance of bean '" + beanName + "'"); } return beanInstance; } catch (BeanCreationException | ImplicitlyAppearedSingletonException ex) { // A previously detected exception with proper bean creation context already, // or illegal singleton state to be communicated up to DefaultSingletonBeanRegistry. throw ex; } catch (Throwable ex) { throw new BeanCreationException( mbdToUse.getResourceDescription(), beanName, "Unexpected exception during bean creation", ex); } }
参考
spring 源码探索-- 静态AOP代理
AbstractApplicationContext.refresh方法
AbstractBeanFactory#getBean()、doGetBean完成Bean的初始化、实例化,以及BeanPostProcessor后置处理器
AbstractApplicationContext之refresh
【小家Spring】Spring IOC容器启动流程 AbstractApplicationContext#refresh()方法源码分析(二),Spring容器启动/刷新的完整总结