工作中的点点滴滴spring是怎么创建Bean的?

背景

  前几天订单处理逻辑里面有个配置里面有个地方添加了一个配置项目,默认对象的一个属性配置了一个默认值是False,然后更具逻辑判断修改。因为一直说Spring的Bean默认是单例的,所以这里我就默认给自己埋了一个坑,如果这里是单例的,当第一次初始化好Bean之后,如果有一个线程过来修改了这个bean的属性,那么后面的线程读取到的配置就会是修改后的了。代码写完保存一起,然后跑起来一看,呵好家伙果然世人诚不欺我。所以抱着好奇心,我就想着看看spring到底是怎么来创建这个bean的,然后嘛接下来就是慢慢debug源码,撸起袖子就是干。

Spring创建Bean的大致过程

  首先我们从我们的测试代码开始入手,有了源头在从源头一步步来深入会方便很多。

1 public static void main(String[] args) {
2         ApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");
3         Person p= applicationContext.getBean("person", Person .class);
4         System.out.println(p.getName());
5 
6     }

一般情况我们要了解一个类的前世今生,我们可以先看一下它的关系图,这样我们也可以顺着他的类关系图来摸索,同时对于阅读源码的效率会有很大的提升。

我们从加载配置文件入手后后,进入refresh()(org.springframework.context.support.AbstractApplicationContext#refresh)方法,这个方法其实就是容器初始化的核心步骤的第一步入口了。在这个方法包含了下列的十三个相关方法:

 1     @Override
 2     public void refresh() throws BeansException, IllegalStateException {
 3         synchronized (this.startupShutdownMonitor) {
 4             // Prepare this context for refreshing.
 5             /**
 6              * 准备刷新,做一些最基本的准备化工作
 7              **/
 8             prepareRefresh();
 9             // Tell the subclass to refresh the internal bean factory.
10             /**
11              * 获得一个刷新的bean容器,实质就是获取工厂。
12              * 加载xml等配置文件,用该文件产生的BeanDefinition来创建一个工厂
13              **/
14             ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
15             // Prepare the bean factory for use in this context.
16             /**
17              * 准备bean工厂
18              **/
19             prepareBeanFactory(beanFactory);
20             try {
21                 // Allows post-processing of the bean factory in context subclasses.
22                 // 后置增强,方便扩展
23                 postProcessBeanFactory(beanFactory);
24                 // Invoke factory processors registered as beans in the context.
25                 // 实例化并且执行BeanFactoryPostProcessors
26                 invokeBeanFactoryPostProcessors(beanFactory);
27                 // Register bean processors that intercept bean creation.
28                 // 实例化并且注册所有的BeanPostProcessor
29                 registerBeanPostProcessors(beanFactory);
30                 // Initialize message source for this context.
31                 // 国际化设置,一般用不到
32                 initMessageSource();
33                 // Initialize event multicaster for this context.
34                 // 初始化应用程序的多波器和广播器
35                 initApplicationEventMulticaster();
36                 // Initialize other special beans in specific context subclasses.
37                 // 空方法,预留给子类做扩展
38                 onRefresh();
39                 // Check for listener beans and register them.
40                 // 注册监听器
41                 registerListeners();
42                 // Instantiate all remaining (non-lazy-init) singletons.
43                 // 工作中常用,面试常问。实例化所有非懒加载的实例对象
44                 finishBeanFactoryInitialization(beanFactory);
45                 // Last step: publish corresponding event.
46                 // 完成刷新
47                 finishRefresh();
48             }
49             catch (BeansException ex) {
50                 if (logger.isWarnEnabled()) {
51                     logger.warn("Exception encountered during context initialization - " +
52                             "cancelling refresh attempt: " + ex);
53                 }
54                 // Destroy already created singletons to avoid dangling resources.
55                 /**
56                  * 销毁已经创建的单例以避免悬空资源。
57                  */
58                 destroyBeans();
59                 // Reset 'active' flag.
60                 /**
61                  * 充值标记
62                  */
63                 cancelRefresh(ex);
64                 // Propagate exception to caller.
65                 throw ex;
66             }
67             finally {
68                 // Reset common introspection caches in Spring's core, since we
69                 // might not ever need metadata for singleton beans anymore...
70                 resetCommonCaches();
71             }
72         }

先看第一个方法prepareRefresh():准备刷新,做一些最基本的初始化工作。

 1 protected void prepareRefresh() {
 2         // Switch to active.
 3         // 设置开始时间
 4         this.startupDate = System.currentTimeMillis();
 5         // 关闭状态设置为false
 6         this.closed.set(false);
 7         // 活跃状态设置为true
 8         this.active.set(true);
 9         // 打印日志
10         if (logger.isDebugEnabled()) {
11             if (logger.isTraceEnabled()) {
12                 logger.trace("Refreshing " + this);
13             }
14             else {
15                 logger.debug("Refreshing " + getDisplayName());
16             }
17         }
18         // Initialize any placeholder property sources in the context environment.
19         // 初始化属性资源
20         initPropertySources();
21         // Validate that all properties marked as required are resolvable:
22         // see ConfigurablePropertyResolver#setRequiredProperties
23         // 获取环境信息,验证属性信息
24         getEnvironment().validateRequiredProperties();
25         // Store pre-refresh
26         // 存储预刷新的一些应用信息的监听器
27         if (this.earlyApplicationListeners == null) {
28             this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
29         }
30         else {
31             // Reset local application listeners to pre-refresh state.
32             this.applicationListeners.clear();
33             this.applicationListeners.addAll(this.earlyApplicationListeners);
34         }
35         // Allow for the collection of early ApplicationEvents,
36         // to be published once the multicaster is available...
37         // 创建一些监听器事件的集合
38         this.earlyApplicationEvents = new LinkedHashSet<>();
39     }

  在这个方法里面,主要是1,设置启动事件。2,设置关闭活跃的状态。3,获取环境变量并设置属性。4设置监听器以及发布事件的集合。

  我们再来看一下下面的这个,第二个方法prepareBeanFactory()获取一个新的Bean容器,这里实质上就是获取一个Bean工厂。顺便来看一下ConfigurableListableBeanFactory的关系图。

org.springframework.context.support.AbstractRefreshableApplicationContext#refreshBeanFactory

 1  // 只要进到这个方法,那么我们创建的一定是一个新的工厂
 2     @Override
 3     protected final void refreshBeanFactory() throws BeansException {
 4         if (hasBeanFactory()) {
 5             // 如果存在先销毁,后关闭
 6             destroyBeans();
 7             closeBeanFactory();
 8         }
 9         try {
10             // 创建bean工厂,这里使用的就是DefaultListableBeanFactory。此时创建的工厂里面的属性值都是默认值
11             DefaultListableBeanFactory beanFactory = createBeanFactory();
12             // 序列化id
13             beanFactory.setSerializationId(getId());
14             // 设置一些属性值
15             customizeBeanFactory(beanFactory);
16             // 加载bean的定义属性值。该方法有很多重载,非常复杂,核心是do操作
17             // 完成配置文件或者配置类文件的加载
18             loadBeanDefinitions(beanFactory);
19             synchronized (this.beanFactoryMonitor) {
20                 this.beanFactory = beanFactory;
21             }
22         }
23         catch (IOException ex) {
24             throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex);
25         }
26     }

  第三个方法prepareBeanFactory(beanFactory),初始化BeanFactory。在第二个方法中我们创建了一个BeanFactory对象,然后在这一步中我们要给这个工厂设置一些具体的属性值。

 1 protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
 2         // Tell the internal bean factory to use the context's class loader etc.
 3         // 为bean工厂设置类加载器
 4         beanFactory.setBeanClassLoader(getClassLoader());
 5         // 设置SPEL解析器
 6         beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
 7         beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));
 8 
 9         // Configure the bean factory with context callbacks.
