Spring源码系列(二) spring的启动细节

阅读须知

  • spring版本 5.2.X
  • 编译器:Idea 2021

容器启动过程

启动类

public class TestFileLoad {
	public static void main(String[] args) {
		ClassPathXmlApplicationContext ac = new ClassPathXmlApplicationContext("com/king/xmlLoad/xmlLoad.xml");

	}
}
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
	   xmlns:context="http://www.springframework.org/schema/context"
	   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	   xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
	http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">
	<context:property-override></context:property-override>
	<bean class="com.king.entity.Person">
		<property name="name" value="zhangsan"></property>
		<property name="age" value="11"></property>
	</bean>
</beans>

ClassPathXmlApplicationContext构造方法

	public ClassPathXmlApplicationContext(String configLocation) throws BeansException {
		//在此处会调用相同方法名的重载方法
		this(new String[] {configLocation}, true, null);
	}
	=================================================================
		public ClassPathXmlApplicationContext(
			String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
			throws BeansException {
		/**
		 * 调用父类的构造方法,在此时parent为null
		 * */
		super(parent);
		/**
		 * 		设置传递的configLocations(文件名称)
		 * 	在此过程中判断Environment为空的情况会调用createEnvironment()方法获取相关环境数据
		 */
		setConfigLocations(configLocations);
		if (refresh) {
			/**
			 * 在此处调用refresh进行spring的相关处理
			 * */
			refresh();
		}
	

解析配置路径 AbstractRefreshableConfigApplicationContext

org.springframework.context.support.AbstractRefreshableConfigApplicationContext

	public void setConfigLocations(@Nullable String... locations) {
		//初始化相关配置文件,加载到configLocations中
		if (locations != null) {
			Assert.noNullElements(locations, "Config locations must not be null");
			this.configLocations = new String[locations.length];
			for (int i = 0; i < locations.length; i++) {
				//当Environment为空的时候,会在此处有相关处理赋值
				this.configLocations[i] = resolvePath(locations[i]).trim();
			}
		}
		else {
			this.configLocations = null;
		}
	}

开始启动流程ClassPathXmlApplicationContext#refresh()

org.springframework.context.support.ClassPathXmlApplicationContext

Spring IOC容器对bean的装载是从refresh方法开始的,refresh()是一个模板方法,规定了IOC 容器的启动流程, 当然也定义了一些钩子函数,交给子类去实现。

refresh()方法主要为 IOC 容器 Bean 的生命周期管理提供条件,整个 refresh() 中 ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory() 这句以后代码的都是注册容器的信息源和生命周期事件,前面载入就是从这句代码开始启动。Spring IOC 容器载入 Bean 配置信息是从其子类容器的 refreshBeanFactory() 方法启动。

	@Override
	public void refresh() throws BeansException, IllegalStateException {
		synchronized (this.startupShutdownMonitor) {
            
			prepareRefresh();
			ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
			prepareBeanFactory(beanFactory);

			try {
				postProcessBeanFactory(beanFactory);
				invokeBeanFactoryPostProcessors(beanFactory);
				registerBeanPostProcessors(beanFactory);
				initMessageSource();
				initApplicationEventMulticaster();
				onRefresh();
				registerListeners();
				finishBeanFactoryInitialization(beanFactory);
				finishRefresh();
			}

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

spring的13个方法

prepareRefresh

  • 设置容器的启动时间
  • 设置活跃状态为ture
  • 设置关闭状态为false
  • 获取Environment对象,并加载当前系统的属性值到Environment对象中
  • 准备监听器和集合对象,此时默认为空的集合(此时在springBoot中有赋值)
	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());
			}
		}
		//模版方法,留给子类进行拓展工作,spring中没有相关实现
		initPropertySources();
		// 创建并获取环境对象,验证需要的环境属性是否已经放在环境中
		getEnvironment().validateRequiredProperties();
		/*
		* 判断刷新前的应用程序监听器集合是否为空,如果为空,则将监听器加到此集合中
		* 初始化一些容器,给其他拓展使用(单纯的spring没有进行赋值,springBoot有进行相关拓展)
		 * 在springMVC,springBoot中有初始化
		 *
		 * */
		if (this.earlyApplicationListeners == null) {
			this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
		}
		else {
			//如果不为空则清空集合元素对象
			this.applicationListeners.clear();
			this.applicationListeners.addAll(this.earlyApplicationListeners);
		}
		//创建刷新前的监听事件集合
		this.earlyApplicationEvents = new LinkedHashSet<>();
	}

