Spring Ioc 容器启动流程

Spring容器的启动流程

本文基于 Spring 5.3.23

基于XML文件

public void test() {
        ApplicationContext applicationContext = new ClassPathXmlApplicationContext("applicationContext.xml");
        User user = applicationContext.getBean("user", User.class);
}

我们进入 ClassPathXmlApplicationContext() 源码

public ClassPathXmlApplicationContext(String configLocation) throws BeansException {
    this(new String[] {configLocation}, true, null);
}

显示的是调用另外一个方法

public ClassPathXmlApplicationContext(
       String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
       throws BeansException {
    super(parent);
    setConfigLocations(configLocations);
    if (refresh) {
       refresh();
    }
}

我们可以看到,这个方法就只运行了三行代码:我们逐个分析

super(parent) parent 为 null。我们进入源码看看到底做了什么

super(parent)源码分析

public AbstractXmlApplicationContext(@Nullable ApplicationContext parent) {
		super(parent);
}
public AbstractRefreshableConfigApplicationContext(@Nullable ApplicationContext parent) {
		super(parent);
}
public AbstractRefreshableApplicationContext(@Nullable ApplicationContext parent) {
		super(parent);
}
public AbstractApplicationContext(@Nullable ApplicationContext parent) {
		this();
		setParent(parent);
}

我们发现它一直向上调用父类的方法,一直到

public AbstractApplicationContext(@Nullable ApplicationContext parent) {
		this();
		setParent(parent);
}

我们来看看这个 this()函数做了什么

this()源码分析

public AbstractApplicationContext() {
		this.resourcePatternResolver = getResourcePatternResolver();
}

大致就是 给 AbstractApplicationContext这个抽象类的 resourcePatternResolver属性赋值。

我们来看看 getResourcePatternResolver();做了什么

getResourcePatternResolver();源码分析

protected ResourcePatternResolver getResourcePatternResolver() {
		return new PathMatchingResourcePatternResolver(this);
}

大致就是 创建了一个 PathMatchingResourcePatternResolver类的实例对象并返回。

这里 提供了一个参数 this 让我们看看getResourcePatternResolver()函数所在的类是什么样子的。

public abstract class AbstractApplicationContext extends DefaultResourceLoader implements ConfigurableApplicationContext{}

继承了一个 AbstractApplicationContext类,实现了ConfigurableApplicationContext接口。很好,先到这里,放我们进去

PathMatchingResourcePatternResolver()源码,看看这个 this到底代表了什么。

PathMatchingResourcePatternResolver()源码分析

public PathMatchingResourcePatternResolver(ResourceLoader resourceLoader) {
		Assert.notNull(resourceLoader, "ResourceLoader must not be null");
		this.resourceLoader = resourceLoader;
}

看到这我们应该明白了 this 就是代表一个 resourceLoader。毕竟 AbstractApplicationContext类继承了 DefaultResourceLoader类。到这里 this()就到头了,大概就是初始化了一个 资源加载器resourceLoader


public AbstractApplicationContext(@Nullable ApplicationContext parent) {
		this();
		setParent(parent);
}

接下来我们来看看setParent(parent)做了什么

setParent(parent)源码分析

public void setParent(@Nullable ApplicationContext parent) {
	this.parent = parent; //赋值
	if (parent != null) {
        //获取 parent 对象的环境
		Environment parentEnvironment = parent.getEnvironment();
        //如果这个环境是 ConfigurableEnvironment 的实例
		if (parentEnvironment instanceof ConfigurableEnvironment) {
            //将 parentEnvironment 强制转换为 父环境,同时,将父环境的配置合并到当前环境
			getEnvironment().merge((ConfigurableEnvironment) parentEnvironment);
		}
	}
}
//简而言之,这段代码的作用是设置当前对象的父应用程序上下文,并在父上下文存在且为可配置环境时,将其环境的配置合并到当前环境中。

emmm,我们一路传递上来的 parent 好像是 null 呀。那个这好像就没有发挥什么作用。

public AbstractApplicationContext(@Nullable ApplicationContext parent) {
		this();
		setParent(parent);
}

这个代码就解析完了。就大概初始化了资源解析器。。


public ClassPathXmlApplicationContext(
       String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
       throws BeansException {
    super(parent);
    setConfigLocations(configLocations);
    if (refresh) {
       refresh();
    }
}

接下来分析 setConfigLocations(configLocations);做了什么

setConfigLocations(configLocations);源码分析

我们要先知道 String[] configLocations 这个数组里就一个String对象 applicationContext.xml

public void setConfigLocations(@Nullable String... locations) {
		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++) {
                // configLocation 也是一个 String 类型的数组
				this.configLocations[i] = resolvePath(locations[i]).trim();
			}
		}
		else {
			this.configLocations = null;
		}
}