10         // 添加一个BeanPostProcessor
11         beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
12         // 忽略对应接口的实现
13         beanFactory.ignoreDependencyInterface(EnvironmentAware.class);
14         beanFactory.ignoreDependencyInterface(EmbeddedValueResolverAware.class);
15         beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class);
16         beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class);
17         beanFactory.ignoreDependencyInterface(MessageSourceAware.class);
18         beanFactory.ignoreDependencyInterface(ApplicationContextAware.class);
19 
20         // BeanFactory interface not registered as resolvable type in a plain factory.
21         // MessageSource registered (and found for autowiring) as a bean.
22         // 注册一些依赖
23         beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);
24         beanFactory.registerResolvableDependency(ResourceLoader.class, this);
25         beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
26         beanFactory.registerResolvableDependency(ApplicationContext.class, this);
27 
28         // Register early post-processor for detecting inner beans as
29         // ApplicationListeners添加一个BeanPostProcessor增强器
30         ApplicationListeners.
31         beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));
32 
33         // Detect a LoadTimeWeaver and prepare for weaving, if found.
34         if (beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
35             beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
36             // Set a temporary ClassLoader for type matching.
37             beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
38         }
39 
40         // Register default environment beans.
41         if (!beanFactory.containsLocalBean(ENVIRONMENT_BEAN_NAME)) {
42             beanFactory.registerSingleton(ENVIRONMENT_BEAN_NAME, getEnvironment());
43         }
44         if (!beanFactory.containsLocalBean(SYSTEM_PROPERTIES_BEAN_NAME)) {
45             beanFactory.registerSingleton(SYSTEM_PROPERTIES_BEAN_NAME, getEnvironment().getSystemProperties());
46         }
47         if (!beanFactory.containsLocalBean(SYSTEM_ENVIRONMENT_BEAN_NAME)) {
48             beanFactory.registerSingleton(SYSTEM_ENVIRONMENT_BEAN_NAME, getEnvironment().getSystemEnvironment());
49         }
50     }

这一步比较简单粗暴,大都是单纯的set方法。

  我们来看下第四个方法postProcessBeanFactory(beanFactory) (org.springframework.context.support.AbstractApplicationContext#postProcessBeanFactory),这个方法是空的,它的实现都是在实现类中实现的。他作为Bean的后置增强器。

  第五个方法invokeBeanFactoryPostProcessors(beanFactory) ,实例化一个BeanFactoryPostProcessors并且执行BeanFactoryPostProcessors。

 1 /**
 2      * Instantiate and invoke all registered BeanFactoryPostProcessor beans,
 3      * respecting explicit order if given.
 4      * <p>Must be called before singleton instantiation.
 5      * 单例对象之前一定调用,因为单例bean创建后就只有一份
 6      */
 7     protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
 8         PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());
 9 
10         // Detect a LoadTimeWeaver and prepare for weaving, if found in the meantime
11         // (e.g. through an @Bean method registered by ConfigurationClassPostProcessor)
12         if (beanFactory.getTempClassLoader() == null && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
13             beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
14             beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
15         }
16     }

  第六个方法:registerBeanPostProcessors(beanFactory) ,实例化并且注册所有的BeanPostProcessor。实例化Bean之前的准备工作。