obtainFreshBeanFactory

该方法的实现如下,通过refreshBeanFacotry重置AbstractApplicationContext持有的BeanFacotry,然后通过getBeanFacotry获得该对象再返回。

AbstractApplicationContext中refreshBeanFacoty方法和getBeanFactory方法都是抽象方法,具体实现在AbstractRefreshableApplicationContext上。

image-20210727161155771

  • 创建容器对象:DefaultListableBeanFactory
  • 加载XML等配置文件的属性值到BeanFactory中
  • 最重要的是BeanDefinition加载XML等配置文件的属性值到BeanFactory中

org.springframework.context.support.ClassPathXmlApplicationContext

	protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
		//初始化BeanFactory进行XML文件的读取工作,并将得到的BeanFactory记录当前的实体属性中
		refreshBeanFactory();
		//返回当前实体的beanFactory属性
		return getBeanFactory();
	}

org.springframework.context.support.AbstractRefreshableApplicationContext

重点在于loadBeanDefinitions方法,该抽象方法在具体实现子类上用于处理不同场景下Bean定义的加载,如Xml配置,注解配置,Web环境等,具体解析会在后面展开

protected final void refreshBeanFactory() throws BeansException {
		//判断是否存在BeanFactory,有则销毁BeanFactory
		if (hasBeanFactory()) {
			//销毁Beans
			destroyBeans();
			//关闭BeanFactory
			closeBeanFactory();
		}
		try {
			//创建DefaultListableBeanFactory对象
			DefaultListableBeanFactory beanFactory = createBeanFactory();
			//设置序列化的id,可以从id反序列化到BeanFactory对象
            //此处的id值由org.springframework.context.support.AbstractApplicationContext中定义private String id = ObjectUtils.identityToString(this);生成
			beanFactory.setSerializationId(getId());
			//定制Bean工厂,设置相关属性值,包括是否运行覆盖通名称的不同定义的对象以及循环依赖
			customizeBeanFactory(beanFactory);
			//初始化documentReader,读取Xml配置,注解配置,Web环境等
			loadBeanDefinitions(beanFactory);
			this.beanFactory = beanFactory;
		}
		catch (IOException ex) {
			throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex);
		}
	}

prepareBeanFactory

为第2步返回的BeanFactory设置基础属性。包括:

  • 设置ClassLoader

  • 设置beanFactory的表达式语言处理器,默认使用EL表达式,可以使用#{bean.xxx}的形式来调用相关属性值

  • 添加默认的属性编辑器

  • 添加后置处理器ApplicationContextAwareProcessor,在Bean初始化后自动执行各Aware接口的set方法,包括ResourceLoaderAware、ApplicationEventPublisherAware、MessageSourceAware、ApplicationContextAware、EnvironmentAware

  • 添加需要忽略的依赖注入类型,这些类型会在ApplicationContextAwareProcessor中通过BeanPostProcessor后置处理,包括第(4)点涉及的各内容预先设置用于自动依赖注入的接口对象,包括BeanFactory、ResourceLoader、ApplicationEventPublisher、ApplicationContext

  • 如果存在loadTimeWeaver这个Bean,则增加对应的后置处理器

  • 如果不存在environment,systemProperties,systemEnvironment这3个默认的环境属性Bean,则注册对应的单例,这3个对象已经在第1步中初始化完成

    这步主要预先设置公共的单例Bean并添加一些公共的后置处理动作,主要体现在BeanPostProcessor上

	protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
		//设置beanFactory的类加载器
		beanFactory.setBeanClassLoader(getClassLoader());
		//设置spring的语言表达器
		beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
		//为beanFactory增加一个默认的propertyEditor,和这个主要对bean的属性等设置管理的工具类
		//在此可以根据自已需要对指定格式进行相关解析的扩展
		beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));
		/*
		* 设置忽略Aware接口,在bean实例化之后再进行Aware接口的实现
		*
		* */
		//添加beanPostProcessor
		beanFactory.addBeanPostProcessor(new ApplicationContextAwareProcessor(this));
		/**
		* @see ApplicationContextAwareProcessor#invokeAwareInterfaces
		* 忽略的6个Aware方法会在invokeAwareInterfaces中进行相关实现
		 * 在此进行忽略是因为这些接口的实现由容器通过set方法进行注入
		 *  @autowire 接口需要set方法,故需要set方法实现,不在beanFactory方法中实现
		* */
		beanFactory.ignoreDependencyInterface(EnvironmentAware.class);
		beanFactory.ignoreDependencyInterface(EmbeddedValueResolverAware.class);
		beanFactory.ignoreDependencyInterface(ResourceLoaderAware.class);
		beanFactory.ignoreDependencyInterface(ApplicationEventPublisherAware.class);
		beanFactory.ignoreDependencyInterface(MessageSourceAware.class);
		beanFactory.ignoreDependencyInterface(ApplicationContextAware.class);
		/*
		*
		* 设置几个自动装配的特殊规则,当进行ioc初始化时有多个实现,那么就使用指定的对象进行相关注入
		* 设置相关注入优先级
		* */
		beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);
		beanFactory.registerResolvableDependency(ResourceLoader.class, this);
		beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
		beanFactory.registerResolvableDependency(ApplicationContext.class, this);
		//注册BeanPostProcessor
		beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));
		/*
		* 增加对AspectJ的支持 在java中织入分为三种方式:1 编译器植入 2 类加载器织入 3 运行期织入
		* 1 编译器织入(静态代理):采用特殊的编译器,把切面织入到类中
		* 2.类加载器织入(静态代理):通过特殊的类加载器,在字节码加载到JVM时,织入切面
		* 3.运行期织入(动态代理):  jdk动态代理(基于接口来实现)、CGlib(基于类实现)。
		*
		* AspectJ提供两种织入方式: 1 通过特殊的编译器,在编译期将AspectJ语言编写的切面类织入到java类中
		* 						  2. 类加载器织入,就是下面的LoadTimeWeaver方式
		* AOP相关准备工作
		* */
		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());
		}
	}

