spring源码:BeanFactoryPostProcessor和BeanDefinitionRegistryPostProcessor的区别

这篇文章主要记录下BeanFactoryPostProcessor和BeanDefinitionRegistryPostProcessor的学习和一些见解;

结论

我习惯先说结论,然后再细说具体的源码:

  1. 前者是后者的父接口,后者是前者的子接口
  2. 两者都是在bean实例化之前对beanDefinition进行的一系列操作
  3. spring源码中,先执行后者的实现类,再实现前者的实现类

在spring源码中,这两个接口的实现类完成了bean的扫描和对配置类生成了代理对象
我们以 ***ConfigurationClassPostProcessor***这个类为例,来学习这两个接口;
说到这个类,我们要说的源码是这个方法:
org.springframework.context.support.AbstractApplicationContext#invokeBeanFactoryPostProcessors

源码分析

在源码中,BeanFactoryPostProcessor的接口中定义的方法是void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException;
BeanDefinitionRegistryPostProcessor定义的方法是void postProcessBeanDefinitionRegistry(BeanDefinitionRegistry registry) throws BeansException; 这两个接口都是spring提供的扩展点,执行时机是在bean实例化之前;

我们在前面的源码解析中 spring源码-bean加载整体流程 文章中有提到过,在spring初始化的源码中,需要特别注意一下ConfigurationClassPostProcessor这个类,因为这个类在spring自动扫描bean起到了非常大的作用

invokeBeanFactoryPostProcessors(beanFactory);方法会调用到下面的这个方法,这个方法就是本篇的核心

/**
 * @param beanFactory
 * @param beanFactoryPostProcessors
 *
 * 这里是对beanDefinitionRegistryPostProcessor和beanFactoryPostProcessor实现类的出来
 * 1.先执行程序员通过API提供的beanDefinitionRegistryPostProcessor的实现类
 * 2.执行spring中,实现了PriorityOrdered接口且实现了beanDefinitionRegistryPostProcessor接口的实现类
 * 3.执行spring中,实现了Ordered接口且实现了beanDefinitionRegistryPostProcessor接口的实现类
 * 4.执行spring中,只实现了beanDefinitionRegistryPostProcessor接口的实现类
 * 5.执行实现了beanFactoryPostProcessor接口的实现类
 */