我们来看看 configLocations[i]中具体存的什么东西

this.configLocations[i] = resolvePath(locations[i]).trim();

resolvePath()源码分析

protected String resolvePath(String path) {
		return getEnvironment().resolveRequiredPlaceholders(path);
}

我们看看 getEnvironment()做了什么

public ConfigurableEnvironment getEnvironment() {
		if (this.environment == null) {
			this.environment = createEnvironment();
		}
		return this.environment;
	}

创建了一个 ConfigurableEnvironment接口类型的对象。

protected ConfigurableEnvironment createEnvironment() {
		return new StandardEnvironment();
}

实际是 StandardEnvironment类型的对象。

然后用我们创建的对象去调用 resolveRequiredPlaceholders()函数,此时 path 仍旧是 applicationContext.xml

我们去resolveRequiredPlaceholders()源码看看

String resolveRequiredPlaceholders(String text) throws IllegalArgumentException;

一个接口的方法,还是要去实现类看看。

在这里插入图片描述

我们去 第一个 AbstractEnvironment类中去看看

public abstract class AbstractEnvironment implements ConfigurableEnvironment {}

这不巧了吗,我们刚生成了一个 ConfigurableEnvironment接口类型的对象,

我们来看看 AbstractEnvironment类中 resolveRequiredPlaceholders()干了什么

public String resolveRequiredPlaceholders(String text) throws IllegalArgumentException {
		return this.propertyResolver.resolveRequiredPlaceholders(text);
}

继续深入。

public String resolveRequiredPlaceholders(String text) throws IllegalArgumentException {
    if (this.strictHelper == null) {
       this.strictHelper = createPlaceholderHelper(false);
    }
    return doResolvePlaceholders(text, this.strictHelper);
}

很好,已经看不懂了。。。。。。。。。。谁来九九我。

学个单词 Placeholder:占位符。

那么这个 doResolvePlaceholders()这个函数大致做了什么。我们可以大胆的猜一下。text就是我们传过来的配置文件的文件名。

那么这个函数大概就是 对我们的文件名 进行了 一些 操作,比如处理处理一下占位符啥啥的。

好了,我不会了。就先到这里

this.configLocations[i] = resolvePath(locations[i]).trim();

这行代码大概就是对我们的文件名做了点操作。我太菜了,只能看到这里。

感兴趣的 spring setConfigLocations方法分析_blueskygotohz的博客-CSDN博客文章走起


public ClassPathXmlApplicationContext(
       String[] configLocations, boolean refresh, @Nullable ApplicationContext parent)
       throws BeansException {
    super(parent);
    setConfigLocations(configLocations);
    if (refresh) {
       refresh();
    }
}

我们传递的 refresh为 true 也就是 一定会运行 refresh()函数。这也是 spring中最重要的一个函数。

refresh()源码分析

@Override
public void refresh() throws BeansException, IllegalStateException {
    synchronized (this.startupShutdownMonitor) {//先加个锁
       StartupStep contextRefresh = this.applicationStartup.start("spring.context.refresh");//1
       // Prepare this context for refreshing.
        //准备此上下文以进行刷新
       prepareRefresh();//2
        
       // Tell the subclass to refresh the internal bean factory.
        //告诉子类刷新内部 Bean 工厂。
       ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();//3
        
       // Prepare the bean factory for use in this context.
        //准备 Bean 工厂以在此上下文中使用。
       prepareBeanFactory(beanFactory);//4

       try {
          // Allows post-processing of the bean factory in context subclasses.
           //允许在上下文子类中对 Bean 工厂进行后处理。
          postProcessBeanFactory(beanFactory);//5

           //不知道是个什么东西
          StartupStep beanPostProcess = this.applicationStartup.start("spring.context.beans.post-process");
           
          // Invoke factory processors registered as beans in the context.
           //调用在上下文中注册为 Bean 的工厂处理器。
          invokeBeanFactoryPostProcessors(beanFactory); // 6

          // Register bean processors that intercept bean creation.
           //注册截获 Bean 创建的 Bean 处理器。
          registerBeanPostProcessors(beanFactory);//7
          beanPostProcess.end();

          // Initialize message source for this context.
           //初始化此上下文的消息源。
          initMessageSource();//8

          // Initialize event multicaster for this context
         //初始化此上下文的事件多播器。
          initApplicationEventMulticaster();//9

          // Initialize other special beans in specific context subclasses.
           //在特定上下文子类中初始化其他特殊 bean。
          onRefresh();// 可以提供子类重写这个方法,在容器刷新时,做些其它操作

          // Check for listener beans and register them.
           //检查侦听器 Bean 并注册它们。
          registerListeners();//10

          // Instantiate all remaining (non-lazy-init) singletons.
           //实例化所有剩余的(非惰性初始化)单例。
          finishBeanFactoryInitialization(beanFactory);//11

          // Last step: publish corresponding event.
           //最后一步:发布相应事件
          finishRefresh();
       }

       catch (BeansException ex) {
          ...
       }

       finally {
          ....
       }
    }
}

