springboot 源码解析(3) - refresh() 方法

refresh()方法

基于 springboot2.2.1.RELEASE 版本
springboot 在启动后,会调用 run 方法创建容器,在完成一系列初始化器,监听器的加载后,开始设置上下文,完成对配置类的加载解析:refresh() 方法调用了父类 AbstractApplicationContext 的refresh() 方法

@Override
	public void refresh() throws BeansException, IllegalStateException {
		synchronized (this.startupShutdownMonitor) {
			//准备刷新容器
			prepareRefresh();

			// 通知子类刷新 Bean 工厂
			ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();

			// 准备 Bean 工厂
			prepareBeanFactory(beanFactory);

			try {
				// 允许子类上下文中对beanFactory做后期处理
				postProcessBeanFactory(beanFactory);

				// 调用 BeanFactoryPostProcessor 各个实现类的方法
				invokeBeanFactoryPostProcessors(beanFactory);

				// 注册 BeanPostProcessor 的实现类,Bean 没有初始化
				registerBeanPostProcessors(beanFactory);

				//初始化ApplicationContext的MessageSource
				initMessageSource();

				//初始化ApplicationContext事件广播器
				initApplicationEventMulticaster();

				// 初始化子类特殊bean
				onRefresh();

				// 注册事件监听器
				registerListeners();

				// 初始化所有 Bean
				finishBeanFactoryInitialization(beanFactory);

				// 广播事件: 初始化完成
				finishRefresh();
			}

			catch (BeansException ex) {
				if (logger.isWarnEnabled()) {
					logger.warn("Exception encountered during context initialization - " +
							"cancelling refresh attempt: " + ex);
				}

				// 销毁 Bean
				destroyBeans();

				// 重置 active 状态;与第一个方法 prepareRefresh() 所做有点关系
				cancelRefresh(ex);

				throw ex;
			}
			……
		}
	}
prepareRefresh()
protected void prepareRefresh() {
		// 记录开启时间
		this.startupDate = System.currentTimeMillis();
		//设置启动状态
		this.closed.set(false);
		this.active.set(true);

		if (logger.isDebugEnabled()) {
			if (logger.isTraceEnabled()) {
				logger.trace("Refreshing " + this);
			}
			else {
				logger.debug("Refreshing " + getDisplayName());
			}
		}

		// 初始化属性源信息:应用启动之前替换一些属性占位符,这个方法用来方便我们后期扩展使用的方法。
		initPropertySources();

		// 校验一些必填属性
		getEnvironment().validateRequiredProperties();

		if (this.earlyApplicationListeners == null) {
			//存储预刷新事件
			this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
		}
		else {
			// 重置本地监听器状态为预刷新状态
			this.applicationListeners.clear();
			this.applicationListeners.addAll(this.earlyApplicationListeners);
		}

		// 当 multicaster 一旦可用的时候,立即发布事件(应用启动之前)
		this.earlyApplicationEvents = new LinkedHashSet<>();
	}
obtainFreshBeanFactory()
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
		//刷新 Bean 工厂:
		refreshBeanFactory();
		//返回 Bean 工厂:这里返回的是 GenericApplicationContext 类中的成员变量,默认的 Bean工厂(DefaultListableBeanFactory)
		return getBeanFactory();
	}
@Override
	protected final void refreshBeanFactory() throws IllegalStateException {
		//以CAS方式设置刷新转态值
		if (!this.refreshed.compareAndSet(false, true)) {
			throw new IllegalStateException(
					"GenericApplicationContext does not support multiple refresh attempts: just call 'refresh' once");
		}
		//设置Bean 工厂的序列化Id
		this.beanFactory.setSerializationId(getId());
	}