1 /**
2      * Instantiate and register all BeanPostProcessor beans,
3      * respecting explicit order if given.
4      * <p>Must be called before any instantiation of application beans.
5      */
6     protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) {
7         PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this);
8     }

  方法7:initMessageSource() => 国际化设置

  方法8:initApplicationEventMulticaster() => 初始化应用程序的多波器和广播器,也属于准备工作

  方法9:onRefresh() => 预留给子类做扩展

  方法10:registerListeners() => 注册监听器,也是属于准备工作

 1 protected void registerListeners() {
 2         // Register statically specified listeners first.
 3         for (ApplicationListener<?> listener : getApplicationListeners()) {
 4             getApplicationEventMulticaster().addApplicationListener(listener);
 5         }
 6 
 7         // Do not initialize FactoryBeans here: We need to leave all regular beans
 8         // uninitialized to let post-processors apply to them!
 9         String[] listenerBeanNames = getBeanNamesForType(ApplicationListener.class, true, false);
10         for (String listenerBeanName : listenerBeanNames) {
11             getApplicationEventMulticaster().addApplicationListenerBean(listenerBeanName);
12         }
13 
14         // Publish early application events now that we finally have a multicaster...
15         Set<ApplicationEvent> earlyEventsToProcess = this.earlyApplicationEvents;
16         this.earlyApplicationEvents = null;
17         if (earlyEventsToProcess != null) {
18             for (ApplicationEvent earlyEvent : earlyEventsToProcess) {
19                 getApplicationEventMulticaster().multicastEvent(earlyEvent);
20             }
21         }
22     }

  第十一个方法,这个方法复杂,也是核心的地方。finishBeanFactoryInitialization(beanFactory) => 实例化所有单例对象,

 1 /**
 2      * Finish the initialization of this context's bean factory,
 3      * initializing all remaining singleton beans.
 4      */
 5     protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) {
 6         // Initialize conversion service for this context.
 7         /**
 8          * 把类型转化操作,设置到当前的beanFactory里面去
 9         **/
10         if (beanFactory.containsBean(CONVERSION_SERVICE_BEAN_NAME) &&
11                 beanFactory.isTypeMatch(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)) {
12             beanFactory.setConversionService(
13                     beanFactory.getBean(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class));
14         }
15 
16         // Register a default embedded value resolver if no bean post-processor
17         // (such as a PropertyPlaceholderConfigurer bean) registered any before:
18         // at this point, primarily for resolution in annotation attribute values.
19         /**
20          * 判断当前的beanFactory有没有内置的值处理器
21         **/
22         if (!beanFactory.hasEmbeddedValueResolver()) {
23             beanFactory.addEmbeddedValueResolver(strVal -> getEnvironment().resolvePlaceholders(strVal));
24         }
25 
26         // Initialize LoadTimeWeaverAware beans early to allow for registering their transformers early.
27         /**
28          * 织入Aware
29         **/
30         String[] weaverAwareNames = beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class, false, false);
31         for (String weaverAwareName : weaverAwareNames) {
32             getBean(weaverAwareName);
33         }
34 
35         // Stop using the temporary ClassLoader for type matching.
36         // 设置类加载器
37         beanFactory.setTempClassLoader(null);
38 
39         // Allow for caching all bean definition metadata, not expecting further changes.
40         /**
41          * 冻结:某些bean不需要进行修改操作了,放入
42         **/
43         beanFactory.freezeConfiguration();
44 
45         // Instantiate all remaining (non-lazy-init) singletons.
46         /**
47          * 实例化所有非懒加载的实例对象(重要)
48         **/
49         beanFactory.preInstantiateSingletons();
50     }

  我们再来看下这一个非常重要的一步, 实例化所有非懒加载的实例对象(org.springframework.beans.factory.support.DefaultListableBeanFactory#preInstantiateSingletons)

 1 @Override
 2     public void preInstantiateSingletons() throws BeansException {
 3         if (logger.isTraceEnabled()) {
 4             logger.trace("Pre-instantiating singletons in " + this);
 5         }
 6 
 7         // Iterate over a copy to allow for init methods which in turn register new bean definitions.
 8         // While this may not be part of the regular factory bootstrap, it does otherwise work fine.
 9         /**
10          * 拿到所有注册bean的名称
11          **/
12         List<String> beanNames = new ArrayList<>(this.beanDefinitionNames);
13 
14         // Trigger initialization of all non-lazy singleton beans...
15         // 循环去创建我们需要的单例对象
16         for (String beanName : beanNames) {
17             // 拿到bean的定义信息,就是我们在xml配置文件里面指定的一些属性
18             RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName);
19             // 是否是抽象的,是否是单例的,是否是懒加载的
20             if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) {
21                 // 判断当前类是否实现了factoryBean接口。一般没实现,直接进入下面的getBean
22                 if (isFactoryBean(beanName)) {
23                     Object bean = getBean(FACTORY_BEAN_PREFIX + beanName);
24                     if (bean instanceof FactoryBean) {
25                         final FactoryBean<?> factory = (FactoryBean<?>) bean;
26                         boolean isEagerInit;
27                         if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) {
28                             isEagerInit = AccessController.doPrivileged((PrivilegedAction<Boolean>)
29                                             ((SmartFactoryBean<?>) factory)::isEagerInit,
30                                     getAccessControlContext());
31                         }
32                         else {
33                             isEagerInit = (factory instanceof SmartFactoryBean &&
34                                     ((SmartFactoryBean<?>) factory).isEagerInit());
35                         }
36                         if (isEagerInit) {
37                             getBean(beanName);
38                         }
39                     }
40                 }
41                 else {
42                     // 通过beanName。拿到bean
43                     getBean(beanName);
44                 }
45             }
46         }
47 
48         // Trigger post-initialization callback for all applicable beans...
49         for (String beanName : beanNames) {
50             Object singletonInstance = getSingleton(beanName);
51             if (singletonInstance instanceof SmartInitializingSingleton) {
52                 final SmartInitializingSingleton smartSingleton = (SmartInitializingSingleton) singletonInstance;
53                 if (System.getSecurityManager() != null) {
54                     AccessController.doPrivileged((PrivilegedAction<Object>) () -> {
55                         smartSingleton.afterSingletonsInstantiated();
56                         return null;
57                     }, getAccessControlContext());
58                 }
59                 else {
60                     smartSingleton.afterSingletonsInstantiated();
61                 }
62             }
63         }
64     }

重要方法:getMergedLocalBeanDefinition

1  // 返回一个合并好的RootBeanDefinition。整合子类和父类
2     protected RootBeanDefinition getMergedLocalBeanDefinition(String beanName) throws BeansException {
3         // Quick check on the concurrent map first, with minimal locking.
4         RootBeanDefinition mbd = this.mergedBeanDefinitions.get(beanName);
5         if (mbd != null && !mbd.stale) {
6             return mbd;
7         }
8         return getMergedBeanDefinition(beanName, getBeanDefinition(beanName));
9     }