我滴妈,这么多。一点一点看吧。。注意注意 refresh()函数 是在 AbstractApplicationContext类中,其实就是 应用上下文容器

1、

StartupStep contextRefresh = this.applicationStartup.start("spring.context.refresh");

不知道干了点啥,不看了

2、 prepareRefresh();

做了一些简单的准备工作

protected void prepareRefresh() {
		// Switch to active.
		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());
			}
		}

		//初始化一下属性(该方法默认是空的,是提供给子类来实现的,
		//假设我们有些工作需要在初始化bean以前就要加载设置等,可以通过重写这个方法来完成)
		initPropertySources();

		//校验设置的属性是否合法 
    	//同样是交给子类去实现
		getEnvironment().validateRequiredProperties();

		//初始化 早期应用监听器
		if (this.earlyApplicationListeners == null) {
			this.earlyApplicationListeners = new LinkedHashSet<>(this.applicationListeners);
		}
		else {
			// Reset local application listeners to pre-refresh state.
			this.applicationListeners.clear();
			this.applicationListeners.addAll(this.earlyApplicationListeners);
		}

		//初始化一个集合属性,提供用来保存后面创建的事件,如果有事件发生会放入这个集合中
    	//初始化早期应用事件
		this.earlyApplicationEvents = new LinkedHashSet<>();
	}

3、获取一个 beanFactory

ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();
protected ConfigurableListableBeanFactory obtainFreshBeanFactory() {
		refreshBeanFactory();
		return getBeanFactory();
}

refreshBeanFactory(): 下面是子类的一个实现

protected final void refreshBeanFactory() throws BeansException {
    if (hasBeanFactory()) { //已经有工厂了
       destroyBeans();//破坏所有的 bean
       closeBeanFactory();//关闭这个工厂
    }
    try {
       DefaultListableBeanFactory beanFactory = createBeanFactory(); //创建一个工厂
        //设置bean工厂的序列化 id 
       beanFactory.setSerializationId(getId());
        //自定义bean工厂
       customizeBeanFactory(beanFactory);
        //加载bean定义信息
       loadBeanDefinitions(beanFactory);
       this.beanFactory = beanFactory;
    }
    catch (IOException ex) {
       throw new ApplicationContextException("I/O error parsing bean definition source for " + getDisplayName(), ex);
    }
}

getBeanFactory()

@Override
public final ConfigurableListableBeanFactory getBeanFactory() {
    DefaultListableBeanFactory beanFactory = this.beanFactory;//这是我们刚才生成的
    if (beanFactory == null) {
        throw new IllegalStateException("BeanFactory not initialized or already closed - " +
                "call 'refresh' before accessing beans via the ApplicationContext");
    }
    return beanFactory;//返回去
}
ConfigurableListableBeanFactory beanFactory = obtainFreshBeanFactory();

这行代码就是获取一个全新的 beanFactory

4、 prepareBeanFactory(beanFactory) : 大致就是做了一些预处理

