Spring:容器创建流程(源码解读)
2020-01-11 18:28
260 查看
一、前言
Spring 容器,是 Spring 框架实现其两大核心思想:IoC、AOP的基础,平时我么可能只是会享受容器带给我们的便利,对容器的了解知之甚少。
今天,我们通过 Spring 底层源码来分析 Spring 容器的构造过程,使我们对 Spring 的认识再上一个台阶,鉴于现在使用 Spring Boot 越来越多,在此将以 Servlet 类型的 AnnotationConfigServletWebServerApplicationContext 为例进行分析,对于Spring Boot 启动流程不太了解的,可以参考这里,其结构图如下:
二、容器初始化
创建 AnnotationConfigServletWebServerApplicationContext,按照 Java 的语法规则会先行调用其父类的构造方法,然后才调用自身的构造函数进行对象的创建。
在GenericApplicationContext中创建Spring IoC最重要的对象beanFactory。
public GenericApplicationContext() { this.beanFactory = new DefaultListableBeanFactory(); }
最后才会调用 AnnotationConfigServletWebServerApplicationContext 的构造函数完成 Spring 容器的创建和初始化工作。
public AnnotationConfigServletWebServerApplicationContext() { this.reader = new AnnotatedBeanDefinitionReader(this); this.scanner = new ClassPathBeanDefinitionScanner(this); }
1) 创建 AnnotatedBeanDefinitionReader,用于对带注解的Bean类进行解析、注册
public AnnotatedBeanDefinitionReader(BeanDefinitionRegistry registry) { //创建一个标准的环境对象StandardEnvironment //如果是web应用,这个环境对象将是StandardServletEnvironment //在SpringBoot项目中,该对象会被SpringBoot内核自动推断出来 this(registry, getOrCreateEnvironment(registry)); } public AnnotatedBeanDefinitionReader(BeanDefinitionRegistry registry, Environment environment) { Assert.notNull(registry, "BeanDefinitionRegistry must not be null"); Assert.notNull(environment, "Environment must not be null"); this.registry = registry; //用于对含有@Condition注解的类进行特殊解析 this.conditionEvaluator = new ConditionEvaluator(registry, environment, null); //关键步骤,会注册用于解析相关注解的处理器 AnnotationConfigUtils.registerAnnotationConfigProcessors(this.registry); }
public static Set<BeanDefinitionHolder> registerAnnotationConfigProcessors( BeanDefinitionRegistry registry, @Nullable Object source) { //从registry也就是AnnotationConfigServletWebServerApplicationContext中获取之前注册到它身上的bean工厂。 DefaultListableBeanFactory beanFactory = unwrapDefaultListableBeanFactory(registry); /** * 向Spring的beanFactory身上添加两个处理注解能力 * 1. AnnotationAwareOrderComparator是处理@oder和@Priority * 2. ContextAnnotationAutowireCandidateResolver是处理@Lazy */ if (beanFactory != null) { if (!(beanFactory.getDependencyComparator() instanceof AnnotationAwareOrderComparator)) { beanFactory.setDependencyComparator(AnnotationAwareOrderComparator.INSTANCE); } if (!(beanFactory.getAutowireCandidateResolver() instanceof ContextAnnotationAutowireCandidateResolver)) { beanFactory.setAutowireCandidateResolver(new ContextAnnotationAutowireCandidateResolver()); } } Set<BeanDefinitionHolder> beanDefs = new LinkedHashSet<>(8); /** * 以下是向bean工厂添加若干个Spring内部的配置类,这些配置类定义在org.springframework.context.annotation.AnnotationConfigUtils中 * 1.defaultListableBeanFactory.beanDefinitionMap中添加配置类的<name ,bd> * 2.defaultListableBeanFactory.beanDefinitionNames中添加bd的name */ if (!registry.containsBeanDefinition(CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(ConfigurationClassPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, CONFIGURATION_ANNOTATION_PROCESSOR_BEAN_NAME)); } if (!registry.containsBeanDefinition(AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(AutowiredAnnotationBeanPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, AUTOWIRED_ANNOTATION_PROCESSOR_BEAN_NAME)); } // Check for JSR-250 support, and if present add the CommonAnnotationBeanPostProcessor. if (jsr250Present && !registry.containsBeanDefinition(COMMON_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, COMMON_ANNOTATION_PROCESSOR_BEAN_NAME)); } // Check for JPA support, and if present add the PersistenceAnnotationBeanPostProcessor. if (jpaPresent && !registry.containsBeanDefinition(PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(); try { def.setBeanClass(ClassUtils.forName(PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME, AnnotationConfigUtils.class.getClassLoader())); } catch (ClassNotFoundException ex) { throw new IllegalStateException( "Cannot load optional framework class: " + PERSISTENCE_ANNOTATION_PROCESSOR_CLASS_NAME, ex); } def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, PERSISTENCE_ANNOTATION_PROCESSOR_BEAN_NAME)); } if (!registry.containsBeanDefinition(EVENT_LISTENER_PROCESSOR_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(EventListenerMethodProcessor.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, EVENT_LISTENER_PROCESSOR_BEAN_NAME)); } if (!registry.containsBeanDefinition(EVENT_LISTENER_FACTORY_BEAN_NAME)) { RootBeanDefinition def = new RootBeanDefinition(DefaultEventListenerFactory.class); def.setSource(source); beanDefs.add(registerPostProcessor(registry, def, EVENT_LISTENER_FACTORY_BEAN_NAME)); } return beanDefs; }
2) 创建 ClassPathBeanDefinitionScanner,
还是老规矩,先构造父类,在调用子类构造方法完成创建和初始化工作。
//定义了扫描resource文件的路径 static final String DEFAULT_RESOURCE_PATTERN = "**/*.class"; private final List<TypeFilter> includeFilters = new LinkedList<>(); private final List<TypeFilter> excludeFilters = new LinkedList<>();
public ClassPathBeanDefinitionScanner(BeanDefinitionRegistry registry) { this(registry, true); } public ClassPathBeanDefinitionScanner(BeanDefinitionRegistry registry, boolean useDefaultFilters, Environment environment, @Nullable ResourceLoader resourceLoader) { Assert.notNull(registry, "BeanDefinitionRegistry must not be null"); this.registry = registry; if (useDefaultFilters) { //在scaner.includeFilters中添加javax.annotation.ManagedBean和javax.inject.Named两种注解类型filter //@javax.annotation.ManagedBean是JAVA EE6自身提供的注解类 //@Inject、@Named、@Qualifier和@Provider是属于javax.inject.Named registerDefaultFilters(); } setEnvironment(environment); setResourceLoader(resourceLoader); }
三、容器刷新
public void refresh() throws BeansException, IllegalStateException { synchronized (this.startupShutdownMonitor) { // 为刷新做准备,设置启动时间和激活标识,初始化上下文中使用占位符的属性 prepareRefresh(); // 创建、初始化BeanFactory,加载、解析Bean的定义 ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory(); // 为BeanFactory填充功能,设置上下文的配置 prepareBeanFactory(beanFactory); try { // 子类扩展,对BeanFactory进行处理,此时所有Bean未被初始化 postProcessBeanFactory(beanFactory); // 实例化、调用已注册的BeanFactoryPostProcessors#postProcessBeanFactory方法,用于修改BeanFactory invokeBeanFactoryPostProcessors(beanFactory); // 实例化,注册BeanPostProcessor registerBeanPostProcessors(beanFactory); // 初始化MessageSource,用于国际化处理 initMessageSource(); // 初始化应用事件广播器 initApplicationEventMulticaster(); // 子类扩展、初始化一些个性化Bean onRefresh(); // 找到ApplicationListener bean,并注册 registerListeners(); // 初始化剩下的所有非lazy-init的单例Bean finishBeanFactoryInitialization(beanFactory); // 初始化LifecycleProcessor(生命周期处理器),发步对应的事件通知,如果配置了JMX,则注册MBean finishRefresh(); } catch (BeansException ex) { if (logger.isWarnEnabled()) { logger.warn("Exception encountered during context initialization - " + "cancelling refresh attempt: " + ex); } // 销毁已经创建的单例Bean destroyBeans(); // 重置active标记为false cancelRefresh(ex); // Propagate exception to caller. throw ex; } finally { // Reset common introspection caches in Spring's core, since we // might not ever need metadata for singleton beans anymore... resetCommonCaches(); } } }
- 点赞
- 收藏
- 分享
- 文章举报
相关文章推荐
- Spring IOC源码分析(七):IOC容器的设计实现与bean对象的创建流程
- Spring 容器从加载文件到创建一个完整Bean的工作流程
- Spring IOC容器启动流程源码解析(一)——容器概念详解及源码初探
- Spring 源码解读 推荐流程
- Spring源码解读-Spring IoC容器初始化之资源注册
- 深入研究Spring-IoC:源码分析容器创建
- spring容器及bean加载机制源码解读
- Spring:源码解读(IOC容器的初始化)
- Spring IOC 容器源码分析 - 创建单例 bean 的过程
- 8-spring源码3.2.18解读+spring技术内幕(IOC容器的依赖注入(反射+递归调用))
- Spring源码分析1 — 容器启动流程
- Spring:源码解读(IOC容器的依赖注入)
- Spring源码解读 :IOC容器实现BeanDefinitionReader篇(四)
- Spring源码--IoC容器创建过程
- Spring 源码解读 推荐流程
- Spring:源码解读(IOC容器的高级特性)
- Spring源码解读之核心容器上节
- Spring源码解读——Spring容器初始化 1
- spring IOC核心源码:容器创建过程
- Spring源码解读(一)——容器是如何初始化的