getBean() => doGetBean()

  1 protected <T> T doGetBean( final String name, final Class<T> requiredType, final Object[] args, boolean typeCheckOnly)
  2         throws BeansException {
  3 
  4     final String beanName = transformedBeanName(name);
  5     Object bean;
  6 
  7     /*
  8      * 尝试从缓存中拿取一个bean实例。
  9      * Spring会在Bean还没完全初始化完毕的前,通过一个ObjectFactory提前暴露出bean实例,这样为解决循环依赖提供了遍历。
 10      */
 11     Object sharedInstance = getSingleton(beanName);
 12     if (sharedInstance != null && args == null) {
 13         if (logger.isDebugEnabled()) {
 14             if (isSingletonCurrentlyInCreation(beanName)) {
 15                 logger.debug("Returning eagerly cached instance of singleton bean '" + beanName +
 16                         "' that is not fully initialized yet - a consequence of a circular reference");
 17             }
 18             else {
 19                 logger.debug("Returning cached instance of singleton bean '" + beanName + "'");
 20             }
 21         }
 22         // 对FactoryBean的情况进行特殊处理。
 23         bean = getObjectForBeanInstance(sharedInstance, name, beanName, null);
 24     }
 25 
 26     else {
 27         // 如果正在创建的bean为原型并且已经正在创建,这种循环依赖是无法解决的,要抛出异常。
 28         if (isPrototypeCurrentlyInCreation(beanName)) {
 29             throw new BeanCurrentlyInCreationException(beanName);
 30         }
 31 
 32         // 如果该beanFactory中不包含要创建bean的beanDefinition,则尝试从父beanFactory中寻找。
 33         BeanFactory parentBeanFactory = getParentBeanFactory();
 34         if (parentBeanFactory != null && !containsBeanDefinition(beanName)) {
 35             String nameToLookup = originalBeanName(name);
 36             if (args != null) {
 37                 return (T) parentBeanFactory.getBean(nameToLookup, args);
 38             }
 39             else {
 40                 return parentBeanFactory.getBean(nameToLookup, requiredType);
 41             }
 42         }
 43 
 44         if (!typeCheckOnly) {
 45             markBeanAsCreated(beanName);
 46         }
 47 
 48         try {
 49             final RootBeanDefinition mbd = getMergedLocalBeanDefinition(beanName);
 50             checkMergedBeanDefinition(mbd, beanName, args);
 51 
 52             // 有些bean是有depends-on/@DependsOn的,需要先初始化这些依赖。
 53             String[] dependsOn = mbd.getDependsOn();
 54             if (dependsOn != null) {
 55                 for (String dep : dependsOn) {
 56                     if (isDependent(beanName, dep)) {
 57                         throw new BeanCreationException(mbd.getResourceDescription(), beanName,
 58                                 "Circular depends-on relationship between '" + beanName + "' and '" + dep + "'");
 59                     }
 60                     registerDependentBean(dep, beanName);
 61                     getBean(dep);
 62                 }
 63             }
 64 
 65             // 创建单例bean。
 66             if (mbd.isSingleton()) {
 67                 /*
 68                  * 调用父类DefaultSingletonBeanRegistry的getSingleton,具体创建bean的工作实际上仍然是
 69                  * 回调参数中传递的ObjectFactory#getObject方法,而createBean实际上是子类AbstractAutowireCapableBeanFactory实现的。
 70                  */
 71                 sharedInstance = getSingleton(beanName, new ObjectFactory<Object>() {
 72                     @Override
 73                     public Object getObject() throws BeansException {
 74                         try {
 75                             return createBean(beanName, mbd, args);
 76                         }
 77                         catch (BeansException ex) {
 78                             destroySingleton(beanName);
 79                             throw ex;
 80                         }
 81                     }
 82                 });
 83                 // 对FactoryBean的情况进行特殊处理。
 84                 bean = getObjectForBeanInstance(sharedInstance, name, beanName, mbd);
 85             }
 86             // 创建原型bean。
 87             else if (mbd.isPrototype()) {
 88                 Object prototypeInstance = null;
 89                 try {
 90                     // 前置处理,维护prototypesCurrentlyInCreation,加入当前bean记录。
 91                     beforePrototypeCreation(beanName);
 92                     // 委托给子类AbstractAutowireCapableBeanFactory来完成具体的创建bean工作。
 93                     prototypeInstance = createBean(beanName, mbd, args);
 94                 }
 95                 finally {
 96                     // 后置处理,维护prototypesCurrentlyInCreation信息,删除当前bean记录。
 97                     afterPrototypeCreation(beanName);
 98                 }
 99                 // 对FactoryBean的情况进行特殊处理。
100                 bean = getObjectForBeanInstance(prototypeInstance, name, beanName, mbd);
101             }
102 
103             else {
104                 String scopeName = mbd.getScope();
105                 final Scope scope = this.scopes.get(scopeName);
106                 if (scope == null) {
107                     throw new IllegalStateException("No Scope registered for scope name '" + scopeName + "'");
108                 }
109                 try {
110                     Object scopedInstance = scope.get(beanName, new ObjectFactory<Object>() {
111                         @Override
112                         public Object getObject() throws BeansException {
113                             beforePrototypeCreation(beanName);
114                             try {
115                                 return createBean(beanName, mbd, args);
116                             }
117                             finally {
118                                 afterPrototypeCreation(beanName);
119                             }
120                         }
121                     });
122                     bean = getObjectForBeanInstance(scopedInstance, name, beanName, mbd);
123                 }
124                 catch (IllegalStateException ex) {
125                     throw new BeanCreationException(beanName,
126                             "Scope '" + scopeName + "' is not active for the current thread; consider " +
127                             "defining a scoped proxy for this bean if you intend to refer to it from a singleton",
128                             ex);
129                 }
130             }
131         }
132         catch (BeansException ex) {
133             cleanupAfterBeanCreationFailure(beanName);
134             throw ex;
135         }
136     }
137 
138     // 到这里一个bean就已经创建完了,最后一步检查类型,如果不匹配会尝试转换。
139     if (requiredType != null && bean != null && !requiredType.isAssignableFrom(bean.getClass())) {
140         try {
141             return getTypeConverter().convertIfNecessary(bean, requiredType);
142         }
143         catch (TypeMismatchException ex) {
144             if (logger.isDebugEnabled()) {
145                 logger.debug("Failed to convert bean '" + name + "' to required type '" +
146                         ClassUtils.getQualifiedName(requiredType) + "'", ex);
147             }
148             throw new BeanNotOfRequiredTypeException(name, requiredType, bean.getClass());
149         }
150     }
151     return (T) bean;
152 }