protected void prepareBeanFactory(ConfigurableListableBeanFactory beanFactory) {
    // Tell the internal bean factory to use the context's class loader etc.
    beanFactory.setBeanClassLoader(getClassLoader());//设置一个 bean 加载器
    
    //表达式语言解析器
    if (!shouldIgnoreSpel) {
        beanFactory.setBeanExpressionResolver(new StandardBeanExpressionResolver(beanFactory.getBeanClassLoader()));
    }
    beanFactory.addPropertyEditorRegistrar(new ResourceEditorRegistrar(this, getEnvironment()));

    // Configure the bean factory with context callbacks.
    //设置添加一个 ApplicationContextAwareProcessor 后置处理器
    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.ignoreDependencyInterface(ApplicationStartupAware.class);

    //注册可以解析的自动装配
    //假设想要使用@Autowired 注解将Spring提供的 BeanFactory 装配到自己创建的某个类的属性上,就要在此处设置
    beanFactory.registerResolvableDependency(BeanFactory.class, beanFactory);
    beanFactory.registerResolvableDependency(ResourceLoader.class, this);
    beanFactory.registerResolvableDependency(ApplicationEventPublisher.class, this);
    beanFactory.registerResolvableDependency(ApplicationContext.class, this);

   //设置添加一个ApplicationListenerDetector后置处理器
    beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(this));

    //添加编译时支持AspectJ
    if (!NativeDetector.inNativeImage() && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
        beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
        // Set a temporary ClassLoader for type matching.
        beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
    }

    // Register default environment beans.
    //注册默认的环境 bean 
    //且是单例模式
    if (!beanFactory.containsLocalBean(ENVIRONMENT_BEAN_NAME)) {
        //注册了一个 Environment,该对象中存了一下我们默认的属性
        beanFactory.registerSingleton(ENVIRONMENT_BEAN_NAME, getEnvironment());
    }
    if (!beanFactory.containsLocalBean(SYSTEM_PROPERTIES_BEAN_NAME)) {
        //向beanFactory中注册了系统属性属性(一个Map集合)
        beanFactory.registerSingleton(SYSTEM_PROPERTIES_BEAN_NAME, getEnvironment().getSystemProperties());
    }
    if (!beanFactory.containsLocalBean(SYSTEM_ENVIRONMENT_BEAN_NAME)) {
        //向beanFactory中注册环境变量等相关信息(一个Map集合)
        beanFactory.registerSingleton(SYSTEM_ENVIRONMENT_BEAN_NAME, getEnvironment().getSystemEnvironment());
    }
    if (!beanFactory.containsLocalBean(APPLICATION_STARTUP_BEAN_NAME)) {
        //向beanFactory中注册 ApplicationStartup 对象。
        beanFactory.registerSingleton(APPLICATION_STARTUP_BEAN_NAME, getApplicationStartup());
    }
}

5、postProcessBeanFactory(beanFactory);

该方法默认是空的,为子类通过的,假设后续开发中,在 beanFactory 创建并且有准备完成后需要执行某些操作,可以提供子类重写这个方法来实现

以上可以看为beanFactory 的创建及预准备工作===========

6、 invokeBeanFactoryPostProcessors(beanFactory)

protected void invokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory) {
    //执行beanFactory后置处理器中的方法,该方法中获取所有BeanFactoryPostProcessor,遍历判断
	//对不同的BeanFactoryPostProcessor进行排序,因为先后执行的顺序不同,
	//PriorityOrderedBeanFactoryPostProcessor
	//然后执行后置处理器中定义的初始化 beanFactory 后要执行的方法
    PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory, getBeanFactoryPostProcessors());
    if (!NativeDetector.inNativeImage() && beanFactory.getTempClassLoader() == null && beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)) {
       beanFactory.addBeanPostProcessor(new LoadTimeWeaverAwareProcessor(beanFactory));
       beanFactory.setTempClassLoader(new ContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));
    }
}

ok 卡! 在看下面的代码之前,了解点知识

什么是后处理(Post-processing)?

在Spring框架中,后处理(Post-processing)是指在应用程序上下文加载和初始化Bean之后,对这些Bean进行进一步的修改或处理的过程。后处理器是实现了相应接口的组件,它们可以在Spring容器生命周期的不同阶段进行自定义的操作。

在Spring中,有多个后处理器接口可供使用,包括:

  1. BeanPostProcessor:该接口定义了在Bean实例化和依赖注入完成之后,在初始化前后对Bean进行修改的方法。可以通过实现该接口来定制Bean的初始化逻辑,例如添加额外的初始化操作、修改属性值等。
  2. BeanFactoryPostProcessor:该接口允许在应用程序上下文创建所有单例Bean之前对Bean工厂进行修改。可以通过实现该接口来修改Bean工厂的配置,例如注册自定义编辑器、添加额外的Bean定义等。
  3. BeanDefinitionRegistryPostProcessor:该接口在Bean定义被加载到应用程序上下文之前,允许对Bean定义进行修改或添加新的Bean定义。可以通过实现该接口来动态注册Bean定义,修改Bean定义的属性等。

通过实现这些后处理器接口,开发人员可以对Spring容器中的Bean进行自定义操作,以满足特定的需求。后处理器在Spring的扩展机制中起到了重要的作用,使得开发者能够更加灵活地定制和扩展应用程序上下文的行为。

invokeBeanFactoryPostProcessors()