postProcessBeanFactory

所有Bean的定义已经加载完成,但是没有实例化,这一步可以修改bean定义或者增加自定义的bean,AbstractApplicationContext中为空实现。

image-20210727163018297

可以继承ClassPathXmlApplicationContext类进行相关自定义实现

public class MyClassPathXmlApplicationContext  extends ClassPathXmlApplicationContext {
   //拓展initPropertySource测试
   @Override
   protected void initPropertySources() {
      System.out.println("拓展initPropertySources");
      /**
       * 会在validateRequiredProperties方法中检测是否包含username,没有会抛异常
       * @see org.springframework.core.env.AbstractPropertyResolver#validateRequiredProperties
       * */
      getEnvironment().setRequiredProperties("username");
//    getEnvironment().setRequiredProperties("abc");

   }
   public MyClassPathXmlApplicationContext(String... configLocations){
      super(configLocations);
   }

   @Override
   protected void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {
      System.out.println("扩展实现beanProcessorFactory方法");
   }

   @Override
   public void addBeanFactoryPostProcessor(BeanFactoryPostProcessor postProcessor) {
      super.addBeanFactoryPostProcessor(postProcessor);
//    实现自定义的BeanPostProcessor方式一
      //方式二:在XML中将BeanPostProcessor注册为bean,详见bean.xml文件
      super.addBeanFactoryPostProcessor(new MyBeanPostProcessor());
   }
}

invokeBeanFactoryPostProcessors

