上个章节讲解了spring启动时解析spring.xml的流程,本章主要解析对注解的解析;目前我们常用的是AnnotationConfigApplicationContext,其中MyApp就是启动类
ApplicationContext ctx = new AnnotationConfigApplicationContext(MyApp.class);
this()方法中可以看到reader为AnnotatedBeanDefinitionReader
点开AnnotatedBeanDefinitionReader中可以看到向beanFactory中注入了一些beanDefinition,如ConfigurationClassPostProcessor,AutowiredAnnotationBeanPostProcessor,CommonAnnotationBeanPostProcessor,这些processor在后面都会有很大的作用。
然后再看下AnnotatedBeanDefinitionReader的属性BeanDefinitionRegistry,以及他的核心方法doRegisterBean方法,主要是根据传进来的beanClass解析为BeanDefinition,然后将beanDefinition注册到beanDefinitonRegistry中
然后再看ApplicationContext中的另外一个属性scanner为ClassPathBeanDefinitionScanner,这个对象主要是用来对包进行扫描,通过传进来的basePackages,也就是包的路径,能够将这个包下面的类解析为beanDefinition注入到beanDefinitionRegistry中,但是扫描的时候肯定是有一定的规则,而不是将所有的都扫描进来,点进去registerDefaultFilters,可以看到熟悉的componet注解,那么ClassPathBeanDefinitionScanner就是通过includeFilters中的filter进行类的过滤的,如果java类上面有componet就会扫描进来,当然includeFilters中可以自定义一些自己的注解。
看完了AnnotationConfigApplicationContext中这两个重要的属性,就会对它有了一定的了解,继续向下看,context通过自身的reader方法将MyApp.class注入到了beanDefinitionRegistry中,这个方法我们前面已经说明。可想而知接下来,就会对MyApp上的注解进行解析。在MyApp上故意加了很多注解,方便后续对每个注解的解析进行详解
最终会进入到spring的主流程refresh()方法,那么这一步invokeBeanFactoryPostProcessor就是执行所有的beanDefinitionRegistryPostprocessor,那么ConfigurationClassPostProcessor也是在这一步发挥了巨大作用。
在进入到这个方法之前,我们先梳理清楚BeanDefinitionRegistryPostProcessor(也就是BeanFactoryPostProcessor的子类)与beanPostProcessor的区别,其实看名字就知道前者是对BeanDefinition的处理,即将java类转换为BeanDefinition的时候起作用,而beanPostProcessor是在从BeanDefinition到bean,即实例化到初始化过程中起作用,不要搞混了。先看下本次要讲解的beanDefinitionRegistryPostProcessor接口定义,核心方法就是postProcessBeanDefinitionRegistry
写个demo,这个接口的关键是能够拿到BeanDefinitonRegistry,这个想必大家都不陌生,所有要加入到spring的对象,都会先解析为BeanDefinition注册到这个容器中,那么拿到这个对象就能获取到所有的BeanDefiniton,我们能在这个方法里面对BeanDefinition中做增删改查,甚至增强BeanDefinition;
那么下面还有个方法postProcessBeanFactory,在这个方法里面能够获取到beanFactory,那么也就是说我们能获取到容器所有的bean,不过这个方法用的比较少,但是后面对带有@Configuration的类中的@Bean方法中有特殊的作用,后面详细会讲解。
看到上面想必大家已经对BeanDefinitionRegistryPostProcessor已经有了大致的了解。
于是就进入到invokeBeanFactoryPostProcessors(beanFactory),这里是根据循环遍历beanDefiniton中去获取这个类型的类,然后再去执行postProcessBeanDefinitionRegistry方法。由于前面在初始化AnnotatedBeanDefinitionReader的时候将ConfigurationClassPostProcessor,AutowiredAnnotationBeanPostProcessor,CommonAnnotationBeanPostProcessor的beanDefinition注册到了容器中,而ConfigurationClassPostProcessor集成了BeanFactoryPostprocessor,另外两个继承了BeanPostProcessor,所以这里就查到了ConfigurationClassPostProcessor。
于是就来到了ConfigurationClassPostProcessor的核心处理逻辑,这个方法发挥了巨大的作用,支持了 @Configuration@ComponentScan@Import@ImportResource@PropertySource@Order 等注解,同时也对大家理解springboot的帮助很大,真正的可以做到0 xml 配置。
下一个章节将详细解说ConfigurationClassPostProcessor对类的处理流程。
标签:spring,ConfigurationClassPostProcessor,configurationClassPostProcessor,注解,解析,方法, From: https://blog.csdn.net/qq_40228720/article/details/143029225