一、版本
<dependency><groupId>org.springframework</groupId><artifactId>spring-context</artifactId><version>4.3.12.RELEASE</version></dependency>
二、接口详解
2.1 什么是BeanPostProcessor?
BeanPostProcessor
也称为Bean后置处理器,在Spring容器的创建过程中(具体为Bean初始化前后)会回调BeanPostProcessor中定义的两个方法。
publicinterfaceBeanPostProcessor{// 在bean初始化回调(例如InitializingBean的afterPropertiesSet或自定义init-method)之前调用
ObjectpostProcessBeforeInitialization(Object bean, String beanName)throws BeansException;// 在bean初始化回调(例如InitializingBeanafterPropertiesSet或自定义init-method)之后调用
ObjectpostProcessAfterInitialization(Object bean, String beanName)throws BeansException;}
其中,可以向IOC容器添加多个BeanPostProcessor(后置处理器),默认情况下容器加载次序决定了BeanPostProcessor调用顺序,也可以实现Ordered{@code getOrder}改变调用次序,其中getOrder返回值越大优先级越高。
publicinterfaceOrdered{int HIGHEST_PRECEDENCE= Integer.MIN_VALUE;int LOWEST_PRECEDENCE= Integer.MAX_VALUE;intgetOrder();}
2.2 BeanPostProcessor有什么作用?
提出一个问题:假设需要在Spring初始化Bean之后做一些定制化逻辑,简单如记录下Bean的初始化记录,或针校验Bean逻辑,又或者是针对某类策略需要执行一些具体的业务逻辑,那么怎么做比较好呢?
其实,Spring在初始化Bean之后已经加入了一些钩子
方法,方便开发一些特定的后置业务处理逻辑
,这也提现了AOP
思想,其中钩子包括:
- BeanPostProcessor
- InitializingBean和DisposableBean
- @PostConstruct、@PreDestroy
- @Bean(initMethod、destroyMethod)
总结作用为:在Bean对象在实例化和依赖注入完毕后,在显示调用初始化方法的前后添加特定的业务逻辑。
2.3 为什么要注册BeanPostProcessor?
所谓的注册,只不过是对当前上下文中所有的BeanPostProcessor
进行一种集中式管理罢了, 为什么非得这么做呢?
因为上下文中BeanPostProcessor的数量不是一成不变的,Spring为了启动的正常,需要添加原生的BeanPostProcessor,程序员因为自己的需求也会添加不同数量的Bean后置处理器,因此需要这种策略,将上下文中所有的后置处理器进行统一的管理,方便回调。
三、IOC容器注册BeanPostProcessor的源码解析
3.1 IOC容器注册BeanPostProcessor的时序图
3.2 刷新IOC容器
目标类:AbstractApplicationContext
publicvoidrefresh()throws BeansException, IllegalStateException{synchronized(this.startupShutdownMonitor){...// 调用容器中注册的Bean工厂处理器invokeBeanFactoryPostProcessors(beanFactory);// 注册拦截Bean创建的处理器registerBeanPostProcessors(beanFactory);...// 实例化所有剩余的(非@Lazy)单例。finishBeanFactoryInitialization(beanFactory);...}}
3.3 调用注册LoadTimeWeaverAwareProcessor
目标类:AbstractApplicationContext
目的:注册LoadTimeWeaverAwareProcessor到Spring IOC容器
// 调用容器中注册的Bean工厂处理器protectedvoidinvokeBeanFactoryPostProcessors(ConfigurableListableBeanFactory beanFactory){
PostProcessorRegistrationDelegate.invokeBeanFactoryPostProcessors(beanFactory,getBeanFactoryPostProcessors());// String LOAD_TIME_WEAVER_BEAN_NAME="loadTimeWeaver"// 注册容器是否包含loadTimeWeaver Bean,如果没有则注册// (如: 通过ConfigurationClassPostProcessor注册的@Bean方法)if(beanFactory.getTempClassLoader()== null&& beanFactory.containsBean(LOAD_TIME_WEAVER_BEAN_NAME)){// LoadTimeWeaverAwareProcessor实现了BeanPostProcessor接口子类
beanFactory.addBeanPostProcessor(newLoadTimeWeaverAwareProcessor(beanFactory));
beanFactory.setTempClassLoader(newContextTypeMatchClassLoader(beanFactory.getBeanClassLoader()));}}
3.4 获取和注册BeanPostProcessor
目标类:PostProcessorRegistrationDelegate
publicstaticvoidregisterBeanPostProcessors(
ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext){// 根据类型获取BeanPostProcessor的Bean(包含多实例、单实例、以及其他Scope范围的Bean)
String[] postProcessorNames= beanFactory.getBeanNamesForType(BeanPostProcessor.class,true,false);// 计算BeanPostProcessor数量, 然后创建BeanPostProcessorChecker添加到容器int beanProcessorTargetCount= beanFactory.getBeanPostProcessorCount()+1+ postProcessorNames.length;
beanFactory.addBeanPostProcessor(newBeanPostProcessorChecker(beanFactory, beanProcessorTargetCount));// 1. priorityOrderedPostProcessors: 实现了PriorityOrdered接口的BeanPostProcessor// 2. internalPostProcessors: 同时实现了PriorityOrdered和MergedBeanDefinitionPostProcessor// 接口的BeanPostProcessor, 也就是Spring内部的BeanPostProcessor// 3. orderedPostProcessorNames: 实现了Ordered接口的BeanPostProcessor// 4. nonOrderedPostProcessorNames: 单纯的BeanPostProcessor// 注意: PriorityOrdered是继承Ordered的接口, 因此处理需要首先判断PriorityOrdered
List<BeanPostProcessor> priorityOrderedPostProcessors=newArrayList<BeanPostProcessor>();
List<BeanPostProcessor> internalPostProcessors=newArrayList<BeanPostProcessor>();
List<String> orderedPostProcessorNames=newArrayList<String>();
List<String> nonOrderedPostProcessorNames=newArrayList<String>();for(String ppName: postProcessorNames){// 首先处理PriorityOrdered, 因为PriorityOrdered是继承自Ordered的接口if(beanFactory.isTypeMatch(ppName, PriorityOrdered.class)){
BeanPostProcessor pp= beanFactory.getBean(ppName, BeanPostProcessor.class);
priorityOrderedPostProcessors.add(pp);if(ppinstanceofMergedBeanDefinitionPostProcessor){
internalPostProcessors.add(pp);}}elseif(beanFactory.isTypeMatch(ppName, Ordered.class)){
orderedPostProcessorNames.add(ppName);}else{
nonOrderedPostProcessorNames.add(ppName);}}// 根据优先级排序priorityOrderedPostProcessorssortPostProcessors(priorityOrderedPostProcessors, beanFactory);// 将priorityOrderedPostProcessors依次注册到beanFactoryregisterBeanPostProcessors(beanFactory, priorityOrderedPostProcessors);// 处理实现Ordered接口的BeanPostProcessor
List<BeanPostProcessor> orderedPostProcessors=newArrayList<BeanPostProcessor>();for(String ppName: orderedPostProcessorNames){
BeanPostProcessor pp= beanFactory.getBean(ppName, BeanPostProcessor.class);
orderedPostProcessors.add(pp);// 如果是Spring内部的BeanPostProcessor,则注册到internalPostProcessorsif(ppinstanceofMergedBeanDefinitionPostProcessor){
internalPostProcessors.add(pp);}}// 根据优先级排序orderedPostProcessorssortPostProcessors(orderedPostProcessors, beanFactory);// 将orderedPostProcessors依次注册到beanFactoryregisterBeanPostProcessors(beanFactory, orderedPostProcessors);// 处理单纯的BeanPostProcessor
List<BeanPostProcessor> nonOrderedPostProcessors=newArrayList<BeanPostProcessor>();for(String ppName: nonOrderedPostProcessorNames){
BeanPostProcessor pp= beanFactory.getBean(ppName, BeanPostProcessor.class);
nonOrderedPostProcessors.add(pp);// 如果是Spring内部的BeanPostProcessor,则注册到internalPostProcessorsif(ppinstanceofMergedBeanDefinitionPostProcessor){
internalPostProcessors.add(pp);}}// 无须排序,直接依次注册到beanFactory的末尾registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors);// 根据优先级排序internalPostProcessorssortPostProcessors(internalPostProcessors, beanFactory);// 将internalPostProcessors依次注册到beanFactory容器registerBeanPostProcessors(beanFactory, internalPostProcessors);// 总结注册顺序(从尾到头, 因为是逆序调用):// internalPostProcessors > nonOrderedPostProcessors > orderedPostProcessors > priorityOrderedPostProcessors// 重新注册用于检测内部Bean的BeanPostProcessor作为ApplicationListener, 将其移至处理器链的末尾(用于获取代理等)。// 注意:applicationContext为AbstractApplicationContext的实现IOC容器
beanFactory.addBeanPostProcessor(newApplicationListenerDetector(applicationContext));}
3.5 注册BeanPostProcessor
目标类:PostProcessorRegistrationDelegate
作用:只是把BeanPostProcessor顺序注册到beanFactory容器
privatestaticvoidregisterBeanPostProcessors(
ConfigurableListableBeanFactory beanFactory, List<BeanPostProcessor> postProcessors){for(BeanPostProcessor postProcessor: postProcessors){
beanFactory.addBeanPostProcessor(postProcessor);}}
3.6 注册BeanPostProcessor到beanFactory
目标类:AbstractBeanFactory
@OverridepublicvoidaddBeanPostProcessor(BeanPostProcessor beanPostProcessor){
Assert.notNull(beanPostProcessor,"BeanPostProcessor must not be null");// 移除已注册的BeanPostProcessor, 原因是按照新规则排序添加this.beanPostProcessors.remove(beanPostProcessor);this.beanPostProcessors.add(beanPostProcessor);// 判断是否有InstantiationAwareBeanPostProcessor的BeanPostProcessorif(beanPostProcessorinstanceofInstantiationAwareBeanPostProcessor){this.hasInstantiationAwareBeanPostProcessors=true;}// 判断是否存在DestructionAwareBeanPostProcessor的BeanPostProcessorif(beanPostProcessorinstanceofDestructionAwareBeanPostProcessor){this.hasDestructionAwareBeanPostProcessors=true;}}
四、IOC容器调用BeanPostProcessor源码解析
4.1 IOC容器调用BeanPostProcessor的时序图
4.2 刷新IOC容器
目标类:AbstractApplicationContext
publicvoidrefresh()throws BeansException, IllegalStateException{synchronized(this.startupShutdownMonitor){...// 调用容器中注册的Bean工厂处理器invokeBeanFactoryPostProcessors(beanFactory);// 注册拦截Bean创建的处理器registerBeanPostProcessors(beanFactory);...// 实例化所有剩余的(非@Lazy)单例。finishBeanFactoryInitialization(beanFactory);...}}
4.3 完成BeanFactory的实例化
目标类:AbstractApplicationContext
protectedvoidfinishBeanFactoryInitialization(ConfigurableListableBeanFactory beanFactory){// String CONVERSION_SERVICE_BEAN_NAME="conversionService"// 判断beanFactory是否存在类型转换服务conversionService, 如果存在则注册到beanFactory// 补充:ConversionService是用于类型转换的服务, 调用convert方法实现类型转换if(beanFactory.containsBean(CONVERSION_SERVICE_BEAN_NAME)&&
beanFactory.isTypeMatch(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class)){
beanFactory.setConversionService(
beanFactory.getBean(CONVERSION_SERVICE_BEAN_NAME, ConversionService.class));}// 注册Spring SPEL解析器EmbeddedValueResolver// 补充:StringValueResolver为SPEL解析器, 如#{1-1}、${app.port}if(!beanFactory.hasEmbeddedValueResolver()){
beanFactory.addEmbeddedValueResolver(newStringValueResolver(){@Overridepublic StringresolveStringValue(String strVal){returngetEnvironment().resolvePlaceholders(strVal);}});}// 目的:根据类型获取LoadTimeWeaverAware的Bean, 并且检测LoadTimeWeaverAware是否存在
String[] weaverAwareNames= beanFactory.getBeanNamesForType(LoadTimeWeaverAware.class,false,false);for(String weaverAwareName: weaverAwareNames){getBean(weaverAwareName);}// 停止使用临时ClassLoader进行类型匹配。
beanFactory.setTempClassLoader(null);// 缓存Bean定义的元数据
beanFactory.freezeConfiguration();// 初始化非Lazy的单实例
beanFactory.preInstantiateSingletons();}
4.4 DefaultListableBeanFactory初始化单实例
目标类:DefaultListableBeanFactory
@OverridepublicvoidpreInstantiateSingletons()throws BeansException{if(this.logger.isDebugEnabled()){this.logger.debug("Pre-instantiating singletons in "+this);}// beanDefinitionNames是配置文件配置的所有Bean名字
List<String> beanNames=newArrayList<String>(this.beanDefinitionNames);// 触发非Lazy的单实例初始化for(String beanName: beanNames){// 返回Bean的定义
RootBeanDefinition bd=getMergedLocalBeanDefinition(beanName);// 非抽象类和非Lazy的单实例if(!bd.isAbstract()&& bd.isSingleton()&&!bd.isLazyInit()){// 如果是实现FactoryBean接口定义的Beanif(isFactoryBean(beanName)){// 获取FactoryBean的Bean, 获取方式为:&+Bean名字final FactoryBean<?> factory=(FactoryBean<?>)getBean(FACTORY_BEAN_PREFIX+ beanName);boolean isEagerInit;if(System.getSecurityManager()!= null&& factoryinstanceofSmartFactoryBean){
isEagerInit= AccessController.doPrivileged(newPrivilegedAction<Boolean>(){@Overridepublic Booleanrun(){return((SmartFactoryBean<?>) factory).isEagerInit();}},getAccessControlContext());}else{// 判断是否需要立即初始化
isEagerInit= factoryinstanceofSmartFactoryBean&&((SmartFactoryBean<?>) factory).isEagerInit();}// 非Lazy单实例if(isEagerInit){getBean(beanName);}}else{getBean(beanName);}}}// 如果Bean实现了SmartInitializingSingleton, 则触发Bean的afterSingletonsInstantiated方法for(String beanName: beanNames){// 获取单实例,如果不是单实例则返回Null
Object singletonInstance=getSingleton(beanName);if(singletonInstanceinstanceofSmartInitializingSingleton){final SmartInitializingSingleton smartSingleton=(SmartInitializingSingleton) singletonInstance;if(System.getSecurityManager()!= null){
AccessController.doPrivileged(newPrivilegedAction<Object>(){@Overridepublic Objectrun(){
smartSingleton.afterSingletonsInstantiated();return null;}},getAccessControlContext());}else{// 调用单实例的SmartInitializingSingleton处理器
smartSingleton.afterSingletonsInstantiated();}}}}
4.5 AbstractBeanFactory获取单实例Bean
目标类:AbstractBeanFactory
@Overridepublic ObjectgetBean(String name)throws BeansException{returndoGetBean(name, null, null,false);}// 思路// 1. 如果已缓存类型单实例, 则直接从缓存获取// 2. 如果有集合其他ApplicationContext容器, 试图从继承容器获取, 获取到直接返回// 3. 对Bean进行检查// 4. 依赖项检查, 以及实例化依赖项// 5. 单实例创建// 6. 多实例创建// 7. 其他Scope实例创建// 8. Bean类型检查// 9. 返回创建的实例对象protected<T> TdoGetBean(final String name,final Class<T> requiredType,final Object[] args,boolean typeCheckOnly)throws BeansException{// 返回Bean名称(去除工厂取消引用前缀:&, 并将别名解析为规范名称)final String beanName=transformedBeanName(name);
Object bean;// singletonObjects : 单例对象缓存的ConcurrentHashMap// earlySingletonObjects: 早期单例对象缓存的HashMap// 调用结果:// 1. 检查Bean是否已经创建放入到容器中(即singletonObjects), 有则返回// 2. 如果容器中不存在, 则创建单实例Bean加入到earlySingletonObjects// 目的在于解决单实例的循环依赖问题// 补充:后续的AbstractAutowireCapableBeanFactory{@Code doCreateBean}有// 调用removeSingletonIfCreatedForTypeCheckOnly移除
Object sharedInstance=getSingleton(beanName);if(sharedInstance!= null&& args== null){if(logger.isDebugEnabled()){if(isSingletonCurrentlyInCreation(beanName)){
logger.debug("Returning eagerly cached instance of singleton bean '"+ beanName+"' that is not fully initialized yet - a consequence of a circular reference");}else{
logger.debug("Returning cached instance of singleton bean '"+ beanName+"'");}}// 从BeanInstance获取Bean的实例
bean=getObjectForBeanInstance(sharedInstance, name, beanName, null