public static void invokeBeanFactoryPostProcessors(
			ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {
		Set<String> processedBeans = new HashSet<>();
    /**
      *1.判断beanFactory是否为BeanDefinitionRegistry,beanFactory为DefaultListableBeanFactory,而				         *DefaultListableBeanFactory实现了BeanDefinitionRegistry接口,因此这边为true
    */
		if (beanFactory instanceof BeanDefinitionRegistry) {
			BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;
            // regular: 常规  用来存储常规的BeanFactoryPostProcessor
			List<BeanFactoryPostProcessor> regularPostProcessors = new ArrayList<>();
            // 用于存放BeanDefinitionRegistryPostProcessor
			List<BeanDefinitionRegistryPostProcessor> registryProcessors = new ArrayList<>();

            // 2.首先处理入参中的beanFactoryPostProcessors
            // 遍历所有的beanFactoryPostProcessors, 将BeanDefinitionRegistryPostProcessor和普通      BeanFactoryPostProcessor区分开

			for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {
				if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
                    // 如果是BeanDefinitionRegistryPostProcessor
					BeanDefinitionRegistryPostProcessor registryProcessor =
							(BeanDefinitionRegistryPostProcessor) postProcessor;
                    //直接执行BeanDefinitionRegistryPostProcessor接口的postProcessBeanDefinitionRegistry方法
					registryProcessor.postProcessBeanDefinitionRegistry(registry);
                    //添加到registryProcessors(用于最后执行postProcessBeanFactory方法)
					registryProcessors.add(registryProcessor);
				}
				else {
                    //加到regularPostProcessors(用于最后执行postProcessBeanFactory方法)
					regularPostProcessors.add(postProcessor);
				}
			}

			// 用于保存本次要执行的BeanDefinitionRegistryPostProcessor
			List<BeanDefinitionRegistryPostProcessor> currentRegistryProcessors = new ArrayList<>();

			// First, invoke the BeanDefinitionRegistryPostProcessors that implement PriorityOrdered.
            //找出所有实现BeanDefinitionRegistryPostProcessor接口的Bean的beanName
			String[] postProcessorNames =
					beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
            //遍历postProcessorNames
			for (String ppName : postProcessorNames) {
                // 校验是否实现了PriorityOrdered接口
				if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
                    //获取ppName对应的bean实例, 添加到currentRegistryProcessors中,
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
                    //将要被执行的加入processedBeans,避免后续重复执行
					processedBeans.add(ppName);
				}
			}
             // 进行排序(根据是否实现PriorityOrdered、Ordered接口和order值来排序)
			sortPostProcessors(currentRegistryProcessors, beanFactory);
            //添加到registryProcessors(用于最后执行postProcessBeanFactory方法)
			registryProcessors.addAll(currentRegistryProcessors);
            //遍历currentRegistryProcessors, 执行postProcessBeanDefinitionRegistry方法
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry, beanFactory.getApplicationStartup());
            //执行完毕后, 清空currentRegistryProcessors
			currentRegistryProcessors.clear();

			// Next, invoke the BeanDefinitionRegistryPostProcessors that implement Ordered.
            //找出所有实现BeanDefinitionRegistryPostProcessor接口的类, 这边重复查找是因为执行完上面的BeanDefinitionRegistryPostProcessor,
            //可能会新增了其他的BeanDefinitionRegistryPostProcessor, 因此需要重新查找
			postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
			for (String ppName : postProcessorNames) {
                // 校验是否实现了Ordered接口,并且还未执行过
				if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) {
					currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
					processedBeans.add(ppName);
				}
			}
			sortPostProcessors(currentRegistryProcessors, beanFactory);
			registryProcessors.addAll(currentRegistryProcessors);
            //遍历currentRegistryProcessors, 执行postProcessBeanDefinitionRegistry方法
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry, beanFactory.getApplicationStartup());
			currentRegistryProcessors.clear();

			// Finally, invoke all other BeanDefinitionRegistryPostProcessors until no further ones appear.
            //最后, 调用所有剩下的BeanDefinitionRegistryPostProcessors
			boolean reiterate = true;
			while (reiterate) {
				reiterate = false;
                //找出所有实现BeanDefinitionRegistryPostProcessor接口的类
				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);
                        //如果有BeanDefinitionRegistryPostProcessor被执行, 则有可能会产生新的BeanDefinitionRegistryPostProcessor,
                    // 因此这边将reiterate赋值为true, 代表需要再循环查找一次
						reiterate = true;
					}
				}
				sortPostProcessors(currentRegistryProcessors, beanFactory);
				registryProcessors.addAll(currentRegistryProcessors);
                //遍历currentRegistryProcessors, 执行postProcessBeanDefinitionRegistry方法
				invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry, beanFactory.getApplicationStartup());
				currentRegistryProcessors.clear();
			}

			// Now, invoke the postProcessBeanFactory callback of all processors handled so far.
            //调用所有BeanDefinitionRegistryPostProcessor的postProcessBeanFactory方法(BeanDefinitionRegistryPostProcessor继承自BeanFactoryPostProcessor)
			invokeBeanFactoryPostProcessors(registryProcessors, beanFactory);
            //调用入参beanFactoryPostProcessors中的普通BeanFactoryPostProcessor的postProcessBeanFactory方法
			invokeBeanFactoryPostProcessors(regularPostProcessors, beanFactory);
		}

		else {
			// Invoke factory processors registered with the context instance.
			invokeBeanFactoryPostProcessors(beanFactoryPostProcessors, beanFactory);
		}
    
    // 到这里 , 入参beanFactoryPostProcessors和容器中的所有BeanDefinitionRegistryPostProcessor已经全部处理完毕,
    // 下面开始处理容器中的所有BeanFactoryPostProcessor

		//找出所有实现BeanFactoryPostProcessor接口的类
		String[] postProcessorNames =
				beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);


    //用于存放实现了PriorityOrdered接口的BeanFactoryPostProcessor
		List<BeanFactoryPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
    //用于存放实现了Ordered接口的BeanFactoryPostProcessor的beanName
		List<String> orderedPostProcessorNames = new ArrayList<>();
    //用于存放普通BeanFactoryPostProcessor的beanName
		List<String> nonOrderedPostProcessorNames = new ArrayList<>();
    //遍历postProcessorNames, 将BeanFactoryPostProcessor按实现PriorityOrdered、实现Ordered接口、普通三种区分开
		for (String ppName : postProcessorNames) {
            //跳过已经执行过的
			if (processedBeans.contains(ppName)) {
				// skip - already processed in first phase above
			}
			else if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
                //添加实现了PriorityOrdered接口的BeanFactoryPostProcessor
				priorityOrderedPostProcessors.add(beanFactory.getBean(ppName, BeanFactoryPostProcessor.class));
			}
			else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
                //添加实现了Ordered接口的BeanFactoryPostProcessor的beanName
				orderedPostProcessorNames.add(ppName);
			}
			else {
                 //添加剩下的普通BeanFactoryPostProcessor的beanName
				nonOrderedPostProcessorNames.add(ppName);
			}
		}

		
    	//调用所有实现PriorityOrdered接口的BeanFactoryPostProcessor
    	//对priorityOrderedPostProcessors排序
		sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
    	//遍历priorityOrderedPostProcessors, 执行postProcessBeanFactory方法
		invokeBeanFactoryPostProcessors(priorityOrderedPostProcessors, beanFactory);

		// Next, invoke the BeanFactoryPostProcessors that implement Ordered.
    	//调用所有实现Ordered接口的BeanFactoryPostProcessor
		List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());
		for (String postProcessorName : orderedPostProcessorNames) {
            //获取postProcessorName对应的bean实例, 添加到orderedPostProcessors, 准备执行
			orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
		}
    	//对orderedPostProcessors排序
		sortPostProcessors(orderedPostProcessors, beanFactory);
    	//遍历orderedPostProcessors, 执行postProcessBeanFactory方法
		invokeBeanFactoryPostProcessors(orderedPostProcessors, beanFactory);

		// Finally, invoke all other BeanFactoryPostProcessors.
    	//调用所有剩下的BeanFactoryPostProcessor
		List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());
		for (String postProcessorName : nonOrderedPostProcessorNames) {
            //获取postProcessorName对应的bean实例, 添加到nonOrderedPostProcessors, 准备执行
			nonOrderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
		}
    	//遍历nonOrderedPostProcessors, 执行postProcessBeanFactory方法
		invokeBeanFactoryPostProcessors(nonOrderedPostProcessors, beanFactory);

		// Clear cached merged bean definitions since the post-processors might have
		// modified the original metadata, e.g. replacing placeholders in values...
    	//清除元数据缓存(mergedBeanDefinitions、allBeanNamesByType、singletonBeanNamesByType
    	//因为后处理器可能已经修改了原始元数据,例如, 替换值中的占位符...
		beanFactory.clearMetadataCache();
	}