上面针对AbstractBeanFactory#doGetBean方法进行了源码分析,从中我们可以看出它主要会干这几件事情:

  1. 转换beanName。
  2. 尝试从缓存的单例中拿实例。
  3. 如果要创建的bean是原型模式,且已经在尝试创建,这种循环依赖是无法解决的。
  4. 当前beanFactory不包含要创建的bean的beanDefinition,会尝试从parentBeanFactory中获取。
  5. 如果当前bean有依赖(xml的话就是有depends-on,注解的话有@DependsOn),则需要先完成那些bean的创建初始化。
  6. 针对scope分类讨论创建。我们比较关心的就是单例,其次是原型。
  7. 类型检查,并且尝试转换。
  8. 我们一般比较关心的就是单例bean和原型bean的创建。

在获取单例bean时doGetBean方法会调用父类DefaultSingletonBeanRegistry#getSingleton。可以把DefaultSingletonBeanRegistry当作一个“单例bean桶”,因为它确实就是一个用来存放单例bean的桶。但是这个桶本身不关心bean到底该怎么创建,所以对于桶里还没有的bean,它将创建bean的职责通过回调ObjectFactory#getObject来完成,而AbstractBeanFactory中传递给getSingleton方法的ObjectFactory#getObject的具体实现是调用createBean,这个方法是真正创建并初始化bean的方法,由子类AbstractAutowireCapableBeanFactory完成。
对于获取原型bean则简单多了,不用关心放到桶里缓存的事情,直接调用createBean创建就是了。

getSingleton

 1 /**
 2      * Return the (raw) singleton object registered under the given name,
 3      * creating and registering a new one if none registered yet.
 4      * @param beanName the name of the bean
 5      * @param singletonFactory the ObjectFactory to lazily create the singleton
 6      * with, if necessary
 7      * @return the registered singleton object
 8      */
 9     public Object getSingleton(String beanName, ObjectFactory<?> singletonFactory) {
10         Assert.notNull(beanName, "Bean name must not be null");
11         synchronized (this.singletonObjects) {
12             Object singletonObject = this.singletonObjects.get(beanName);
13             if (singletonObject == null) {
14                 if (this.singletonsCurrentlyInDestruction) {
15                     throw new BeanCreationNotAllowedException(beanName,
16                             "Singleton bean creation not allowed while singletons of this factory are in destruction " +
17                             "(Do not request a bean from a BeanFactory in a destroy method implementation!)");
18                 }
19                 if (logger.isDebugEnabled()) {
20                     logger.debug("Creating shared instance of singleton bean '" + beanName + "'");
21                 }
22                 beforeSingletonCreation(beanName);
23                 boolean newSingleton = false;
24                 boolean recordSuppressedExceptions = (this.suppressedExceptions == null);
25                 if (recordSuppressedExceptions) {
26                     this.suppressedExceptions = new LinkedHashSet<>();
27                 }
28                 try {
29                     // 实际上就是调用了CreateBean
30                     singletonObject = singletonFactory.getObject();
31                     newSingleton = true;
32                 }
33                 catch (IllegalStateException ex) {
34                     // Has the singleton object implicitly appeared in the meantime ->
35                     // if yes, proceed with it since the exception indicates that state.
36                     singletonObject = this.singletonObjects.get(beanName);
37                     if (singletonObject == null) {
38                         throw ex;
39                     }
40                 }
41                 catch (BeanCreationException ex) {
42                     if (recordSuppressedExceptions) {
43                         for (Exception suppressedException : this.suppressedExceptions) {
44                             ex.addRelatedCause(suppressedException);
45                         }
46                     }
47                     throw ex;
48                 }
49                 finally {
50                     if (recordSuppressedExceptions) {
51                         this.suppressedExceptions = null;
52                     }
53                     afterSingletonCreation(beanName);
54                 }
55                 if (newSingleton) {
56                     addSingleton(beanName, singletonObject);
57                 }
58             }
59             return singletonObject;
60         }
61     }