在Spring容器中找出实现了BeanFactoryPostProcessor接口的Bean并执行。Spring容器会委托给PostProcessorRegistrationDelegate的invokeBeanFactoryPostProcessors方法执行

	protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
		/*
		* 获取当前应用中上下文的beanFactoryPostProcessors变量的值,并且实例化调用执行所有已经注册的beanFactoryPostProcessor
		* 默认情况下,可以通过getBeanFactoryPostProcessors()来获取已经注册的BFPP
		* */
		PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());
		if (beanFactory.getTempClassLoader() == null && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
			beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
			beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
		}
	}
	public static void invokeBeanFactoryPostProcessors(
			ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {
		//无论什么情况优先执行BeanDefinitionRegistryPostProcessors
		//将已经执行的BFPP存储在processedBeans中,防止重复执行
		Set<String> processedBeans = new HashSet<>();

		//判断BeanFactory是否是BeanDefinitionRegistry类型,此处是DefaultListableBeanFactory,实现了BeanDefinitionRegistry接口
		if (beanFactory instanceof BeanDefinitionRegistry) {
			//强制类型转换
			BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;
			/*
			* BeanFactoryPostProcessor主要针对的操作对象是BeanFactory,
			* BeanDefinitionRegistryPostProcessor主要针对BeanDefinition
			* */
			//存放BeanFactoryPostProcessor集合
			List<BeanFactoryPostProcessor> regularPostProcessors = new ArrayList<>();
			//存放BeanDefinitionRegistryPostProcessor集合
			List<BeanDefinitionRegistryPostProcessor> registryProcessors = new ArrayList<>();

			/*
			* 首先处理BeanFactoryPostProcessor,遍历所有的BeanFactoryPostProcessors
			* 将 BeanDefinitionRegistryPostProcessor 和BeanFactoryPostProcessor  区分开
			* */
			for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {
				if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
					BeanDefinitionRegistryPostProcessor registryProcessor =
							(BeanDefinitionRegistryPostProcessor) postProcessor;
					//直接执行BeanDefinitionRegistryPostProcessor接口中的postProcessBeanDefinitionRegistry方法
					//在此过程中可能会添加新的postProcessBeanFactory,故后面会有重复代码对相关新增的进行处理
					registryProcessor.postProcessBeanDefinitionRegistry(registry);
					registryProcessors.add(registryProcessor);
				}
				else {
					//普通的BeanFactoryPostProcessor,添加到相关集合,在后续集中执行postProcessBeanFactory方法
					regularPostProcessors.add(postProcessor);
				}
			}
			//用于保存本次要执行的BeanDefinitionRegistryPostProcessor
			List<BeanDefinitionRegistryPostProcessor> currentRegistryProcessors = new ArrayList<>();
			//调用所有实现PriorityOrdered接口的BeanDefinitionRegistryPostProcessor实现类
			//找到所有实现BeanDefinitionRegistryPostProcessor 接口的bean的beanName
			String[] postProcessorNames =
					beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
			//遍历处理所有的符合规则的postProcessorNames
			for (String ppName : postProcessorNames) {
				//优先执行实现PriorityOrdered接口
				if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
					processedBeans.add(ppName);
				}
			}
			sortPostProcessors(currentRegistryProcessors, beanFactory);
			//添加registryProcessors,用于最后执行的postProcess方法
			registryProcessors.addAll(currentRegistryProcessors);
			//遍历currentRegistryProcessors,执行postProcessBeanDefinitionRegistry
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
			//执行完毕,清空currentRegistryProcessors集合
			currentRegistryProcessors.clear();

			// Next, invoke the BeanDefinitionRegistryPostProcessors that implement Ordered.
			//调用所有实现PriorityOrdered接口的BeanDefinitionRegistryPostProcessor实现类
			//找到所有实现BeanDefinitionRegistryPostProcessor 接口的bean的beanName
			// 此处需要重复查找的原因在于可能在上面执行的过程中会新增新的BeanDefinitionRegistryPostProcessor
			postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
			for (String ppName : postProcessorNames) {
				//检测是否实现Ordered接口(未实现PriorityOrdered接口),并且还未被执行过
				if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) {
					//获取名字对应的bean实例,添加到currentRegistryProcessors中
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
					//将要执行的BFPP名称添加到processedBeans中,避免后续重复执行
					processedBeans.add(ppName);
				}
			}
			sortPostProcessors(currentRegistryProcessors, beanFactory);
			//添加registryProcessors,用于最后执行的postProcess方法
			registryProcessors.addAll(currentRegistryProcessors);
			//遍历currentRegistryProcessors,执行postProcessBeanDefinitionRegistry
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
			//执行完毕,清空currentRegistryProcessors集合
			currentRegistryProcessors.clear();
			boolean reiterate = true;
			while (reiterate) {
				reiterate = false;
				postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
				for (String ppName : postProcessorNames) {
					if (!processedBeans.contains(ppName)) {
						currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
						processedBeans.add(ppName);
						reiterate = true;
					}
				}
				sortPostProcessors(currentRegistryProcessors, beanFactory);
				registryProcessors.addAll(currentRegistryProcessors);
				//在此调用自定义的selfBeanPostRegistryProcessor
				invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
				currentRegistryProcessors.clear();
			}
			//调用所有的BeanDefinitionRegistryPostProcessor的postProcessBeanFactory 方法
			invokeBeanFactoryPostProcessors(registryProcessors, beanFactory);
			//最后调用父类的入参BeanFactoryPostProcessor中普通BeanFactoryPostProcessor的postProcessBeanFactory 方法
			invokeBeanFactoryPostProcessors(regularPostProcessors, beanFactory);
		}
		else {
			//如果beanFactory不属于BeanDefinitionRegistry类型,直接执行postProcessBeanFactory方法
			invokeBeanFactoryPostProcessors(beanFactoryPostProcessors, beanFactory);
		}
		/*
		 *	到此为止,入参beanFactoryProcessors和容器中所有的BeanDefinitionRegistryPostProcessor已经全部处理完成
		 * 现在开始处理BeanFactoryPostProcessor
		 * 这里可能存在一部分只实现了BeanFactoryPostProcessor,没有实现BeanDefinitionRegistryPostProcessor接口的类
		 */
		String[] postProcessorNames =
				beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);
		//用于存放实现了priorityOrdered接口的beanName集合
		List<BeanFactoryPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
		//用于存放实现了ordered接口的BeanFactoryProcessor的beanName
		List<String> orderedPostProcessorNames = new ArrayList<>();
		//存放普通的BeanFactoryProcessor的beanName
		List<String> nonOrderedPostProcessorNames = new ArrayList<>();
		//遍历postProcessorNames,将三种不同集合区分开
		for (String ppName : postProcessorNames) {
			if (processedBeans.contains(ppName)) {
                //BeanDefinitionRegistryPostProcessor继承自BeanFactoryPostProcessor,所以执行后者时会过滤掉前者的内容
				//已经执行过的BeanFactoryPostProcessor不再执行
                
			}
			else if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
				priorityOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
			}
			else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
				orderedPostProcessorNames.add(ppName);
			}
			else {
				nonOrderedPostProcessorNames.add(ppName);
			}
		}
		//对实现priorityOrdered接口的BeanFactoryPostProcessor进行排序
		sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
		//对实现priorityOrdered接口的BeanFactoryPostProcessor执行PostProcessorBeanFactory方法
		invokeBeanFactoryPostProcessors(priorityOrderedPostProcessors, beanFactory);
		List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());
		for (String postProcessorName : orderedPostProcessorNames) {
			orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
		}
		//对实现ordered接口的BeanFactoryPostProcessor进行排序操作
		sortPostProcessors(orderedPostProcessors, beanFactory);
		//遍历实现了ordered接口的BeanFactoryPostProcessor,执行PostProcessorBeanFactory方法
		invokeBeanFactoryPostProcessors(orderedPostProcessors, beanFactory);
		//创建存放BeanFactoryPostProcessor的集合对象
		List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());
		for (String postProcessorName : nonOrderedPostProcessorNames) {
			nonOrderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
		}
		invokeBeanFactoryPostProcessors(nonOrderedPostProcessors, beanFactory);
		beanFactory.clearMetadataCache();
	}