Spring Ioc 容器启动流程_第1张图片

7、registerBeanPostProcessors(beanFactory)

protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) {
		PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this);
}
public static void registerBeanPostProcessors(
			ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {
		//根据类型获取 beanFactory 中所有的 BeanPostProcessor 名字
		String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);
		int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length;
     	//添加了一个后置处理器,通过添加的这个后置处理器检查 前获取的这些后置处理器 
    //BeanPostProcessorChecker 是一个内部类,继承了BeanPostProcessor接口
		beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));

		//创建两个集合用来存放不同的BeanPostProcessor,通过这两个集合对不同的BeanPostProcessor 进行排序
		List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
		List<BeanPostProcessor> internalPostProcessors = new ArrayList<>();
		List<String> orderedPostProcessorNames = new ArrayList<>();
		List<String> nonOrderedPostProcessorNames = new ArrayList<>();
		for (String ppName : postProcessorNames) {
			if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
				BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
				priorityOrderedPostProcessors.add(pp);
				if (pp instanceof MergedBeanDefinitionPostProcessor) {
					internalPostProcessors.add(pp);
				}
			}
			else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
				orderedPostProcessorNames.add(ppName);
			}
			else {
				nonOrderedPostProcessorNames.add(ppName);
			}
		}

		// 首先对 priorityOrderedPostProcessors 中的进行排序
		sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
    	//注册,也就是创建BeanPostProcessor设置到beanFactory中
		registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors);

		// Next, register the BeanPostProcessors that implement Ordered.
		List<BeanPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());
		for (String ppName : orderedPostProcessorNames) {
			BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
			orderedPostProcessors.add(pp);
			if (pp instanceof MergedBeanDefinitionPostProcessor) {
				internalPostProcessors.add(pp);
			}
		}
    	//对orderedPostProcessors集合中的后置处理器排序
		sortPostProcessors(orderedPostProcessors, beanFactory);
    	//注册
		registerBeanPostProcessors(beanFactory, orderedPostProcessors);

		// Now, register all regular BeanPostProcessors.
		List<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());
		for (String ppName : nonOrderedPostProcessorNames) {
			BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
			nonOrderedPostProcessors.add(pp);
			if (pp instanceof MergedBeanDefinitionPostProcessor) {
				internalPostProcessors.add(pp);
			}
		}
    	//注册nonOrderedPostProcessors集合中的后置处理器
		registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);

		//对internalPostProcessors集合中的后置处理器进行排序
		sortPostProcessors(internalPostProcessors, beanFactory);
    	//注册internalPostProcessors集合中的后置处理器
		registerBeanPostProcessors(beanFactory, internalPostProcessors);

		//又添加了一个后置处理器ApplicationListenerDetector,
		//该后置处理器用来判断是否是某个监听器,如果是添加到容器中
		beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext));
	}

