前言
在上一篇文章:【小家Spring】Spring IOC容器启动流程 AbstractApplicationContext#refresh()方法源码分析(一)中已经介绍了前五步,现在Spring IOC容器的工厂环境已经都准备好了。
Bean工厂可以简单理解为一个钩子容器,里面注册有众多的BeanFactoryPostProcessor以及BeanFactoryPostProcessor,接下来我们就前去学习钩子的细节~
Spring源码基于的Spring版本为:5.0.6.RELEASE(下同)
Spring源码基于的Spring版本为:5.0.6.RELEASE(下同)
Spring源码基于的Spring版本为:5.0.6.RELEASE(下同)
refresh() 第六步:registerBeanPostProcessors(beanFactory)
在讲解这个方法之前先看下什么是BeanPostProcessor,下面是BeanPostProcessor的代码:
public interface BeanPostProcessor { // 在Bean实例化/依赖注入完毕以及自定义的初始化方法之前调用。什么叫自定义初始化方法:比如init-method、比如@PostConstruct标、比如实现InitailztingBean接口的方法等等 // bean:这个Bean实例 beanName:bean名称 @Nullable default Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { return bean; } // 在上面基础上,初始化方法之后调用 @Nullable default Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException { return bean; } }
口中两个方法不能返回null,如果返回null那么在后续初始化方法将报空指针异常或者通过getBean()方法获取不到bena实例对象 ,因为后置处理器从Spring IoC容器中取出bean实例对象没有再次放回IoC容器中
BeanFactory和ApplicationContext注册Bean的后置处理器不通点:
ApplicationContext直接使用@Bean注解,就能向容器注册一个后置处理器。
原因:它注册Bean的时候,会先检测是否实现了BeanPostProcessor接口,并自动把它们注册为后置处理器。所在在它这部署一个后置处理器和注册一个普通的Bean,是没有区别的
BeanFactory必须显示的调用:void addBeanPostProcessor(BeanPostProcessor beanPostProcessor才能注册进去。
Spring 可以注册多个Bean的后置处理器,是按照注册的顺序进行调用的。若想定制顺序,可以实现@Order或者实现Order接口~
源码解读
先说说:((DefaultListableBeanFactory) beanFactory).getBeanPostProcessors();这个方法:
public List<BeanPostProcessor> getBeanPostProcessors() { return this.beanPostProcessors; }
它返回的是所有的通过BeanFactory#addBeanPostProcessor
方法添加进去的后置处理器们,会存在这个List里面。
还有就是这个内部类:(一共4个,是容器启动时,用BeanFactory添加进去的Bean后置处理器)
而这个方法getBeanNamesForType是从Bean定义信息里面去找:主要是如下几个属性缓存上的:
(所以请注意和getBeanPostProcessors的结果区分开来,虽然都是BeanPostProcessor)
/** Map of bean definition objects, keyed by bean name */ private final Map<String, BeanDefinition> beanDefinitionMap = new ConcurrentHashMap<>(256); /** Map of singleton and non-singleton bean names, keyed by dependency type */ private final Map<Class<?>, String[]> allBeanNamesByType = new ConcurrentHashMap<>(64); /** Map of singleton-only bean names, keyed by dependency type */ private final Map<Class<?>, String[]> singletonBeanNamesByType = new ConcurrentHashMap<>(64); /** List of bean definition names, in registration order */ private volatile List<String> beanDefinitionNames = new ArrayList<>(256);
这些其实就是IOC容器的本质:一堆Map
具体源码:
// 发现它又是委托给PostProcessorRegistrationDelegate 去做的 protected void registerBeanPostProcessors(ConfigurableListableBeanFactory beanFactory) { PostProcessorRegistrationDelegate.registerBeanPostProcessors(beanFactory, this); } public static void registerBeanPostProcessors( ConfigurableListableBeanFactory beanFactory, AbstractApplicationContext applicationContext) { // 从所与Bean定义中提取出BeanPostProcessor类型的Bean,显然,最初的6个bean,有三个是BeanPostProcessor: // AutowiredAnnotationBeanPostProcessor RequiredAnnotationBeanPostProcessor CommonAnnotationBeanPostProcessor String[] postProcessorNames = beanFactory.getBeanNamesForType(BeanPostProcessor.class, true, false); // Register BeanPostProcessorChecker that logs an info message when // a bean is created during BeanPostProcessor instantiation, i.e. when // a bean is not eligible for getting processed by all BeanPostProcessors. // 此处有点意思了,向beanFactory又add了一个BeanPostProcessorChecker,并且此事后总数设置为了getBeanPostProcessorCount和addBeanPostProcessor的总和(+1表示自己) int beanProcessorTargetCount = beanFactory.getBeanPostProcessorCount() + 1 + postProcessorNames.length; // 此处注意:第一个参数beanPostProcessorTargetCount表示的是处理器的总数,总数(包含两个位置离的,用于后面的校验) beanFactory.addBeanPostProcessor(new BeanPostProcessorChecker(beanFactory, beanProcessorTargetCount)); // Separate between BeanPostProcessors that implement PriorityOrdered, // Ordered, and the rest. // 同样的 先按优先级,归类了BeanPostProcessor List<BeanPostProcessor> priorityOrderedPostProcessors = new ArrayList<>(); List<BeanPostProcessor> internalPostProcessors = new ArrayList<>(); 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); // MergedBeanDefinitionPostProcessor则是在合并处理Bean定义的时候的回调。这个东东按我的理解也基本是框架内部使用的,用户不用管 if (pp instanceof MergedBeanDefinitionPostProcessor) { internalPostProcessors.add(pp); } } else if (beanFactory.isTypeMatch(ppName, Ordered.class)) { orderedPostProcessorNames.add(ppName); } else { nonOrderedPostProcessorNames.add(ppName); } } // First, register the BeanPostProcessors that implement PriorityOrdered. sortPostProcessors(priorityOrderedPostProcessors, beanFactory); registerBeanPostProcessors(beanFactory, priorityOrderedPostProcessors); // Next, register the BeanPostProcessors that implement Ordered. List<BeanPostProcessor> orderedPostProcessors = new ArrayList<>(); 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); // Now, register all regular BeanPostProcessors. List<BeanPostProcessor> nonOrderedPostProcessors = new ArrayList<>(); for (String ppName : nonOrderedPostProcessorNames) { BeanPostProcessor pp = beanFactory.getBean(ppName, BeanPostProcessor.class); nonOrderedPostProcessors.add(pp); if (pp instanceof MergedBeanDefinitionPostProcessor) { internalPostProcessors.add(pp); } } registerBeanPostProcessors(beanFactory, nonOrderedPostProcessors); // Finally, re-register all internal BeanPostProcessors. sortPostProcessors(internalPostProcessors, beanFactory); registerBeanPostProcessors(beanFactory, internalPostProcessors); // Re-register post-processor for detecting inner beans as ApplicationListeners, // moving it to the end of the processor chain (for picking up proxies etc). // 最后此处需要注意的是:Spring还给我们注册了一个Bean的后置处理器:ApplicationListenerDetector 它的作用:用来检查所有得ApplicationListener // 有的人就想问了:之前不是注册过了吗,怎么这里又注册一次呢?其实上面的doc里面说得很清楚: // Re-register重新注册这个后置处理器。把它移动到处理器连条的最后面,最后执行(小技巧是:先remove,然后执行add操作~~~ 自己可以点进addBeanPostProcessor源码可以看到这个小技巧) beanFactory.addBeanPostProcessor(new ApplicationListenerDetector(applicationContext)); } // 把类型是BeanPostProcessor的Bean,注册到beanFactory里面去 private static void registerBeanPostProcessors( ConfigurableListableBeanFactory beanFactory, List<BeanPostProcessor> postProcessors) { for (BeanPostProcessor postProcessor : postProcessors) { beanFactory.addBeanPostProcessor(postProcessor); } }
这一步:我们从所有的@Bean定义中抽取出来了BeanPostProcessor
然后都注册进去,等待后面的的顺序调用
refresh() 第七步:initMessageSource()
初始化消息源。
protected void initMessageSource() { ConfigurableListableBeanFactory beanFactory = getBeanFactory(); // 判断是否已经存在名为“messageSource”的Bean了(一般情况下,我们都是没有的) if (beanFactory.containsLocalBean(MESSAGE_SOURCE_BEAN_NAME)) { // 从容器里拿出这个messageSource this.messageSource = beanFactory.getBean(MESSAGE_SOURCE_BEAN_NAME, MessageSource.class); // Make MessageSource aware of parent MessageSource. // 设置父属性。。。。。。。。。。。。。 if (this.parent != null && this.messageSource instanceof HierarchicalMessageSource) { HierarchicalMessageSource hms = (HierarchicalMessageSource) this.messageSource; if (hms.getParentMessageSource() == null) { // Only set parent context as parent MessageSource if no parent MessageSource // registered already. hms.setParentMessageSource(getInternalParentMessageSource()); } } } else { // Use empty MessageSource to be able to accept getMessage calls. DelegatingMessageSource dms = new DelegatingMessageSource(); // 其实就是获取到父容器的messageSource字段(否则就是getParent()上下文自己) dms.setParentMessageSource(getInternalParentMessageSource()); // 给当前的messageSource赋值 this.messageSource = dms; // 把messageSource作为一个单例的Bean注册进beanFactory工厂里面 beanFactory.registerSingleton(MESSAGE_SOURCE_BEAN_NAME, this.messageSource); } }
这部分逻辑比较简单:向容器里注册一个一个事件源的单例Bean:MessageSource
refresh() 第八步:initApplicationEventMulticaster()
初始化Spring的事件多播器:ApplicationEventMulticaster
protected void initApplicationEventMulticaster() { ConfigurableListableBeanFactory beanFactory = getBeanFactory(); if (beanFactory.containsLocalBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME)) { this.applicationEventMulticaster = beanFactory.getBean(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, ApplicationEventMulticaster.class); } else { this.applicationEventMulticaster = new SimpleApplicationEventMulticaster(beanFactory); beanFactory.registerSingleton(APPLICATION_EVENT_MULTICASTER_BEAN_NAME, this.applicationEventMulticaster); } }
这个逻辑太简单了,一句话:若用户自己定义了这个Bean(备注:Bean名称必须是"applicationEventMulticaster"哦),就以用户的为准。否则注册一个系统默认的SimpleApplicationEventMulticaster
refresh() 第九步:onRefresh()
类似于第四步的postProcessBeanFactory,它也是个模版方法。本环境中的实现为:AbstractRefreshableWebApplicationContext#onRefresh方法:
@Override protected void onRefresh() { this.themeSource = UiApplicationContextUtils.initThemeSource(this); }
web环境,所以去初始化了它的主题。
context = new ClassPathXmlApplicationContext(configPath.split("[,\\s]+")); context.start();