invokeBeanFactoryPostProcessors在处理时,BeanFactoryPostProcessor分为了两类进行处理,BeanFactoryPostProcessorBeanDefinitionRegistryPostProcessor,其中BeanDefinitionRegistryPostProcessor继承自BeanFactoryPostProcessor。执行的时候,先找出所有的BeanDefinitionRegistryPostProcessor执行再找出所有BeanFactoryPostProcessor执行。因为BeanDefinitionRegistryPostProcessor继承自BeanFactoryPostProcessor,所以执行后者时会过滤掉前者的内容。

在执行BeanDefinitionRegistryPostProcessor时,会按照如下的优先级,分类先执行postProcessBeanDefinitionRegistry方法,再统一执行所有的postProcessBeanFactory方法,,规则为:

  1. 筛选实现了PriorityOrdered接口的BeanDefinitionRegistryPostProcessor实现
  2. 筛选实现了Ordered接口的BeanDefinitionRegistryPostProcessor实现,并执行
  3. 执行其他BeanDefinitionRegistryPostProcessors

在执行BeanFactoryPostProcessor也会按照如上的规则,执行BeanFactoryPostProcessor方法。

这里会实例化并初始化实现BeanFactoryPostProcessor接口的类并执行,若存在依赖的的Bean也会被初始化和实例化

registerBeanPostProcessors

从Spring容器中找出的BeanPostProcessor接口的Bean,并添加到BeanFactory内部维护的List属性中,以便后续Bean被实例化的时候调用这个BeanPostProcessor进行回调处理。该方法委托给了org.springframework.context.support.PostProcessorRegistrationDelegate类的registerBeanPostProcessors方法执行。执行过程同步骤5类似,也是按照优先级进行了筛选,具体顺序为:

  1. 将实现PriorityOrdered接口的BeanPostProcessor列表注册到ApplicationContext中
  2. 将实现Ordered接口的BeanPostProcessor列表注册到ApplicationContext中
  3. 将剩余的BeanPostProcessor列表注册到ApplicationContext中
  4. 将实现MergedBeanDefinitionPostProcessor接口的BeanPostProcessor列表注册到ApplicationContext中