public static void invokeBeanFactoryPostProcessors(
		ConfigurableListableBeanFactory beanFactory, List<BeanFactoryPostProcessor> beanFactoryPostProcessors) {

	// Invoke BeanDefinitionRegistryPostProcessors first, if any.
	//这个set集合可以理解为存储的是已经执行过的beanDefinitionRegistryPostProcessor
	Set<String> processedBeans = new HashSet<>();

	/**
	 * 这里之所以要判断beanFactory是哪种类型的,应该和org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor#postProcessBeanDefinitionRegistry(org.springframework.beans.factory.support.BeanDefinitionRegistry)
	 * 的入参有关系
	 */
	if (beanFactory instanceof BeanDefinitionRegistry) {
		BeanDefinitionRegistry registry = (BeanDefinitionRegistry) beanFactory;
		//regularPostProcessors这个list存储的是beanFactoryPostProcessor接口的实现类
		List<BeanFactoryPostProcessor> regularPostProcessors = new ArrayList<>();
		//registryProcessors 这个list存储的是beanDefinitionRegistryPostProcessor接口的实现类
		List<BeanDefinitionRegistryPostProcessor> registryProcessors = new ArrayList<>();

		/**
		 * 序号1
		 * 这里的beanFactoryPostProcessors是程序员自己提供的BeanFactoryPostProcessor的实现类
		 */
		for (BeanFactoryPostProcessor postProcessor : beanFactoryPostProcessors) {
			/**
			 * 区分当前bean是BeanDefinitionRegistryPostProcessor还是 beanFactoryPostProcessor
			 * 因为前者是后者的子类,所以在获取beanFactoryPostprocessor的时候 也可以获取到
			 *
			 * 在本方法中  是先执行实现了BeanDefinitionRegistryPostProcessor的类
			 * 再执行beanFactoryPostProcessor的类
			 * 序号1.1
			 */
			if (postProcessor instanceof BeanDefinitionRegistryPostProcessor) {
				BeanDefinitionRegistryPostProcessor registryProcessor =
						(BeanDefinitionRegistryPostProcessor) postProcessor;
				//这里直接执行程序员通过API注入的beanDefinitionRegistryPostProcessor的实现类
				registryProcessor.postProcessBeanDefinitionRegistry(registry);
				registryProcessors.add(registryProcessor);
			}
			else {
				// 序号1.2 将beanFactoryPostProcessor添加到regularPostProcessors
				regularPostProcessors.add(postProcessor);
			}
		}

		// Do not initialize FactoryBeans here: We need to leave all regular beans
		// uninitialized to let the bean factory post-processors apply to them!
		// Separate between BeanDefinitionRegistryPostProcessors that implement
		// PriorityOrdered, Ordered, and the rest.
		//这里的这个list是用来存放spring中实现了beanFactoryRegistryPostProcessor接口的实现类
		List<BeanDefinitionRegistryPostProcessor> currentRegistryProcessors = new ArrayList<>();

		// First, invoke the BeanDefinitionRegistryPostProcessors that implement PriorityOrdered.
		/**
		 * 序号2
		 *获取到了一个BeanDefinitionRegistryPostProcessor的实现类 --  ConfigurationClassPostprocessor
		 * 并且这里也只会获取到一个,因为截止到目前,spring容器中还没有我们自己写的业务类,只有spring自己注入的集合bean;
		 * 而这几个bean中,只有ConfigurationClassPostProcessor是BeanDefinitionRegistryPostProcessor的实现类
		 *
		 * 需要注意的是:
		 * 	这个类在spring解析扫描初始化的时候用到了,ConfigurationClassPostProcessor是最重要的一个
		 *
		 * 在这里获取beanDefinitionRegistryPostProcessor类型的bean的时候,会对bean一个合并,也就是所谓的mergeBean
		 * 在后面finishBeanFactoryInitialization方法中,对bean进行实例化的时候,会再判断一次
		 */
		String[] postProcessorNames =
				beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);

		/**
		 * 序号3
		 * spring内部在执行BeanDefinitionRegistryPostProcessor的实现类的时候,是由顺序的
		 * 	实现了PriorityOrdered接口的类 -->  实现了Ordered接口的类  --> other
		 *
		 */
		for (String ppName : postProcessorNames) {
			if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
				currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
				processedBeans.add(ppName);
			}
		}
		//排序,合并spring自己的和程序员自定义的beanFactoryRegistryPostProcessor
		sortPostProcessors(currentRegistryProcessors, beanFactory);
		registryProcessors.addAll(currentRegistryProcessors);
		/**
		 * 序号3.1
		 * invokeBeanDefinitionRegistryPostProcessors这行代码,在本方法中调用了三次
		 * 这里是第一次调用,这是,理论上只有一个,就是ConfigurationClassPostProcessor
		 *
		 */
		invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
		currentRegistryProcessors.clear();

		// Next, invoke the BeanDefinitionRegistryPostProcessors that implement Ordered.
		postProcessorNames = beanFactory.getBeanNamesForType(BeanDefinitionRegistryPostProcessor.class, true, false);
		for (String ppName : postProcessorNames) {
			/**
			 * 可以看到,在第二次和第三次从容器中获取实现类的时候,会先从已经执行过的集合中进行过滤(processedBeans)过滤
			 */
			if (!processedBeans.contains(ppName) && beanFactory.isTypeMatch(ppName, Ordered.class)) {
				currentRegistryProcessors.add(beanFactory.getBean(ppName, BeanDefinitionRegistryPostProcessor.class));
				processedBeans.add(ppName);
			}
		}
		/**
		 * 序号3.2
		 * 这里是第二次调用,执行实现了Ordered接口的类
		 */
		sortPostProcessors(currentRegistryProcessors, beanFactory);
		registryProcessors.addAll(currentRegistryProcessors);
		invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
		currentRegistryProcessors.clear();

		// Finally, invoke all other BeanDefinitionRegistryPostProcessors until no further ones appear.
		/**
		 * 序号3.3
		 * 这里执行的是所有实现了beanDefinitionRegistryPostProcessor且无实现其他接口的类
		 *
		 * 这里为什么要用while(true)?
		 *  因为有可能beanDefinitionRegistryPostProcessor的实现类中有可能会又注入了一个beanDefinitionRegistryPostProcessor的实现类,所以这里要循环查找并执行;
		 *  如果第二次从beanFactory中没有找到beanDefinitionRegistryPostProcessor的实现类,那么,这里reiterate就是false,就不会再执行了
		 *  如果第二次从beanFactory中找到了未执行的实现类,那么就会继续执行,同时,reiterate变为true;然后进行下一轮的循环
		 */
		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);
			invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry);
			currentRegistryProcessors.clear();
		}

		// Now, invoke the postProcessBeanFactory callback of all processors handled so far.
		/**
		 * 序号4
		 * 前面说了,registryProcessors是保存beanDefinitionRegistryPostProcessor接口的实现类
		 * regularPostProcessors保存的是程序员提供的beanFactoryPostProcessor接口的实现类,
		 * 那为什么这里还会有 invokeBeanFactoryPostProcessors(registryProcessors, beanFactory);这行代码?
		 *  原因很简单,一个接口在实现beanDefinitionRegistryPostProcessor接口的同时,必然会实现beanFactoryPostProcessor接口
		 *  所以,这里要执行
		 *  registryProcessors中是spring内置的beanFactoryPostProcessor
		 *  regularPostProcessors是程序员提供的beanFactoryPostProcessor
		 *
		 *  所以,spring源码中,
		 *  	1.会先执行程序员提供的BeanDefinitionRegistryPostProcessor接口的实现类,
		 *  	2.会执行spring自带的	BeanDefinitionRegistryPostProcessor接口的实现类
		 *  	3.然后执行spring自带的	BeanDefinitionRegistryPostProcessor接口的实现类中的postProcessBeanFactory方法
		 *  	4.最后执行程序员提供的	BeanDefinitionRegistryPostProcessor接口的实现类中的postProcessBeanFactory方法
		 */
		invokeBeanFactoryPostProcessors(registryProcessors, beanFactory);
		invokeBeanFactoryPostProcessors(regularPostProcessors, beanFactory);
	}

	else {
		// Invoke factory processors registered with the context instance.
		/**
		 *  如果beanFactory不是BeanDefinitionRegistry类型,就执行BeanFactoryPostProcessor的实现类
		 */
		invokeBeanFactoryPostProcessors(beanFactoryPostProcessors, beanFactory);
	}

	// Do not initialize FactoryBeans here: We need to leave all regular beans
	// uninitialized to let the bean factory post-processors apply to them!
	/**
	 * 这里的是程序员提供的beanFactoryPostProcessor的实现类,是通过@Component注解提供的,而不是ac.addBeanFactoryPostProcessor提供的
	 *
	 * 上面执行的,仅仅是程序员通过add到spring容器中的beanFactoryPostProcessor
	 *
	 * 在对包进行扫描的时候,会把我们定义的通过@Component注入的beanFactoryPostProcessor的实现类,作为beanDefinition注入,然后在这里进行处理:也即:当spring执行到这里的时候,已经将bean转换成了beanDefinition,且存到了BeanDefinitionMaps中
	 */
	String[] postProcessorNames =
			beanFactory.getBeanNamesForType(BeanFactoryPostProcessor.class, true, false);

	// Separate between BeanFactoryPostProcessors that implement PriorityOrdered,
	// Ordered, and the rest.
	/**
	 * BeanFactoryPostProcess的实现类,在执行的时候,也是有优先级的
	 * PriorityOrdered  --> Ordered --> other
	 */
	List<BeanFactoryPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
	List<String> orderedPostProcessorNames = new ArrayList<>();
	List<String> nonOrderedPostProcessorNames = new ArrayList<>();
	for (String ppName : postProcessorNames) {
		//如果当前beanFactoryPostProcessor已经被执行过了,就跳过,无需再次执行
		if (processedBeans.contains(ppName)) {
			// skip - already processed in first phase above
		}
		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);
		}
	}

	// First, invoke the BeanFactoryPostProcessors that implement PriorityOrdered.
	sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
	invokeBeanFactoryPostProcessors(priorityOrderedPostProcessors, beanFactory);

	// Next, invoke the BeanFactoryPostProcessors that implement Ordered.
	List<BeanFactoryPostProcessor> orderedPostProcessors = new ArrayList<>();
	for (String postProcessorName : orderedPostProcessorNames) {
		orderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
	}
	sortPostProcessors(orderedPostProcessors, beanFactory);
	invokeBeanFactoryPostProcessors(orderedPostProcessors, beanFactory);

	// Finally, invoke all other BeanFactoryPostProcessors.
	List<BeanFactoryPostProcessor> nonOrderedPostProcessors = new ArrayList<>();
	for (String postProcessorName : nonOrderedPostProcessorNames) {
		nonOrderedPostProcessors.add(beanFactory.getBean(postProcessorName, BeanFactoryPostProcessor.class));
	}
	invokeBeanFactoryPostProcessors(nonOrderedPostProcessors, beanFactory);

	// Clear cached merged bean definitions since the post-processors might have
	// modified the original metadata, e.g. replacing placeholders in values...
	beanFactory.clearMetadataCache();
}

方法里面的注释我分别标上了序号,其中,在序号3.1这里的invokeBeanDefinitionRegistryPostProcessors(currentRegistryProcessors, registry)
方法中,完成了对@ComponeneScan注解的处理,将包中添加了@Component注解的业务类解析成BeanDefinition,存入到BeanDefinitionMap中

扩展

本身而言,BeanFactoryPostProcessor和BeanDefinitionRegistryPostProcessor是spring的扩展点;
如果我们自己声明一个类,实现了BeanFactoryPostProcessor接口,那我们可以在实现类中,获取到beanFactory对象,可以对所有的beanDefinition进行操作(因为在spring源码中,会先执行spring字段的ConfigurationClassPostProcessor,完成bean的扫描,并将bean转换为beanDefinition,存入到beanDefinitionMap中);但是这个扩展点的执行时机,太早了,我觉得一般的业务代码,可能不怎么会用到的这个扩展点。

你可能感兴趣的:(spring源码)