doCreateBean => 通过上方法的singletonObject = singletonFactory.getObject();进入的

  1 protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final Object[] args) throws BeanCreationException {
  2 
  3     BeanWrapper instanceWrapper = null;
  4     if (mbd.isSingleton()) {
  5         // 尝试从factoryBean缓存中获取。
  6         instanceWrapper = this.factoryBeanInstanceCache.remove(beanName);
  7     }
  8     if (instanceWrapper == null) {
  9         // 创建bean实例。
 10         instanceWrapper = createBeanInstance(beanName, mbd, args);
 11     }
 12     final Object bean = (instanceWrapper != null ? instanceWrapper.getWrappedInstance() : null);
 13     Class<?> beanType = (instanceWrapper != null ? instanceWrapper.getWrappedClass() : null);
 14 
 15     synchronized (mbd.postProcessingLock) {
 16         if (!mbd.postProcessed) {
 17             try {
 18                 applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
 19             }
 20             catch (Throwable ex) {
 21                 throw new BeanCreationException(mbd.getResourceDescription(), beanName,
 22                         "Post-processing of merged bean definition failed", ex);
 23             }
 24             mbd.postProcessed = true;
 25         }
 26     }
 27 
 28     /*
 29      * Spring为了解决单例bean的循环引用问题,会在bean还没有完全初始化完毕前通过添加singletonFactory
 30      * 使得其它bean可以拿到某个bean的实例引用。
 31      */
 32     boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
 33             isSingletonCurrentlyInCreation(beanName));
 34     if (earlySingletonExposure) {
 35         if (logger.isDebugEnabled()) {
 36             logger.debug("Eagerly caching bean '" + beanName +
 37                     "' to allow for resolving potential circular references");
 38         }
 39         addSingletonFactory(beanName, new ObjectFactory<Object>() {
 40             @Override
 41             public Object getObject() throws BeansException {
 42                 return getEarlyBeanReference(beanName, mbd, bean);
 43             }
 44         });
 45     }
 46 
 47     // 接下去初始化bean。
 48     Object exposedObject = bean;
 49     try {
 50         // 填充bean中的属性。
 51         populateBean(beanName, mbd, instanceWrapper);
 52         if (exposedObject != null) {
 53             /*
 54              * 调用初始化方法,比如:
 55              * 1. 各种aware回调
 56              * 2. 调用BeanPostProcessor#postProcessBeforeInitialization
 57              * 3. 调用InitializingBean#afterPropertiesSet, xml中的init-method
 58              * 4. 调用BeanPostProcessor#postProcessAfterInitialization
 59              */
 60             exposedObject = initializeBean(beanName, exposedObject, mbd);
 61         }
 62     }
 63     catch (Throwable ex) {
 64         if (ex instanceof BeanCreationException && beanName.equals(((BeanCreationException) ex).getBeanName())) {
 65             throw (BeanCreationException) ex;
 66         }
 67         else {
 68             throw new BeanCreationException(
 69                     mbd.getResourceDescription(), beanName, "Initialization of bean failed", ex);
 70         }
 71     }
 72 
 73     if (earlySingletonExposure) {
 74         Object earlySingletonReference = getSingleton(beanName, false);
 75         /*
 76          * 上面的getSingleton第二个参数为false表示不会主动触发early reference的创建。
 77          * 所以此处earlySingletonReference只有在bean创建过程中发现有别的bean与当前bean有循环依赖才不为空。
 78          */
 79         if (earlySingletonReference != null) {
 80             /*
 81              * 如果当前bean调用initializeBean没有增强原始bean实例,则取earlySingletonReference。
 82              * 
 83              * 举例:
 84              * BeanA与BeanB互相依赖。Srping先创建BeanA,再创建BeanB。
 85              * BeanA通过addSingletonFactory暴露了获取BeanA引用的途径。
 86              *
 87              * 在populateBean的时候需要注入BeanB,而BeanB又需要注入BeanA,
 88              * 则在获取BeanA时会调用原先BeanA暴露的ObjectFactory,继而使得earlySingletonObjects中加入了BeanA引用。
 89              *
 90              * 回到BeanA的创建过程,走到此步时,发现initializeBean没有增强原始bean实例,
 91              * 则需要取其它循环依赖bean拿BeanA时在registry留下的结果(原始bean经过SmartInstantiationAwareBeanPostProcessor#getEarlyBeanReference回调)。
 92              */
 93             if (exposedObject == bean) {
 94                 exposedObject = earlySingletonReference;
 95             }
 96             else if (!this.allowRawInjectionDespiteWrapping && hasDependentBean(beanName)) {
 97                 // 获取当前bean依赖的其它bean。
 98                 String[] dependentBeans = getDependentBeans(beanName);
 99                 // 过滤筛选出真正依赖的bean。
100                 Set<String> actualDependentBeans = new LinkedHashSet<String>(dependentBeans.length);
101                 for (String dependentBean : dependentBeans) {
102                     if (!removeSingletonIfCreatedForTypeCheckOnly(dependentBean)) {
103                         actualDependentBeans.add(dependentBean);
104                     }
105                 }
106                 /*
107                  * 举例:
108                  * BeanA与BeanB互相依赖。Srping先创建BeanA,再创建BeanB。
109                  * BeanA的创建走到这里时会抛出异常。
110                  *
111                  * 原因是上面的exposedObject != bean说明initializeBean方法的调用增强了原始的BeanA。
112                  * 而BeanB中注入的BeanA很可能是原始beanA(可能会有SmartInstantiationAwareBeanPostProcessor#getEarlyBeanReference回调,
113                  * 也就是BeanB中注入的BeanA不是此处BeanA的最终版exposedObject。
114                  */
115                 if (!actualDependentBeans.isEmpty()) {
116                     throw new BeanCurrentlyInCreationException(beanName,
117                             "Bean with name '" + beanName + "' has been injected into other beans [" +
118                             StringUtils.collectionToCommaDelimitedString(actualDependentBeans) +
119                             "] in its raw version as part of a circular reference, but has eventually been " +
120                             "wrapped. This means that said other beans do not use the final version of the " +
121                             "bean. This is often the result of over-eager type matching - consider using " +
122                             "'getBeanNamesOfType' with the 'allowEagerInit' flag turned off, for example.");
123                 }
124             }
125         }
126     }
127 
128     try {
129         registerDisposableBeanIfNecessary(beanName, bean, mbd);
130     }
131     catch (BeanDefinitionValidationException ex) {
132         throw new BeanCreationException(
133                 mbd.getResourceDescription(), beanName, "Invalid destruction signature", ex);
134     }
135 
136     return exposedObject;
137 }

在这里我们要提及一个知识点,就是Bean的循环依赖是如何解决的?

1.首先我们要明确一点就是,不是所有的循环依赖Spring都能够解决的。
  第一点:对于最简单的情况,bean为单例,且使用Autowired或者setter注入,Spring是可以解决这样的循环依赖的。通过上面的代码中我们可以看出,在一个Bean实例化后,会调用addSingletonFactory方法,在IOC容器中通过一个ObjectFactory暴露出可以获取还未完全初始化完毕的bean引用。若存在循环依赖,则依赖的bean可以在调用getBean时通过getSingleton方法获取到循环依赖的bean。
  第二点:但是Spring是不允许出现原型环的,举例来说,BeanA和BeanB循环依赖且scope都为prototype。因为prototype的bean,不会触发addSingletonFactory,即每次get这样的bean都会新创建一个。所以创建BeanA需要注入一个BeanB,而这个BeanB又需要注入一个新的BeanA,这样的循环依赖是没办法解决的。Spring会判断当前bean是否是prototype并且已经在创建中,然后抛出异常。