prepareBeanFactory(beanFactory)
//完成 BeanFactory 的注册功能
protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
		// 设置类加载器,没有就获取一个新的类加载器
		beanFactory.setBeanClassLoader(getClassLoader());
		//设置 EL 表达式解析器;Bean 初始化结束后填充属性用到
		beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
		//设置Bean 属性解析器
		beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));

		// 添加 ApplicationContextAwareProcessor ;目的是处理和回调实现各种 Aware 接口的 Bean
		beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
		//忽略指定的接口
		beanFactory.ignoreDependencyInterface(EnvironmentAware.class);
		beanFactory.ignoreDependencyInterface(EmbeddedValueResolverAware.class);
		beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class);
		beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class);
		beanFactory.ignoreDependencyInterface(MessageSourceAware.class);
		beanFactory.ignoreDependencyInterface(ApplicationContextAware.class);

		// 设置自身依赖
		beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);
		beanFactory.registerResolvableDependency(ResourceLoader.class, this);
		beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
		beanFactory.registerResolvableDependency(ApplicationContext.class, this);

		// 设置 Bean 后置处理器
		beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));

		// 如果当前BeanFactory 包含loadTimeWeaver Bean,则类加载器织入AspectJ,则把当前BeanFactory 交给 手指处理器 LoadTimeWeaverAwareProcessor 来处理
		if (beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
			beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
			beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
		}
		
		// 添加一些组件Bean
		if (!beanFactory.containsLocalBean(ENVIRONMENT_BEAN_NAME)) {
			beanFactory.registerSingleton(ENVIRONMENT_BEAN_NAME, getEnvironment());
		}
		if (!beanFactory.containsLocalBean(SYSTEM_PROPERTIES_BEAN_NAME)) {
			beanFactory.registerSingleton(SYSTEM_PROPERTIES_BEAN_NAME, getEnvironment().getSystemProperties());
		}
		if (!beanFactory.containsLocalBean(SYSTEM_ENVIRONMENT_BEAN_NAME)) {
			beanFactory.registerSingleton(SYSTEM_ENVIRONMENT_BEAN_NAME, getEnvironment().getSystemEnvironment());
		}
	}
总结:
	1、设置 beanFactory 属性
	2、添加后置处理器
	3、设置忽略的自动装配接口
	3、添加组件
postProcessBeanFactory(beanFactory)
//注册Web 相关请求的处理器,Bean 。添加一些Web 组件
//AnnotationConfigServletWebServerApplicationContext # postProcessBeanFactory
protected void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {
		super.postProcessBeanFactory(beanFactory);
		if (this.basePackages != null && this.basePackages.length > 0) {
			this.scanner.scan(this.basePackages);
		}
		if (!this.annotatedClasses.isEmpty()) {
			this.reader.register(ClassUtils.toClassArray(this.annotatedClasses));
		}
	}

// ServletWebServerApplicationContext # postProcessBeanFactory
protected void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {
		//设置后置处理器
		beanFactory.addBeanPostProcessor(new WebApplicationContextServletContextAwareProcessor(this));
		//忽略自动装配
		beanFactory.ignoreDependencyInterface(ServletContextAware.class);
		//注册web应用作用域
		registerWebApplicationScopes();

	}
invokeBeanFactoryPostProcessors(beanFactory)
protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
		//这个方法太长了,直接看下面画的流程图
		PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());

		// prepareBeanFactory(beanFactory) 中的 AspectJ 织入
		if (beanFactory.getTempClassLoader() == null && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
			beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
			beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
		}
	}

invokeBeanFactoryPostProcessors方法

总结:
1、调用 BeanDefinitionRegistryPostProcessor 实现向容器中添加 Bean
2、调用 BeanFactoryPostProcessor 实现向容器内 Bean 添加属性
registerBeanPostProcessors(beanFactory)

这个和上个方法很相似,通过获取当前 BeanPostProcessor 实现类 集合进行分组,添加到不同的集合中,再对这些集合中的对象排序,分组;这个方法 和 invokeBeanFactoryPostProcessors(beanFactory) 方法不同在于:这个方法只会注册BeanPostProcess并不会调用,原因在于 BeanPostProcess 在 BeanFacory 中的Bean实例化完成后在调用

总结:
1、找到 BeanpostProcessor 的实现
2、排序并分组后注册静容器内
initMessageSource()

