Spring扩展接口解析4--bean后置处理器BeanPostProcessor接口
本文内容纲要:
- 前言- 1、BeanPostProcessor接口
- 2、后置处理器的使用
- 3、后置处理器的实现原理
- 3.1、初始化后置处理器
- 3.2、 添加后置处理器
- 4、BeanPostProcessor的子接口
- 4.1、InstantiationAwareBeanPostProcessor
- 4.2、MergedBeanDefinitionPostProcessor
- 4.3、SmartInstantiationAwareBeanPostProcessor
- 4.4、DestructionAwareBeanPostProcessor
- 5、Spring的核心后置处理器(*)
- 5.1、AutowiredAnnotationBeanPostProcessor(@Autowired注解处理器)
- 5.2、CommonAnnotationBeanPostProcessor(@Resource注解处理器)
- 5.3、ApplicationContextAwareProcessor(Aware子接口方法执行)
- 6、Extra(*)
前言
众所周知,Spring的核心思想为IOC和AOP,而AOP实际就是在对业务代码进行逻辑增强,以切面的形式将需要增强的代码加入到业务代码前后去执行。而处理业务代码的增强,在Bean的初始化过程中通用采用了AOP设计思想,来对bean进行功能增强。
比如Spring容器加载了bean之后,如果需要对所有的bean,或者某部分bean进行功能增强时,此时就可以采用一个叫做后置处理器的工具来对bean进行增强或扩展,Spring中的后置处理器也就是BeanPostProcessor接口。
1、BeanPostProcessor接口
BeanPostProcessor接口就是Spring后置处理器的顶级接口,该接口只有两个方法,一个是在bean执行初始化方法之前执行,一个是在bean执行初始化方法之后执行,源码如下:
1 public interface BeanPostProcessor { 2
3 /**
4 * bean执行初始化方法之前执行该方法
5 */
6 @Nullable
7 default Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
8 return bean;
9 }
10
11 /**
12 * bean执行初始化之后执行该方法
13 */
14 @Nullable
15 default Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
16 return bean;
17 }
18 }
Spring容器加载bean的时候,会先创建bean,然后对bean进行属性注入,然后再执行bean的初始化方法,而后置处理器就是在bean执行初始化方法initializeBean方法中进行处理的,逻辑代码如下:
1 protected Object initializeBean(final String beanName, final Object bean, @Nullable RootBeanDefinition mbd) { 2
3 /**1.执行实现了Aware系列接口的方法*/
4 invokeAwareMethods(beanName, bean);
5
6 Object wrappedBean = bean;
7 /** 2.遍历执行所有后置处理器的初始化之前处理方法*/
8 if (mbd == null || !mbd.isSynthetic()) {
9 wrappedBean = applyBeanPostProcessorsBeforeInitialization(wrappedBean, beanName);
10 }
11
12 /** 3.执行初始化方法*/
13 invokeInitMethods(beanName, wrappedBean, mbd);
14
15 /** 4.遍历执行所有后置处理器的初始化之后处理方法*/
16 if (mbd == null || !mbd.isSynthetic()) {
17 wrappedBean = applyBeanPostProcessorsAfterInitialization(wrappedBean, beanName);
18 }
19 return wrappedBean;
20 }
1 @Override
2 public Object applyBeanPostProcessorsBeforeInitialization(Object existingBean, String beanName)
3 throws BeansException {
4
5 Object result = existingBean;
6 /** 遍历执行postProcessBeforeInitialization方法*/
7 for (BeanPostProcessor processor : getBeanPostProcessors()) {
8 Object current = processor.postProcessBeforeInitialization(result, beanName);
9 if (current == null) {
10 return result;
11 }
12 result = current;
13 }
14 return result;
15 }
16
17 @Override
18 public Object applyBeanPostProcessorsAfterInitialization(Object existingBean, String beanName)
19 throws BeansException {
20
21 Object result = existingBean;
22 /** 遍历执行postProcessAfterInitialization方法*/
23 for (BeanPostProcessor processor : getBeanPostProcessors()) {
24 Object current = processor.postProcessAfterInitialization(result, beanName);
25 if (current == null) {
26 return result;
27 }
28 result = current;
29 }
30 return result;
31 }
可以看出在bean执行初始化之前,会遍历所有后置处理器,执行后置处理器的postProcessBeforeInitialization方法,而在初始化之后会遍历所有后置处理器,执行postProcessorAfterInitialization方法。
2、后置处理器的使用
自定义后置处理器,作用是在bean初始化之前打印日志,bean初始化之后如果beanName是以xxxService命名的,则通过bean的Class重新创建一个bean对象,自定义后置处理器代码如下:
1 public class MyBeanPostProcessor implements BeanPostProcessor { 2
3 @Override
4 public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException {
5 System.out.println("后置处理器 初始化方法之前执行");
6 return bean;
7 }
8
9 @Override
10 public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException {
11 System.out.println("后置处理器 初始化方法之后执行");
12 if(beanName.endsWith("Service")){
13 try {
14 System.out.println("通过类的newInstance方法创造对象");
15 Class c = bean.getClass();
16 bean = c.newInstance();
17 } catch (Exception e) {
18 e.printStackTrace();
19 }
20 }
21 return bean;
22 }
23
24 }
定义GoodsService类代码如下:
1 public class GoodsService { 2
3 private String orderCode;
4 private String goodsCode;
5
6 public GoodsService(){
7
8 }
9
10 public GoodsService(String goodsCode, String orderCode){
11 this.goodsCode = goodsCode;
12 this.orderCode = orderCode;
13 }
14
15 public void init(){
16 System.out.println("执行init方法");
17 }
18
19 public String getOrderCode() {
20 return orderCode;
21 }
22
23 public void setOrderCode(String orderCode) {
24 this.orderCode = orderCode;
25 }
26
27 public String getGoodsCode() {
28 return goodsCode;
29 }
30
31 public void setGoodsCode(String goodsCode) {
32 this.goodsCode = goodsCode;
33 }
34 }
application.xml添加bean和后置处理器的声明,代码如下:
1 <?xml version="1.0" encoding="UTF-8" ?> 2 <beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop"
4 xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">
5
6
7
8 <bean id="goodsService" class="com.lucky.test.spring.demo.GoodsService" init-method="init">
9 <constructor-arg index="0" value="test_order_code_1"/>
10 <constructor-arg index="1" value="test_goods_code_1"/>
11 </bean>
12 <bean id="goods" class="com.lucky.test.spring.demo.GoodsService" init-method="init">
13 <constructor-arg index="0" value="test_order_code_2"/>
14 <constructor-arg index="1" value="test_goods_code_2"/>
15 </bean>
16
17 <bean id="myBeanPostProcessor" class="com.lucky.test.spring.demo.MyBeanPostProcessor"/>
18
19 </beans>
本案例中,分别声明两个GoodsService类的bean,一个beanName为goodsService,一个beanName为goods,而自定义的后置处理器只处理beanName的后缀为Service的bean,所以这里会处理goodsService这个bean,测试代码如下:
1 public static void main(String[] args) throws Exception {2 ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("application.xml");
3 GoodsService goodsService = context.getBean("goodsService", GoodsService.class);
4 GoodsService goods = context.getBean("goods", GoodsService.class);
5 System.out.println(goodsService.getGoodsCode());
6 System.out.println(goods.getGoodsCode());
7 }
从容器中获取这两个bean,分别调用getGoodsCode()方法,由于在配置bean的时候才有的构造器方式注入属性,所以该bean的goodsCode属性应该是有值的,测试结果如下:
1 后置处理器 初始化方法之前执行2 执行init方法
3 后置处理器 初始化方法之后执行
4 通过类的newInstance方法创造对象
5 后置处理器 初始化方法之前执行
6 执行init方法
7 后置处理器 初始化方法之后执行
8 null
9 test_order_code_2
可以看出goodsService这个bean被后置处理器重新处理了,才有newInstance方法重新创建了一个对象,替换了通过构造器创建的bean,所以原先通过构造器方法注入的属性值为null,而goods这个bean没有被后置处理器处理,还是构造器创建的bean对象。
从案例可以看出,后置处理器可以对Spring容器中的bean做很多的后置处理,比如强制执行bean的某些方法,给bean注入属性,甚至是直接将初始化的bean直接替换掉也可以。
3、后置处理器的实现原理
在Spring容器初始化的时候,会初始化所有的后置处理器,而后置处理器本身也是一个bean,所以也是归Spring容器所管理的,当bean初始化的过程中,会从Spring容器中获取所有的后置处理器,分别遍历执行后置处理器的方法,从而来对bean进行处理。
3.1、初始化后置处理器
Spring容器BeanFactory的子接口ConfigurableBeanFactory接口中定义了方法addPostProcessor,用于容器动态添加后置处理器
1 void addBeanPostProcessor(BeanPostProcessor beanPostProcessor);
该接口的默认实现类是AbstractBeanFactory,实现代码如下:
1 /** Spring容器的后置处理器集合 */ 2 private final List<BeanPostProcessor> beanPostProcessors = new CopyOnWriteArrayList<>();
3
4 /** Indicates whether any InstantiationAwareBeanPostProcessors have been registered. */
5 private volatile boolean hasInstantiationAwareBeanPostProcessors;
6
7 /** Indicates whether any DestructionAwareBeanPostProcessors have been registered. */
8 private volatile boolean hasDestructionAwareBeanPostProcessors;
9
10 @Override
11 public void addBeanPostProcessor(BeanPostProcessor beanPostProcessor) {
12 // 从List中先删除该处理器
13 this.beanPostProcessors.remove(beanPostProcessor);
14 // Track whether it is instantiation/destruction aware
15 if (beanPostProcessor instanceof InstantiationAwareBeanPostProcessor) {
16 this.hasInstantiationAwareBeanPostProcessors = true;
17 }
18 if (beanPostProcessor instanceof DestructionAwareBeanPostProcessor) {
19 this.hasDestructionAwareBeanPostProcessors = true;
20 }
21 //将后置处理器加入List中
22 this.beanPostProcessors.add(beanPostProcessor);
23 }
addBeanPostProcessor方法的逻辑比较简单,Spring容器内部有一个所有后置处理器的列表,每次加入新的后置处理器,就会加入到列表中即可,另外还有两个boolean类型的属性,分别表示如果当前加入的后置处理器如果是指定的类型,就将指定的属性值置为true
3.2、 添加后置处理器
从3.1可知Spring容器会保存所有后置处理器,所以就需要向Spring容器去添加,添加的逻辑是在Spring容器初始化的时候。Spring容器初始化的时候执行refresh()方法时,该方法内会注册所有后置和处理器,方法如下:
1 /** 注册所有后置处理器*/2 registerBeanPostProcessors(beanFactory);
该方法会注册所有后置处理器到Spring容器中,实际也就是调用3.1中的addBeanPostProcesser方法,后置处理器实际的执行是给getBean的过程中,准确点将是在bean初始化的过程中。
接下来就看下是如何注册所有后置处理器的,registerBeanPostProcessors方法源码如下:
1 /** 委托PostProcessorRegistrationDelegate来给当前容器注册后置处理器*/ 2 protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) {
3 PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this);
4 }
5
6 /**
7 * Spring容器注册后置处理器
8 * @param beanFactory:加载了所有bean的容器
9 * @param applicationContext:当前Spring上下文
10 * @deprecated 从beanFactory中找到所有BeanPostProcessor接口的bean加入到applicationContext中
11 * */
12 public static void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) {
13
14 /**
15 * 1. 从BeanFactory中找到所有BeanPostProcessor的bean
16 * */
17 String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false);
18
19 int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length;
20 //注册BeanPostProcessorChecker后置处理器,该处理器用于校验后置处理器的注册
21 beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));
22
23 /**
24 * 2.定义了多个后置处理器列表
25 * priorityOrderedPostProcessors用于存储实现了PriorityOrdered接口的后置处理器(用于排序)
26 * orderedPostProcessorNames用于存储实现了Ordered接口的后置处理器(用于排序)
27 * nonOrderedPostProcessorNames用于存储没有实现排序接口的后置处理器
28 * */
29 List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>();
30 List<BeanPostProcessor> internalPostProcessors = new ArrayList<>();
31 List<String> orderedPostProcessorNames = new ArrayList<>();
32 List<String> nonOrderedPostProcessorNames = new ArrayList<>();
33 /**
34 * 3.遍历所有后置处理器
35 * */
36 for (String ppName : postProcessorNames) {
37 if (beanFactory.isTypeMatch(ppName, PriorityOrdered.class)) {
38 BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
39 //3.1.将实现了PriorityOrdered接口的后置处理器加入到对应列表中
40 priorityOrderedPostProcessors.add(pp);
41 if (pp instanceof MergedBeanDefinitionPostProcessor) {
42 internalPostProcessors.add(pp);
43 }
44 }
45 else if (beanFactory.isTypeMatch(ppName, Ordered.class)) {
46 //3.2.将实现了Ordered接口的后置处理器加入到对应列表中
47 orderedPostProcessorNames.add(ppName);
48 }
49 else {
50 //3.3.没有实现排序接口的后置处理器加入到对应列表中
51 nonOrderedPostProcessorNames.add(ppName);
52 }
53 }
54
55 /**
56 * 4.分别将三个列表中的后置处理器进行排序,注册到Spring容器中
57 * */
58 //4.1.将实现了PriorityOrdered接口的后置处理器进行排序
59 sortPostProcessors(priorityOrderedPostProcessors, beanFactory);
60 //4.2.将排序后的列表注册到容器中
61 registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors);
62
63
64 List<BeanPostProcessor> orderedPostProcessors = new ArrayList<>(orderedPostProcessorNames.size());
65 for (String ppName : orderedPostProcessorNames) {
66 BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
67 orderedPostProcessors.add(pp);
68 if (pp instanceof MergedBeanDefinitionPostProcessor) {
69 internalPostProcessors.add(pp);
70 }
71 }
72 //4.3.将实现了Ordered接口的后置处理器进行排序
73 sortPostProcessors(orderedPostProcessors, beanFactory);
74 //4.4.将排序后的列表注册到容器中
75 registerBeanPostProcessors(beanFactory, orderedPostProcessors);
76
77 List<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>(nonOrderedPostProcessorNames.size());
78 for (String ppName : nonOrderedPostProcessorNames) {
79 BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class);
80 nonOrderedPostProcessors.add(pp);
81 if (pp instanceof MergedBeanDefinitionPostProcessor) {
82 internalPostProcessors.add(pp);
83 }
84 }
85 //4.5将所有无序的列表注册到Spring容器中
86 registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);
87
88 //4.6将所有实现了MergedBeanDefinitionPostProcessor接口的后置处理器进行排序
89 sortPostProcessors(internalPostProcessors, beanFactory);
90 //4.6.将排序后的列表注册到Spring容器中
91 registerBeanPostProcessors(beanFactory, internalPostProcessors);
92
93 //5.添加ApplicationListenerDetector类型的后置处理器
94 beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext));
95 }
96
97 private static void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory, List<BeanPostProcessor> postProcessors) {
98
99 /** 遍历执行Spring容器的addBeanPostProcessor方法 */
100 for (BeanPostProcessor postProcessor : postProcessors) {
101 beanFactory.addBeanPostProcessor(postProcessor);
102 }
103 }
从源码上逻辑也比较清晰,总结步骤如下:
1、从BeanFactory中根据BeanPostProcessor类型找到所有注册的后置处理器的bean
2、判断后置处理器是否实现了PriorityOrdered接口、Ordered接口和没有实现任何排序接口,分别加入到对应的列表中
3、分别对各个列表中的后置处理器进行排序,然后遍历加入到Spring容器中
Tip:
1、PriorityOrdered接口是继承之Ordered接口,该接口没有额外定义方法,所以仅仅是起到了一个标志的作用,而Ordered接口是用于排序
2、后置处理器的注册顺序为,优先所有PriorityOrdered实现类进行排序;再按Ordered实现类进行排序,最后才注册所有无序的后置处理器
4、BeanPostProcessor的子接口
BeanPostProcessor只有两个方法,一个是在bean初始化之前执行,一个是在bean初始化之后执行,而除了这两个方法,Spring还提供了在其他情况下执行的后置处理逻辑,这就需要使用BeanPostProcessor的子接口来实现。
4.1、InstantiationAwareBeanPostProcessor
用于处理bean实例化前后的处理操作,Spring容器获取bean时需要先创建bean(实例化),然后在对bean的属性进行赋值(初始化),BeanPostProcessor接口的两个方法分别是在bean初始化前后来执行的,而InstanitationAwareBeanPostProcessor提供的方法则是分别在Bean实例化前后来处理的方法,提供的方法如下:
1 public interface InstantiationAwareBeanPostProcessor extends BeanPostProcessor { 2
3 /**
4 * bean实例化之前直接返回一个对象(如代理对象)来代替通过构造器创建的对象
5 */
6 @Nullable
7 default Object postProcessBeforeInstantiation(Class<?> beanClass, String beanName) throws BeansException {
8 return null;
9 }
10
11 /**
12 * bean实例化之后,在populateBean方法中执行,在setter属性注入之前执行
13 * 如果返回true表示需要属性依赖注入
14 * 如果返回false表示不需要属性依赖注入
15 */
16 default boolean postProcessAfterInstantiation(Object bean, String beanName) throws BeansException {
17 return true;
18 }
19
20 /**
21 * 对于bean的属性值进行设置操作,在populateBean方法中执行,在setter属性注入之前执行
22 */
23 @Nullable 24 default PropertyValues postProcessProperties(PropertyValues pvs, Object bean, String beanName)
25 throws BeansException {
27 return null;
28 }
29 }
InstantiationAwareBeanPostProcessor接口在父接口BeanPostProcessor的基础之上添加了三个方法,分别是在bean实例化前后以及属性注入之前设置属性三个方法。执行的源码如下:
4.1.1、postProcessBeforeInstantiation方法执行
bean的实例是调用容器的createBean方法来进行创建,createBean方法逻辑代码如下:
1 @Override 2 protected Object createBean(String beanName, RootBeanDefinition mbd, @Nullable Object[] args)
3 throws BeanCreationException {
4 RootBeanDefinition mbdToUse = mbd;
5 mbdToUse.prepareMethodOverrides();
6
7 /***
8 * 1.通过InstantiationAwareBeanPostProcessor 实例化bean
9 * * */
10 Object bean = resolveBeforeInstantiation(beanName, mbdToUse);
11 if (bean != null) {
12 return bean;
13 }
14
15 /**
16 * 2.通过构造函数实例bean
17 * */
18 Object beanInstance = doCreateBean(beanName, mbdToUse, args);
19 return beanInstance;
20 }
1 @Nullable
2 protected Object resolveBeforeInstantiation(String beanName, RootBeanDefinition mbd) {
3 Object bean = null;
4 if (!Boolean.FALSE.equals(mbd.beforeInstantiationResolved)) {
5 /** 判断容器中是否有 InstantiationAwareBeanPostProcessor 后置处理器*/
6 if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
7 Class<?> targetType = determineTargetType(beanName, mbd);
8 if (targetType != null) {
9 /** 执行applyBeanPostProcessorBeforeInstantiation方法*/
10 bean = applyBeanPostProcessorsBeforeInstantiation(targetType, beanName);
11 if (bean != null) {
12 bean = applyBeanPostProcessorsAfterInitialization(bean, beanName);
13 }
14 }
15 }
16 mbd.beforeInstantiationResolved = (bean != null);
17 }
18 return bean;
19 }
20
21 @Nullable
22 protected Object applyBeanPostProcessorsBeforeInstantiation(Class<?> beanClass, String beanName) {
23 /**
24 * 遍历所有的InstantiationAwareBeanPostProcessor,依次执行postProcessBeforeInstantiation方法
25 * */
26 for (BeanPostProcessor bp : getBeanPostProcessors()) {
27 if (bp instanceof InstantiationAwareBeanPostProcessor) {
28 InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
29 Object result = ibp.postProcessBeforeInstantiation(beanClass, beanName);
30 if (result != null) {
31 return result;
32 }
33 }
34 }
35 return null;
36 }
整体逻辑比较清晰,createBean时先通过InstantationAwareBeanPostProcessor后置处理器处理,从容器中找到所有InstantationAwareBeanPostProcessor,然后遍历一次执行postProcessorBeforeInstantiation方法,执行完之后如果bean不为空,表示当前的bean不需要通过构造器来创建,而是直接通过后置处理器来创建的,此时就不会在执行doCreateBean方法来。如果没有后置处理器,才会执行doCreateBean方法通过构造器的方式来创建bean
4.1.2、postProcessAfterInstantiation方法和postProcessProperties方法执行
postProcessAfterInstantiation方法是在方法实例化之后执行,在属性填充之前执行,在doCreateBean方法之中,会先通过构造器方法创建bean,然后调用populateBean方法对bean进行填充,方法如下:
1 protected void populateBean(String beanName, RootBeanDefinition mbd, @Nullable BeanWrapper bw) { 2
3 /**
4 * 1、遍历所有的InstantiationAwareBeanPostProcessor后置处理器
5 * 依次执行postProcessAfterInstantiation方法
6 * */
7 if (!mbd.isSynthetic() && hasInstantiationAwareBeanPostProcessors()) {
8 for (BeanPostProcessor bp : getBeanPostProcessors()) {
9 if (bp instanceof InstantiationAwareBeanPostProcessor) {
10 InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
11 if (!ibp.postProcessAfterInstantiation(bw.getWrappedInstance(), beanName)) {
12 return;
13 }
14 }
15 }
16 }
17
18 PropertyValues pvs = (mbd.hasPropertyValues() ? mbd.getPropertyValues() : null);
19
20 /**
21 * 2.属性注入
22 * */
23 int resolvedAutowireMode = mbd.getResolvedAutowireMode();
24 if (resolvedAutowireMode == AUTOWIRE_BY_NAME || resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
25 MutablePropertyValues newPvs = new MutablePropertyValues(pvs);
26 // Add property values based on autowire by name if applicable.
27 if (resolvedAutowireMode == AUTOWIRE_BY_NAME) {
28 autowireByName(beanName, mbd, bw, newPvs);
29 }
30 // Add property values based on autowire by type if applicable.
31 if (resolvedAutowireMode == AUTOWIRE_BY_TYPE) {
32 autowireByType(beanName, mbd, bw, newPvs);
33 }
34 pvs = newPvs;
35 }
36
37 boolean hasInstAwareBpps = hasInstantiationAwareBeanPostProcessors();
38 boolean needsDepCheck = (mbd.getDependencyCheck() != AbstractBeanDefinition.DEPENDENCY_CHECK_NONE);
39
40 PropertyDescriptor[] filteredPds = null;
41 if (hasInstAwareBpps) {
42 if (pvs == null) {
43 pvs = mbd.getPropertyValues();
44 }
45 /**
46 * 3.遍历所有的InstantiationAwareBeanPostProcessor后置处理器
47 * 依次执行postProcessProperties方法
48 * */
49 for (BeanPostProcessor bp : getBeanPostProcessors()) {
50 if (bp instanceof InstantiationAwareBeanPostProcessor) {
51 InstantiationAwareBeanPostProcessor ibp = (InstantiationAwareBeanPostProcessor) bp;
52 PropertyValues pvsToUse = ibp.postProcessProperties(pvs, bw.getWrappedInstance(), beanName);
53 if (pvsToUse == null) {
54 if (filteredPds == null) {
55 filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
56 }
57 pvsToUse = ibp.postProcessPropertyValues(pvs, filteredPds, bw.getWrappedInstance(), beanName);
58 if (pvsToUse == null) {
59 return;
60 }
61 }
62 pvs = pvsToUse;
63 }
64 }
65 }
66 if (needsDepCheck) {
67 if (filteredPds == null) {
68 filteredPds = filterPropertyDescriptorsForDependencyCheck(bw, mbd.allowCaching);
69 }
70 checkDependencies(beanName, mbd, filteredPds, pvs);
71 }
72
73 if (pvs != null) {
74 applyPropertyValues(beanName, mbd, bw, pvs);
75 }
76 }
可以看出逻辑比较清晰,先是遍历所有的后置处理器,依次执行postProcessAfterInstantiation方法,然后是对bean进行依赖注入,然后在遍历所有的后置处理器,依次执行postProcessProperties方法进行属性设置
4.2、MergedBeanDefinitionPostProcessor
MergedBeanDefiniationPostProcessor是用于合并bean定义时用到的处理器,当一个bean存在有父bean时,在初始化bean之后,需要将父bean的属性合并到该bean的实例中。另外对于bean需要注入的元数据,也可以通过该处理器来对bean进行属性注入,
比如Spring框架中常用到的@Autowired注解就是通过MergedBeanDefinitionPostProcessor来实现的,因为通过@Autowired注解注入的属性是没有setter方法的,也不是通过构造器注入的,所以需要额外的处理器来对bean的属性进行注入。
MergedBeanDefiniationPostProcessor接口方法定义如下:
1 public interface MergedBeanDefinitionPostProcessor extends BeanPostProcessor { 2
3 /**
4 * bean实例化执行,用于处理合并beanDefinition的属性,比如非构造器和setter注入的属性
5 * 在bean实例化执行;属性填充之前执行
6 */
7 void postProcessMergedBeanDefinition(RootBeanDefinition beanDefinition, Class<?> beanType, String beanName);
8
9 /**
10 * 重置bean的定义BeanDefinition
11 */
12 default void resetBeanDefinition(String beanName) {
13 }
14
15 }
MergedBeanDefiniationPostProcessor的执行时间是在bean实例化之后,属性填充方法popluate方法执行之前执行。同样也是在doCreateBean方法中执行的,逻辑如下:
1 protected Object doCreateBean(final String beanName, final RootBeanDefinition mbd, final @Nullable Object[] args) 2 throws BeanCreationException {
3
4 /**
5 * 1、通过构造器创建bean
6 * */
7 BeanWrapper instanceWrapper = null;
8 if (instanceWrapper == null) {
9 instanceWrapper = createBeanInstance(beanName, mbd, args);
10 }
11
12 /**
13 * 2、遍历执行MergedBeanDefinitionPostProcessor的postProcessMergedBeanDefinition方法
14 * */
15 synchronized (mbd.postProcessingLock) {
16 if (!mbd.postProcessed) {
17 try {
18 applyMergedBeanDefinitionPostProcessors(mbd, beanType, beanName);
19 }
20 catch (Throwable ex) {
21 throw new BeanCreationException(mbd.getResourceDescription(), beanName,
22 "Post-processing of merged bean definition failed", ex);
23 }
24 mbd.postProcessed = true;
25 }
26 }
27
28 Object exposedObject = bean;
29 try {
30 /**
31 * 3.属性填充
32 * */
33 populateBean(beanName, mbd, instanceWrapper);
34 /**
35 * 4.执行初始化方法
36 * */
37 exposedObject = initializeBean(beanName, exposedObject, mbd);
38 }
39 return exposedObject;
40 }
1 /**
2 * 遍历执行后置处理器的 postProcessMergedBeanDefinition 方法
3 * */
4 protected void applyMergedBeanDefinitionPostProcessors(RootBeanDefinition mbd, Class<?> beanType, String beanName) {
5 for (BeanPostProcessor bp : getBeanPostProcessors()) {
6 if (bp instanceof MergedBeanDefinitionPostProcessor) {
7 MergedBeanDefinitionPostProcessor bdp = (MergedBeanDefinitionPostProcessor) bp;
8 bdp.postProcessMergedBeanDefinition(mbd, beanType, beanName);
9 }
10 }
11 }
4.3、SmartInstantiationAwareBeanPostProcessor
SmartInstantiationAwareBeanPostProcessor继承之InstantiationAwareBeanPostProcessor,在InstantiationAwareBeanPostProcessor接口的基础之上又额外定义了几个方法,源码如下:
1 public interface SmartInstantiationAwareBeanPostProcessor extends InstantiationAwareBeanPostProcessor { 2
3 /**
4 * 获取目标对象bean的类型
5 */
6 @Nullable
7 default Class<?> predictBeanType(Class<?> beanClass, String beanName) throws BeansException {
8 return null;
9 }
10
11 /**
12 * 获取用于对象实例化的构造器对象(在创建bean的时候调用)
13 */
14 @Nullable
15 default Constructor<?>[] determineCandidateConstructors(Class<?> beanClass, String beanName)
16 throws BeansException {
17
18 return null;
19 }
20
21 /**
22 * 获取提前曝光的单例bean对象
23 */
24 default Object getEarlyBeanReference(Object bean, String beanName) throws BeansException {
25 return bean;
26 }
27 }
4.4、DestructionAwareBeanPostProcessor
DestructionAwareBeanPostProcessor是用于处理bean销毁的时候进行后置处理,方法定义如下:
1 public interface DestructionAwareBeanPostProcessor extends BeanPostProcessor { 2
3 /**
4 * 当bean销毁的时候后置处理
5 */
6 void postProcessBeforeDestruction(Object bean, String beanName) throws BeansException;
7
8 /**
9 * 判断bean销毁的时候实现需要处理
10 */
11 default boolean requiresDestruction(Object bean) {
12 return true;
13 }
14 }
5、Spring的核心后置处理器**(*)**
5.1、AutowiredAnnotationBeanPostProcessor(@Autowired注解处理器)
AutowiredAnnotationBeanPostProcessor既实现了SmartInstantiationAwareBeanPostProcessor接口又实现了MergedBeanDefinitionPostProcessor接口,按执行顺序来看,bean加载的过程中方法的执行顺序如下:
1、执行SmartInstantiationAwareBeanPostProcessor接口的determineCandidateConstructors方法(找到bean的构造器方法)
2、执行MergedBeanDefinitionPostProcessor接口的postProcessMergedBeanDefinition方法(注入元属性)
3、执行InstantiationAwareBeanPostProcessor接口的postProcessProperties方法(属性设置)
5.1.1、determineCandidateConstructors方法的作用了找到该bean所有的构造器对象
5.1.2、postProcessMergedBeanDefinition方法实现逻辑如下:
1、遍历该bean所有的属性,找到被@Autowired、@Value、@Inject等注解修饰的属性,封装成AutowiredFieldElement对象,加入到列表中
2、遍历该bean所有的方法,找到被@Autowired、@Value、@Inject等注解修饰的方法,封装成AutowiredMethodElement对象,加入到列表中
3、将1、2步找到的两个列表,加入到一个InjectedElement列表中
4、根据InjectedElement列表和Class对象,封装成InjectedMetadata对象
5.1.3、postProcessProperties方法实现逻辑如下:
1、获取或构造5.1.2中的InjectedMetadata对象
2、执行InjectedMetadata对象的inject方法注入元属性
3、遍历InjectedMetadata对象的InjectedElement列表,依次执行InjectedElement对象的inject方法
4、InjectedElement的inject的逻辑如下,从容器中找到需要注入的bean,然后通过反射来进行注入:
4.1、如果当前Element是属性,那么就通过反射先调用Field的setAccessible(true)设置Field可以操作,然后通过反射调用Field的set(Obejct target, Object value)方法设置属性的值
4.2、如果当前Element是方法,那么就通过反射调用Method的setAccessible(true)设置Method可以操作,然后通过反射调用Method的invoke(Obejct obj, Object...args)方法执行方法
5.2、CommonAnnotationBeanPostProcessor(@Resource注解处理器)
CommonAnnotationBeanPostProcessor的作用是处理@Resource用的,当某个bean中定义了@Resource来修饰属性或者方法,那么该后置处理器就会将该bean依赖的bean注入进去,具体的实现逻辑和5.1的处理@Autowired注解的逻辑基本上一致。
只不过5.1是遍历bean的属性或方法中的@Autowired注解,而CommonAnnotationBeanPostProcessor是遍历属性或方法修饰的@Resource注解,注入的逻辑是一样的,都是通过InjectedMetadata类来实现的。
5.3、ApplicationContextAwareProcessor(Aware子接口方法执行)
Spring框架提供了众多的Aware接口,如ApplicationContextAware、MessageSoureceAware接口等,bean如果实现了对应的接口,就需要实现对应的set方法,而这些set方法的执行就是通过ApplicationContextAwareProcessor来执行的,
ApplicationContextAwareProcessor实现了BeanPostProcessor的postProcessBeforeInitialization方法,所以会在bean初始化之前执行,会依次执行Context包中提供的Aware子接口对应的set方法
6、Extra(*)
加载bean时各种BeanPostProcessor执行的时序图如下图示
本文内容总结:前言,1、BeanPostProcessor接口,2、后置处理器的使用,3、后置处理器的实现原理,3.1、初始化后置处理器,3.2、 添加后置处理器,4、BeanPostProcessor的子接口,4.1、InstantiationAwareBeanPostProcessor,4.2、MergedBeanDefinitionPostProcessor,4.3、SmartInstantiationAwareBeanPostProcessor,4.4、DestructionAwareBeanPostProcessor,5、Spring的核心后置处理器(),5.1、AutowiredAnnotationBeanPostProcessor(@Autowired注解处理器),5.2、CommonAnnotationBeanPostProcessor(@Resource注解处理器),5.3、ApplicationContextAwareProcessor(Aware子接口方法执行),6、Extra(),
原文链接:https://www.cnblogs.com/jackion5/p/13325136.html
以上是 Spring扩展接口解析4--bean后置处理器BeanPostProcessor接口 的全部内容, 来源链接: utcz.com/z/362514.html