2.对于构造器依赖,可以作一下讨论,下面讨论的bean的scope都为单例
  如果BeanA构造器中依赖BeanB,并且BeanA先创建,则无论BeanB以哪种形式依赖BeanA,都没办法解决这样的循环依赖。因为实例化BeanA需要先得到BeanB(此时还未提前暴露引用),BeanB依赖BeanA,但是拿不到BeanA提前暴露的引用,这就形成了无限循环。这种情况会在BeanB试图获取BeanA时在beforeSingletonCreation方法抛出异常。
  如果BeanA非构造器依赖BeanB,并且BeanA先创建,BeanB即使构造器依赖BeanA,也可以进行解决循环依赖。 因为这种情况BeanB可以拿到BeanA提前暴露的引用。

createBeanInstance => 核心的创建和实例化bean的过程,由doCreateBean调用,大量的反射出现在该方法中,用来创建对象

 1 /**
 2      * Create a new instance for the specified bean, using an appropriate instantiation strategy:
 3      * factory method, constructor autowiring, or simple instantiation.
 4      * @param beanName the name of the bean
 5      * @param mbd the bean definition for the bean
 6      * @param args explicit arguments to use for constructor or factory method invocation
 7      * @return a BeanWrapper for the new instance
 8      * @see #obtainFromSupplier
 9      * @see #instantiateUsingFactoryMethod
10      * @see #autowireConstructor
11      * @see #instantiateBean
12      */
13     protected BeanWrapper createBeanInstance(String beanName, RootBeanDefinition mbd, @Nullable Object[] args) {
14         // Make sure bean class is actually resolved at this point.
15         Class<?> beanClass = resolveBeanClass(mbd, beanName);
16 
17         if (beanClass != null && !Modifier.isPublic(beanClass.getModifiers()) && !mbd.isNonPublicAccessAllowed()) {
18             throw new BeanCreationException(mbd.getResourceDescription(), beanName,
19                     "Bean class isn't public, and non-public access not allowed: " + beanClass.getName());
20         }
21 
22         Supplier<?> instanceSupplier = mbd.getInstanceSupplier();
23         if (instanceSupplier != null) {
24             return obtainFromSupplier(instanceSupplier, beanName);
25         }
26 
27         if (mbd.getFactoryMethodName() != null) {
28             return instantiateUsingFactoryMethod(beanName, mbd, args);
29         }
30 
31         // Shortcut when re-creating the same bean...
32         boolean resolved = false;
33         boolean autowireNecessary = false;
34         if (args == null) {
35             synchronized (mbd.constructorArgumentLock) {
36                 if (mbd.resolvedConstructorOrFactoryMethod != null) {
37                     resolved = true;
38                     autowireNecessary = mbd.constructorArgumentsResolved;
39                 }
40             }
41         }
42         if (resolved) {
43             if (autowireNecessary) {
44                 return autowireConstructor(beanName, mbd, null, null);
45             }
46             else {
47                 return instantiateBean(beanName, mbd);
48             }
49         }
50 
51         // Candidate constructors for autowiring?
52         // 构造器
53         Constructor<?>[] ctors = determineConstructorsFromBeanPostProcessors(beanClass, beanName);
54         if (ctors != null || mbd.getResolvedAutowireMode() == AUTOWIRE_CONSTRUCTOR ||
55                 mbd.hasConstructorArgumentValues() || !ObjectUtils.isEmpty(args)) {
56             return autowireConstructor(beanName, mbd, ctors, args);
57         }
58 
59         // Preferred constructors for default construction?
60         ctors = mbd.getPreferredConstructors();
61         if (ctors != null) {
62             return autowireConstructor(beanName, mbd, ctors, null);
63         }
64 
65         // No special handling: simply use no-arg constructor.
66         /**
67          * 默认无参构造
68          **/
69         return instantiateBean(beanName, mbd);
70     }

instantiateBean(beanName, mbd) => 默认无参构造

 1 /**
 2      * Instantiate the given bean using its default constructor.
 3      * @param beanName the name of the bean
 4      * @param mbd the bean definition for the bean
 5      * @return a BeanWrapper for the new instance
 6      */
 7     protected BeanWrapper instantiateBean(final String beanName, final RootBeanDefinition mbd) {
 8         try {
 9             Object beanInstance;
10             final BeanFactory parent = this;
11             if (System.getSecurityManager() != null) {
12                 beanInstance = AccessController.doPrivileged((PrivilegedAction<Object>) () ->
13                         // 实例化只会分配内存空间,设置默认值
14                         getInstantiationStrategy().instantiate(mbd, beanName, parent),
15                         getAccessControlContext());
16             }
17             else {
18                 beanInstance = getInstantiationStrategy().instantiate(mbd, beanName, parent);
19             }
20             BeanWrapper bw = new BeanWrapperImpl(beanInstance);
21             initBeanWrapper(bw);
22             return bw;
23         }
24         catch (Throwable ex) {
25             throw new BeanCreationException(
26                     mbd.getResourceDescription(), beanName, "Instantiation of bean failed", ex);
27         }
28     }

instantiate

 1 @Override
 2     public Object instantiate(RootBeanDefinition bd, @Nullable String beanName, BeanFactory owner) {
 3         // Don't override the class with CGLIB if no overrides.
 4         if (!bd.hasMethodOverrides()) {
 5             Constructor<?> constructorToUse;
 6             synchronized (bd.constructorArgumentLock) {
 7                 constructorToUse = (Constructor<?>) bd.resolvedConstructorOrFactoryMethod;
 8                 if (constructorToUse == null) {
 9                     final Class<?> clazz = bd.getBeanClass();
10                     if (clazz.isInterface()) {
11                         throw new BeanInstantiationException(clazz, "Specified class is an interface");
12                     }
13                     try {
14                         if (System.getSecurityManager() != null) {
15                             constructorToUse = AccessController.doPrivileged(
16                                     (PrivilegedExceptionAction<Constructor<?>>) clazz::getDeclaredConstructor);
17                         }
18                         else {
19                             constructorToUse = clazz.getDeclaredConstructor();
20                         }
21                         bd.resolvedConstructorOrFactoryMethod = constructorToUse;
22                     }
23                     catch (Throwable ex) {
24                         throw new BeanInstantiationException(clazz, "No default constructor found", ex);
25                     }
26                 }
27             }
28             return BeanUtils.instantiateClass(constructorToUse);
29         }
30         else {
31             // Must generate CGLIB subclass.
32             return instantiateWithMethodInjection(bd, beanName, owner);
33         }
34     }