在这里插入图片描述

8、 initMessageSource();

在 SpringMVC 中用来做国际化功能,消息解析,消息绑定,MessageSource中有getMessage()方法,一般用来取出国际化配置文件中的key的值,能按照区域信息去获取

protected void initMessageSource() {
    //获取beanFactory
    ConfigurableListableBeanFactory beanFactory = getBeanFactory();
    //判断beanFactory中是否有一个id为"messageSource" 的 bean
    if (beanFactory.containsLocalBean(MESSAGE_SOURCE_BEAN_NAME)) {
        //如果有通过id获取这个bean,赋值给 messageSource  属性
       this.messageSource = beanFactory.getBean(MESSAGE_SOURCE_BEAN_NAME, MessageSource.class);
       // Make MessageSource aware of parent MessageSource.
       if (this.parent != null && this.messageSource instanceof HierarchicalMessageSource) {
          HierarchicalMessageSource hms = (HierarchicalMessageSource) this.messageSource;
          if (hms.getParentMessageSource() == null) {
             // Only set parent context as parent MessageSource if no parent MessageSource
             // registered already.
             hms.setParentMessageSource(getInternalParentMessageSource());
          }
       }
       if (logger.isTraceEnabled()) {
          logger.trace("Using MessageSource [" + this.messageSource + "]");
       }
    }
    else {
       //如果没有创建一个MessageSource组件
       DelegatingMessageSource dms = new DelegatingMessageSource();
       //将这个组件注册到容器中(以后获取国际化配置文件的相关信息,可以通过@Autowired在Spring
       //容器中直接获取装配到自己的类的属性上,然后调用MessageSource的方法)
       dms.setParentMessageSource(getInternalParentMessageSource());
       this.messageSource = dms;
       beanFactory.registerSingleton(MESSAGE_SOURCE_BEAN_NAME, this.messageSource);
       if (logger.isTraceEnabled()) {
          logger.trace("No '" + MESSAGE_SOURCE_BEAN_NAME + "' bean, using [" + this.messageSource + "]");
       }
    }
}

9、initApplicationEventMulticaster()

在这里插入图片描述

