当前位置:首页 > 编程笔记 > 正文
已解决

10. Spring源码篇之BeanPostProcessor

来自网友在路上 176876提问 提问时间:2023-11-19 08:47:54阅读次数: 76

最佳答案 问答题库768位专家为你答疑解惑

简介

在Bean的创建过程中会有很多的后置处理器,例如实例化前、实例化后、初始化前、初始化后,属性填充等,这些都是通过BeanPostProcessor来实现的

那么既然每个Bean都有有这些生命周期,这些BeanPostProcessor肯定需要提前知道,并且实例化出来保存,而我们前面介绍来BeanDefinition的扫描,就可以把所有的Bean找出来,只要在实例化单例Bean之前把BeanPostProcessor实例化好就行了

在spring中就有这么一步注册BeanPostProcessor
就在AbstractApplicationContext#refresh方法中的一步registerBeanPostProcessors(beanFactory);

源码解析

public static void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {// 通过getBeanNamesForType可以拿到所有的名字,因为这个时候还没有实例化,所以就拿到名字,里面使用isTypeMatch匹配String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();    // 找出所有实现 PriorityOrdered的BeanPostProcessorList<BeanPostProcessor> internalPostProcessors = new ArrayList<>();    // 内置的BeanPostProcessor 如 MergedBeanDefinitionPostProcessorList<String> orderedPostProcessorNames = new ArrayList<>();    // 找出所有实现 Ordered的BeanPostProcessorList<String> nonOrderedPostProcessorNames = new ArrayList<>();    // 没有任何排序的BeanPostProcessorfor (String ppName : postProcessorNames) {if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {// 通过getBean获得BeanPostProcessor对象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);}}sortPostProcessors(priorityOrderedPostProcessors, beanFactory);    // 升序排序registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors); // 注册BeanPostProcessorsList<BeanPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());for (String ppName : orderedPostProcessorNames) {BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);         // 通过getBean获得BeanPostProcessor对象orderedPostProcessors.add(pp);if (pp instanceof MergedBeanDefinitionPostProcessor) {internalPostProcessors.add(pp);}}sortPostProcessors(orderedPostProcessors, beanFactory);    // 升序排序registerBeanPostProcessors(beanFactory, orderedPostProcessors); // 注册BeanPostProcessorsList<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());for (String ppName : nonOrderedPostProcessorNames) {BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);  // 通过getBean获得BeanPostProcessor对象nonOrderedPostProcessors.add(pp);if (pp instanceof MergedBeanDefinitionPostProcessor) {internalPostProcessors.add(pp);}}registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);sortPostProcessors(internalPostProcessors, beanFactory);     // 升序排序 MergedBeanDefinitionPostProcessor排在最后registerBeanPostProcessors(beanFactory, internalPostProcessors);beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext)); //注册 ApplicationListenerDetector 这个后续将
}

注册也会有个先后顺序,首先是实现了PriorityOrdered的排在前面,然后是实现Ordered接口的,再然后是没有现实排序接口的,最后是内置的例如MergedBeanDefinitionPostProcessor

这些BeanPostProcessor都会注册,通过beanFactory缓存起来

private final List<BeanPostProcessor> beanPostProcessors = new BeanPostProcessorCacheAwareList();public void addBeanPostProcessor(BeanPostProcessor beanPostProcessor) {Assert.notNull(beanPostProcessor, "BeanPostProcessor must not be null");this.beanPostProcessors.remove(beanPostProcessor);this.beanPostProcessors.add(beanPostProcessor);
}

总结

从上面的代码中可以看出,在其他的单例Bean实例化之前,会先把BeanPostProcessor实例化好,并且排序

后面讲实例化前的BeanPostProcessor


欢迎关注,学习不迷路!

查看全文

99%的人还看了

猜你感兴趣

版权申明

本文"10. Spring源码篇之BeanPostProcessor":http://eshow365.cn/6-39094-0.html 内容来自互联网,请自行判断内容的正确性。如有侵权请联系我们,立即删除!