判断 beanFactory 中是否存在 messageSourcebean,若存在,从beanFactory中获取并且判断获取的是不是HierarchicalMessageSource 类型的,如果是设置其父级消息源;反之,新建 DelegatingMessageSource 类作为messageSource 的 Bean。

总结:
1、初始化消息源属性,代码自己看吧,有上面几个方法的经验,很简单的
initApplicationEventMulticaster

初始化 ApplicationEventMulticaster
判断 beanFactory 容器中是否存在 applicationEventMulticaster 广播器;
若存在,则使用 beanFactory 中的 bean;若不存在则 新建 SimpleApplicationEventMulticaster

总结:
1、初始化时间广播器,代码自己看吧,有上面几个方法的经验,很简单的
registerListeners()
//广播器中添加监听器
protected void registerListeners() {
		for (ApplicationListener<?> listener : getApplicationListeners()) {
			getApplicationEventMulticaster().addApplicationListener(listener);
		}
		String[] listenerBeanNames = getBeanNamesForType(ApplicationListener.class, true, false);
		for (String listenerBeanName : listenerBeanNames) {
			getApplicationEventMulticaster().addApplicationListenerBean(listenerBeanName);
		}

		Set<ApplicationEvent> earlyEventsToProcess = this.earlyApplicationEvents;
		this.earlyApplicationEvents = null;
		//当监听机制还没有初始化完成时候,容器需要发布事件,这些事件会被放置在 earlyEventsToProcess 中
		if (earlyEventsToProcess != null) {
			for (ApplicationEvent earlyEvent : earlyEventsToProcess) {
				getApplicationEventMulticaster().multicastEvent(earlyEvent);
			}
		}
	}
finishBeanFactoryInitialization(beanFactory)
总结:
1、判断 beanFactory 中是否存在 转换Bean(conversionService)
2、缓存 beanDefinition 数据
3、完成上下文的 bean 工厂的初始化,初始化所有剩余的非懒加载单例 bean。
finishRefresh()
总结:
1、清除缓存
2、注册 lifecycleProcessor Bean 并刷新
3、发布最终事件:contextRefreshed
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
`refresh()` 是 Spring 框架中的一个方法,它用于刷新应用程序上下文(ApplicationContext)以更新其内部状态。在 Spring 框架中,`refresh()` 方法是非常重要的,因为它负责完成应用程序上下文的初始化和配置,并准备好所有的单例 bean 以供使用。 下面是 `refresh()` 方法的主要流程: 1. 准备刷新过程中需要用到的变量和标志位; 2. 调用 `prepareRefresh()` 方法,进行一些预处理工作; 3. 调用 `obtainFreshBeanFactory()` 方法,创建 BeanFactory 并进行一些初始化工作; 4. 调用 `prepareBeanFactory(beanFactory)` 方法,对 BeanFactory 进行一些后续处理; 5. 调用 `postProcessBeanFactory(beanFactory)` 方法,对 BeanFactory 进行后置处理; 6. 调用 `invokeBeanFactoryPostProcessors(beanFactory)` 方法,执行 BeanFactoryPostProcessor 的 postProcessBeanFactory() 方法; 7. 调用 `registerBeanPostProcessors(beanFactory)` 方法,注册 BeanPostProcessor 实例; 8. 调用 `initMessageSource()` 方法,初始化 MessageSource 组件; 9. 调用 `initApplicationEventMulticaster()` 方法,初始化 ApplicationEventMulticaster 组件; 10. 调用 `onRefresh()` 方法,进行一些自定义的刷新工作; 11. 调用 `registerListeners()` 方法,注册事件监听器; 12. 调用 `finishBeanFactoryInitialization(beanFactory)` 方法,完成所有非延迟初始化的单例 bean 的初始化工作; 13. 调用 `finishRefresh()` 方法,完成上下文的刷新工作。 需要注意的是,`refresh()` 方法在执行过程中会涉及到很多细节,比如如何处理环境变量、如何处理自定义的 bean 定义、如何处理多个上下文之间的关系等等。如果需要深入了解 `refresh()` 方法的实现细节,可以查看 Spring 框架的源代码。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值