其中MergedBeanDefinitionPostProcessor接口继承自BeanPostProcessor接口,因而,上述第(4)点的列表同头三点的列表是存在交集的。但是,AbstraceApplicationContext在添加BeanPostProcessor时,会先将存在的对象删除,再添加新的,如下:

org.springframework.beans.factory.support.AbstractBeanFactory类的addBeanPostProcessor

	@Override
	public void addBeanPostProcessor(BeanPostProcessor beanPostProcessor) {
		Assert.notNull(beanPostProcessor, "BeanPostProcessor must not be null");
		//在原来的集合中移除这次要定义的beanPostProcessor对象
		this.beanPostProcessors.remove(beanPostProcessor);
		// 判断beanPostProcessor给hasInstantiationAwareBeanPostProcessors值赋值
		if (beanPostProcessor instanceof InstantiationAwareBeanPostProcessor) {
			this.hasInstantiationAwareBeanPostProcessors = true;
		}
		if (beanPostProcessor instanceof DestructionAwareBeanPostProcessor) {
			this.hasDestructionAwareBeanPostProcessors = true;
		}
		//添加此次的新对象到beanPostProcessors集合中
		this.beanPostProcessors.add(beanPostProcessor);
	}

initMessageSource

国结化(根据语言切换系统语言),在springMVC开发会用到

initApplicationEventMulticaster

在Spring容器中初始化事件广播器对象SimpleApplicationEventMulticaster,并将该对象作为单例applicationEventMulticaster注册到Context中。该广播器用于广播ApplicationEvent事件对应的ApplicationListener接口Bean

根据以上的顺序,在这之前实例化的Bean,都不会经过BeanFactoryPostProcessor和BeanPostProcessor的处理,包括因为依赖而实例化的Bean,还有提前通过new注册的Bean(只有直接调用BeanFactory.getBean方法获取的bean才会进行后置回调)。这里需要注意,Context提前将两种后置处理器的所有实现都提前加载了,由于实例化前需要将依赖的Bean提前实例化,所以被这两种后置处理器依赖的Bean的初始化动作,是不会被其监听到的

onRefresh

模板方法,可用于refresh动作的扩展,默认为空实现。在SpringBoot中主要用于启动内嵌的web服务器。

registerListeners

获取系统中的ApplicationListener对象,注册到事件广播器中。如果有需要提前进行广播的事件,则执行广播.

finishBeanFactoryInitialization

实例化BeanFactory中已经被注册但是未实例化的所有实例(懒加载的不需要实例化),主要操作是BeanFacotry的preInstantiateSingletons方法。该方法分为两部分:

  1. 遍历已经解析出来的所有beanDefinitionNames,如果不是抽象类、是单例且没有设置懒加载,则进行实例化和初始化。
  2. 在spring容器管理的所有单例对象(非懒加载对象)初始化完成之后调用SmartInitializingSingleton回调接口,注意,该回调只会发生在启动阶段,后续懒加载对象再初始化的话,不会再进行回
  3. finishRefresh

刷新后的其他动作,包括:

  1. 初始化生命周期处理器DefaultLifecycleProcessor,该处理器管理所有实现了Lifecycle接口的类
  2. 通知所有Lifecycle.onRefresh,该方法内部调用LifecycleProcessor.startBeans(false),这里只会调用实现了SmartLifecycle接口,并且设定了AutoStartup的实例,回调将按照设定的优先级,从低到高执行
  3. 发布ContextRefreshedEvent通知事件
  4. 调用LiveBeansView的registerApplicationContext方法

finishRefresh

完成刷新过程,通知生命周期处理器lifecycleProcessor刷新过程,同时发出ContextRefreshEvent通知

destroyBeans

销毁所有已经注册的单例,对于实现了DisposableBean的类,会先单独进行销毁,以便执行回调方法,再清理所有单例的缓存信息和剩余的单例实例

cancelRefresh

将当前的活动状态标识为false

posted @ 2021-07-27 20:25  知白守黑,和光同尘  阅读(166)  评论(0编辑  收藏  举报