Spring IoC容器与应用上下文的设计与实现
SpringBoot启动流程源码分析:
SpringBoot启动流程分析(一):SpringApplication类初始化过程
SpringBoot启动流程分析(二):SpringApplication的run方法
SpringBoot启动流程分析(三):SpringApplication的run方法之prepareContext()方法
SpringBoot启动流程分析(四):IoC容器的初始化过程
SpringBoot启动流程分析(五):SpringBoot自动装配原理实现
SpringBoot启动流程分析(六):IoC容器依赖注入
笔者注释版Spring Framework与SpringBoot源码git传送门:请不要吝啬小星星
spring-framework-5.0.8.RELEASE
SpringBoot-2.0.4.RELEASE
一、前言前面我们对IoC容器的初始化过程进行了详细的分析,这个初始化过程完成的主要工作是在IoC容器中建立BeanDefinition数据映射。在此过程中并没有看到IoC容器对Bean依赖关系进行注入,接下来分析一下IoC容器是怎样对Bean的依赖关系进行注入的。
前面在refresh()-->invokeBeanFactoryPostProcessors(beanFactory);方法中已经完成了IoC容器的初始化并已经载入了我们定义的Bean的信息(BeanDefinition),现在我们开始分析依赖注入的原理。首先需要说明的是依赖注入在用户第一次向IoC容器索要Bean时触发,当然也有例外,我们可以在BeanDefinition中中通过控制lazy-init属性来让容器完成对Bean的预实例化。这个预实例化实际上也是一个依赖注入的过程,但它是在初始化过程中完成的。
二、源码分析 2.1、getBean()的过程
接着前面看refresh()方法,这已经是refresh()方法的第三篇博文了,别迷糊我们还没走出refresh()方法。
1 // AbstractApplicationContext类 2 @Override 3 public void refresh() throws BeansException, IllegalStateException { 4 synchronized (this.startupShutdownMonitor) { 5 ... 6 try { 7 ... 8 // Instantiate all remaining (non-lazy-init) singletons. 9 finishBeanFactoryInitialization(beanFactory); 10 ... 11 } 12 ... 13 } 14 } 15 // AbstractApplicationContext类 16 protected void finishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory) { 17 ... 18 // Instantiate all remaining (non-lazy-init) singletons. 19 // 实例化所有剩余的(non-lazy-init)单例。 20 beanFactory.preInstantiateSingletons(); 21 } 22 // DefaultListableBeanFactory类 23 @Override 24 public void preInstantiateSingletons() throws BeansException { 25 ... 26 // Iterate over a copy to allow for init methods which in turn register new bean definitions. 27 // While this may not be part of the regular factory bootstrap, it does otherwise work fine. 28 List<String> beanNames = new ArrayList<>(this.beanDefinitionNames); 29 // Trigger initialization of all non-lazy singleton beans... 30 for (String beanName : beanNames) { 31 RootBeanDefinition bd = getMergedLocalBeanDefinition(beanName); 32 if (!bd.isAbstract() && bd.isSingleton() && !bd.isLazyInit()) { 33 if (isFactoryBean(beanName)) { 34 Object bean = getBean(FACTORY_BEAN_PREFIX + beanName); 35 if (bean instanceof FactoryBean) { 36 final FactoryBean<?> factory = (FactoryBean<?>) bean; 37 boolean isEagerInit; 38 if (System.getSecurityManager() != null && factory instanceof SmartFactoryBean) { 39 isEagerInit = AccessController.doPrivileged((PrivilegedAction<Boolean>) 40 ((SmartFactoryBean<?>) factory)::isEagerInit, 41 getAccessControlContext()); 42 } else { 43 isEagerInit = (factory instanceof SmartFactoryBean && 44 ((SmartFactoryBean<?>) factory).isEagerInit()); 45 } 46 if (isEagerInit) { 47 getBean(beanName); 48 } 49 } 50 } else { 51 // 这里就是触发依赖注入的地方 52 getBean(beanName); 53 } 54 } 55 } 56 ... 57 }