BeanUtils.instantiateClass => 通过构造器反射创建bean

 1 /**
 2      * Convenience method to instantiate a class using the given constructor.
 3      * <p>Note that this method tries to set the constructor accessible if given a
 4      * non-accessible (that is, non-public) constructor, and supports Kotlin classes
 5      * with optional parameters and default values.
 6      * @param ctor the constructor to instantiate
 7      * @param args the constructor arguments to apply (use {@code null} for an unspecified
 8      * parameter, Kotlin optional parameters and Java primitive types are supported)
 9      * @return the new instance
10      * @throws BeanInstantiationException if the bean cannot be instantiated
11      * @see Constructor#newInstance
12      */
13     public static <T> T instantiateClass(Constructor<T> ctor, Object... args) throws BeanInstantiationException {
14         Assert.notNull(ctor, "Constructor must not be null");
15         try {
16             ReflectionUtils.makeAccessible(ctor);
17             if (KotlinDetector.isKotlinReflectPresent() && KotlinDetector.isKotlinType(ctor.getDeclaringClass())) {
18                 return KotlinDelegate.instantiateClass(ctor, args);
19             }
20             else {
21                 Class<?>[] parameterTypes = ctor.getParameterTypes();
22                 Assert.isTrue(args.length <= parameterTypes.length, "Can't specify more arguments than constructor parameters");
23                 Object[] argsWithDefaultValues = new Object[args.length];
24                 for (int i = 0 ; i < args.length; i++) {
25                     if (args[i] == null) {
26                         Class<?> parameterType = parameterTypes[i];
27                         argsWithDefaultValues[i] = (parameterType.isPrimitive() ? DEFAULT_TYPE_VALUES.get(parameterType) : null);
28                     }
29                     else {
30                         argsWithDefaultValues[i] = args[i];
31                     }
32                 }
33                 return ctor.newInstance(argsWithDefaultValues);
34             }
35         }
36         catch (InstantiationException ex) {
37             throw new BeanInstantiationException(ctor, "Is it an abstract class?", ex);
38         }
39         catch (IllegalAccessException ex) {
40             throw new BeanInstantiationException(ctor, "Is the constructor accessible?", ex);
41         }
42         catch (IllegalArgumentException ex) {
43             throw new BeanInstantiationException(ctor, "Illegal arguments for constructor", ex);
44         }
45         catch (InvocationTargetException ex) {
46             throw new BeanInstantiationException(ctor, "Constructor threw exception", ex.getTargetException());
47         }
48     }

方法12:finishRefresh() => 完成刷新

 1 /**
 2      * Finish the refresh of this context, invoking the LifecycleProcessor's
 3      * onRefresh() method and publishing the
 4      * {@link org.springframework.context.event.ContextRefreshedEvent}.
 5      */
 6     protected void finishRefresh() {
 7         // Clear context-level resource caches (such as ASM metadata from scanning).
 8         // 
 9         clearResourceCaches();
10 
11         // Initialize lifecycle processor for this context.
12         initLifecycleProcessor();
13 
14         // Propagate refresh to lifecycle processor first.
15         getLifecycleProcessor().onRefresh();
16 
17         // Publish the final event.
18         publishEvent(new ContextRefreshedEvent(this));
19 
20         // Participate in LiveBeansView MBean, if active.
21         LiveBeansView.registerApplicationContext(this);
22     }

方法13:resetCommonCaches() => 缓存重置

 1 /**
 2      * Reset Spring's common reflection metadata caches, in particular the
 3      * {@link ReflectionUtils}, {@link AnnotationUtils}, {@link ResolvableType}
 4      * and {@link CachedIntrospectionResults} caches.
 5      * @since 4.2
 6      * @see ReflectionUtils#clearCache()
 7      * @see AnnotationUtils#clearCache()
 8      * @see ResolvableType#clearCache()
 9      * @see CachedIntrospectionResults#clearClassLoader(ClassLoader)
10      */
11     protected void resetCommonCaches() {
12         ReflectionUtils.clearCache();
13         AnnotationUtils.clearCache();
14         ResolvableType.clearCache();
15         CachedIntrospectionResults.clearClassLoader(getClassLoader());
16     }

 搞清楚整个Spring IOC容器创建Bean的过程,对于阅读源码的效率会有很大的提升。

下面梳理一下整个过程:

步骤一:由spring创建一个BeanFactory。
⁣步骤二:BeanFactory通过AbstractApplicationContext的不同的实现类可以从xml,java配置或者注解中加载BeanDefinition,也就是spring bean的建模对象,如springbean当中的scope、lazy,以及属性和方法等等其他信息。
⁣步骤三,实例化BeanFactoryPostProcessor,他是实现spring容器功能扩展的重要接口,例如修改bean属性值,实现bean动态代理等。
⁣步骤四,创建Bean对象,首先获取对象的实例,然后 通过populateBean填充属性,已经通过上一步中的PostProcessor后置处理器对BeanFactory的相关信息修改或者扩展。
⁣步骤五,调用相关的Aware接口方法设置对应的属性值,比如BeanNameAware来setBeanName。BeanClassLoaderAware来设置类加载器等。
⁣步骤六,调用Bean的Init_method方法。
⁣步骤七,调用BeanPostProcessor来增强Bean,完成对Bean的修改或者扩展。

原文地址:https://www.cnblogs.com/yangkangIT/p/7613893.html