protected void initApplicationEventMulticaster() {
    //获取beanFactory
    ConfigurableListableBeanFactory beanFactory = getBeanFactory();
    //获取beanFactory中id为"applicationEventMulticaster"的事件派发器
    if (beanFactory.containsLocalBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME)) {
       this.applicationEventMulticaster =
             beanFactory.getBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, ApplicationEventMulticaster.class);
       if (logger.isTraceEnabled()) {
          logger.trace("Using ApplicationEventMulticaster [" + this.applicationEventMulticaster + "]");
       }
    }
    else {
        //如果没有创建一个 SimpleApplicationEventMulticaster 事件派发器,
       this.applicationEventMulticaster = new SimpleApplicationEventMulticaster(beanFactory);
        //注册到 Spring 容器中
       beanFactory.registerSingleton(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, this.applicationEventMulticaster);
       if (logger.isTraceEnabled()) {
          logger.trace("No '" + APPLICATION_EVENT_MULTICASTER_BEAN_NAME + "' bean, using " +
                "[" + this.applicationEventMulticaster.getClass().getSimpleName() + "]");
       }
    }
}

10、registerListeners()

protected void registerListeners() {
		// Register statically specified listeners first.
		for (ApplicationListener<?> listener : getApplicationListeners()) {
			getApplicationEventMulticaster().addApplicationListener(listener);
		}

		// Do not initialize FactoryBeans here: We need to leave all regular beans
		// uninitialized to let post-processors apply to them!
    	//在容器中拿到所有的监听器的名字
		String[] listenerBeanNames = getBeanNamesForType(ApplicationListener.class, true, false);
    	//遍历,将每个监听器添加到事件派发器中
		for (String listenerBeanName : listenerBeanNames) {
			getApplicationEventMulticaster().addApplicationListenerBean(listenerBeanName);
		}

		// Publish early application events now that we finally have a multicaster...
    	//获取早期设置的事件(派发之前的事件)
		Set<ApplicationEvent> earlyEventsToProcess = this.earlyApplicationEvents;
		this.earlyApplicationEvents = null;
    	//如果有
		if (!CollectionUtils.isEmpty(earlyEventsToProcess)) {
			for (ApplicationEvent earlyEvent : earlyEventsToProcess) {
                将早期的事件派发出去
				getApplicationEventMulticaster().multicastEvent(earlyEvent);
			}
		}
	}

在这里插入图片描述

11、finishBeanFactoryInitialization(beanFactory)

涉及到bean的生命周期,看这篇文章(正在创作)

Spring Ioc 容器启动流程_第2张图片

12、finishRefresh()

protected void finishRefresh() {
    // Clear context-level resource caches (such as ASM metadata from scanning).
    clearResourceCaches();

    // Initialize lifecycle processor for this context.
    initLifecycleProcessor();

    // Propagate refresh to lifecycle processor first.
    getLifecycleProcessor().onRefresh();

    // Publish the final event.
    publishEvent(new ContextRefreshedEvent(this));

    // Participate in LiveBeansView MBean, if active.
    if (!NativeDetector.inNativeImage()) {
       LiveBeansView.registerApplicationContext(this);
    }
}

Spring Ioc 容器启动流程_第3张图片

emmmm 都是什么玩意,服了,不看了


总结

Spring中的Ioc 容器启动主要是在 AbstractApplicationContext # refresh() 方实现的。大致过程如下:

1、首先会执行一些容器刷新前的准备工作,如设置容器启动时间、一些状态标志位等

2、创建容器对象、其实就是实例化DefaultListableBeanFactory对象,这一步包含了bean定义信息的解析,解析后的属性都封装到DefaultListableBeanFactory的成员属性中了,如我们常见的beanDefinitionMapbeanDefinitionNames;

3、准备bean工厂,实际就是设置 beanFactory的一些属性

4、Spring提供了 postProcessorBeanFactory()方法给我们去扩展、例如我们可以注册一些特殊的BeanPostProcessor后置处理器等操作

5、执行BeanFactoryPostProcessor后置处理器的postProcessBeanFactory()增强方法,使三个不同的集合分别存放实现了PriorityOrdered接口、实现了Ordered接口、普通的BeanFactoryPostProcessor,经过排序后之执行BeanFactoryPostProcessor的回调postProcessorBeanFactory

6、第六步,注册BeanPostProcessor后置处理器,注意,这里还不会执行BeanPostProcessor对应的增强方法;同样的,使用三个不同的集合分别存放实现了PriorityOrdered接口、实现了Ordered接口、普通的BeanPostProcessor,依次调用beanFactory.addBeanPostProcessor(postProcessor)方法往bean工厂中添加BeanPostProcessor;

7、为上下文初始化MessageResource,即国际化处理

8、初始化事件多播器,即ApplicationEventMulticaster,为后面的事件发布-监听做准备

9、提供了一个模板方法onRefresh(),留给子类初始化其他的bean

10、注册Listener监听器

11、最关键的一步,这里会实例化所有剩下的非懒加载的单例Bean,Bean的生命周期也是从这里开始的。

12、完成上下文刷新工作,如清除一些缓存、发布容器刷新完成事件等。

你可能感兴趣的:(spring,java,后端)