Spring IOC源码:registerBeanPostProcessors 详解

Spring源码系列:

Spring IOC源码:简单易懂的Spring IOC 思路介绍
Spring IOC源码:核心流程介绍
Spring IOC源码:ApplicationContext刷新前准备工作
Spring IOC源码:obtainFreshBeanFactory 详解(上)
Spring IOC源码:obtainFreshBeanFactory 详解(中)
Spring IOC源码:obtainFreshBeanFactory 详解(下)
Spring IOC源码:<context:component-scan>源码详解
Spring IOC源码:invokeBeanFactoryPostProcessors 后置处理器详解
Spring IOC源码:registerBeanPostProcessors 详解
Spring IOC源码:实例化前的准备工作
Spring IOC源码:finishBeanFactoryInitialization详解
Spring IoC源码:getBean 详解
Spring IoC源码:createBean( 上)
Spring IoC源码:createBean( 中)
Spring IoC源码:createBean( 下)
Spring IoC源码:finishRefresh 完成刷新详解

前言

上篇文章介绍了后置处理器BeanFactoryPostProcessor的注册、实例化及执行操作,这节介绍一下另外一个后置处理器BeanPostProcessor。前者是针对BeanFactory工厂对象进行增上改查操作,在bean实例化之前,我们可以修改其定义。后者是对实例化后的初始化环节前后对实例对象进行操作。

正文

进入refresh中的registerBeanPostProcessors(beanFactory)方法。该方法会将beanFactory工厂中所有BeanPostProcessor类型的BeanDefinition定义信息进行实例化注册,以便在bean的初始化环节中调用。

	protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) {
		PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this);
	}

PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this),见方法1详解

方法1:registerBeanPostProcessors

public static void registerBeanPostProcessors(
			ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {
		//从BeanFactory工厂中获取BeanPostProcessor的实现类beanName
		String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);

		//定义目标长度
		int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length;
		//添加BeanPostProcessorChecker到beanFactory工厂中的beanPostProcessors集合中
		//这是个内部类,用来检查是否在bean的创建过程中,经过了所有本来应经过的后置处理器
		beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));

		//实现了PriorityOrdered接口的后置处理器集合
		List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
		//内部的后置处理器集合
		List<BeanPostProcessor> internalPostProcessors = new ArrayList<>();
		//实现了Ordered接口的后置处理器集合
		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);
				}
			}
			//Ordered类型
			else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
				orderedPostProcessorNames.add(ppName);
			}
			else {
				nonOrderedPostProcessorNames.add(ppName);
			}
		}

		//对集合中的后置处理器进行排序
		sortPostProcessors(priorityOrderedPostProcessors, 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);
			}
		}
		//排序
		sortPostProcessors(orderedPostProcessors, beanFactory);
		//注册添加到集合中
		registerBeanPostProcessors(beanFactory, orderedPostProcessors);

		// 处理普通的后置处理器
		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);
			}
		}
		//注册添加到集合中
		registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);

		// 最后对所有的内部后置处理器进行排序,注册处理
		sortPostProcessors(internalPostProcessors, beanFactory);
		registerBeanPostProcessors(beanFactory, internalPostProcessors);

		//移除之前添加的ApplicationListenerDetector,将其放到最后端
		beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext));
	}

sortPostProcessors(priorityOrderedPostProcessors, beanFactory),方法我们在上篇文章中讲解《invokeBeanFactoryPostProcessors》中方法6

registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors),见方法2详解

beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext)):

之前在refresh中的方法prepareBeanFactory添加过ApplicationListenerDetector,这里主要是排序,将该类型的后置处理器移到最后面来。

方法2:registerBeanPostProcessors

	private static void registerBeanPostProcessors(
			ConfigurableListableBeanFactory beanFactory, List<BeanPostProcessor> postProcessors) {

		for (BeanPostProcessor postProcessor : postProcessors) {
			beanFactory.addBeanPostProcessor(postProcessor);
		}
	}
	public void addBeanPostProcessor(BeanPostProcessor beanPostProcessor) {
		Assert.notNull(beanPostProcessor, "BeanPostProcessor must not be null");
		// 如果之前容器中存在该对象,则移除
		this.beanPostProcessors.remove(beanPostProcessor);
		// 如果是InstantiationAwareBeanPostProcessor类型的后置处理器,则标识为已注册
		if (beanPostProcessor instanceof InstantiationAwareBeanPostProcessor) {
			this.hasInstantiationAwareBeanPostProcessors = true;
		}
		// 如果是DestructionAwareBeanPostProcessor类型的后置处理器,则标识为已注册
		if (beanPostProcessor instanceof DestructionAwareBeanPostProcessor) {
			this.hasDestructionAwareBeanPostProcessors = true;
		}
		// 添加到集合末尾
		this.beanPostProcessors.add(beanPostProcessor);
	}

自定义

我们知道BeanPostProcessor实现类会在bean实例化后,初始化环节中进行调用,那我们如何自定义一个BeanPostProcessor 实现类并注册到工厂中呢?上篇文章我们演示了如何自定义BeanFactoryPostProcessor,其操作方法也是类型的;

1、自定义BeanPostProcessor

public class MyBeanPostProcessor implements BeanPostProcessor {
	@Override
	public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
		System.out.println("after:"+beanName);
		return null;
	}

	@Override
	public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
		System.out.println("before:"+beanName);
		return null;
	}
}

2、自定义上下文子类

通过拓展接口postProcessBeanFactory我们可以拿到工厂对象,并对其注册。

public class MyClassPathApplicationContext extends ClassPathXmlApplicationContext {

	public MyClassPathApplicationContext(String path){
		super(path);
	}

	@Override
	protected void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) {
		beanFactory.addBeanPostProcessor(new MyBeanPostProcessor());
	}

}

3、编写入口

public class PersonTest {
	public static void main(String[] args) {

		MyClassPathApplicationContext applicationContext=new MyClassPathApplicationContext("application-scan.xml");
		StudentDao zdcDomain = (StudentDao) applicationContext.getBean("studentDao");
		System.out.println(zdcDomain);
	}
}

在这里插入图片描述

总结

BeanPostProcessor和BeanFactoryPostProcessor都属于IOC后置处理器,只是两者操作的对象不一样,并且调用时间点也不一样;
BeanPostProcessor:在bean实例化后的初始化环节中进行调用,可以对实例化的bean对象进行操作。
BeanFactoryPostProcessor:在实例化前进行调用,可以修改bean的定义信息。

  • 9
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

@猪大肠

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值