重温 - spring 源码 - ConfigurationClassPostProcessor(@Configuration和@Component的区别)

8 篇文章 0 订阅

      概要:ConfigurationClassPostProcessor 是 spring 中极为重要的一个类尤其是在 springboot 广泛应用的背景下,ConfigurationClassPostProcessor 类 在spring 容器启动流程之初 收集 @Configuration 注解的类以及 @Component @ComponentScan @Import @ImportResource 和 @Bean 将其封装成BeanDefinition 注册到spring registry中,以备后期的实例化。

     1. AnnotationConfigApplicationContext 构造函数中 三步走

       (1) this() 用于注册 两个类 AnnotatedBeanDefinitionReader ClassPathBeanDefinitionScanner

       (2)setConfig(location / configclass) 用于配置项目的基础扫描路径

       (3)refresh() 调用AbstractApplicationContext 的 refresh() 方法 改方法 就是spring和核心路程方法(spring的流程模板)

      AnnotatedBeanDefinitionReader 注册几个BeanRegistryPostProcessor ConfigurationClassPostProcessor / AutowiredAnnotationBeanPostProcessor / CommonAnnotationBeanPostProcessor

     以及事件等的一些类。

       invokeBeanFactoryPostProcessor(beanFactory)  ->  实例化 ConfigurationClassPostProcessor -> invokeBeanDefinitionRegistrPostProcessors()

       -> ConfigurationClassPostProcessor . postProcessBeanDefinitionRegistry . processConfigBeanDefinitions

        在processConfigBeanDefinitions()中 首先收集 上面描述的注解的类 装入集合遍历解析 引出 ConfigurationClassParser 类进行解析

      ConfigurationClassParser 解析 parse() 使用方法的递归进行循环的遍历

       @ComponentScan 注解定义的包类会被扫描后封装成BeanDefinition 注册到 BeanDifinitionRegistry 中待实例化。

       @PropertyResource 中的配置项 会被包装成 PropertyResource 添加到 Environment 的 MutablePropertySources 类型的变量中

       @Import 导入的类 ImportSelector(DeferredImportSelector) / ImportBeanDefinitionRegistrar 会被收集到 不同的容器中后面 beanDefinition的注册

       ImportSelector 接口 selectImports() 方法返回的是 String 类型的数组 String字符串必须是 类的全限定名 

      ImportBeanDefinitionRegistrar 提供了默认的方法给子类实现  registryBeanDefinitions (meta , registry) 实现BeanDefinition 增删改操作

@Bean 注解方法收集到 宿主类的 method的集合 

@ImportResource 等以及 当前配置类的 父类的扫描

收集完成后 ConfigurationClassBeanDefinitionRender 进行 beanDefinition 的封装和注册

(1)配置类本身注册

(2) @Bean 方法的注册

实现 通过factoryMethod 实现的,每一个@Bean 注册成一个 ConfigurationClassBeanDefinition类型的 BeanDefinition 通过设置改 BeanDefinition的 factoryMethod 和 factoryBeanName / BeanClassName 等属性来为后期 @Bean的实例化作准备。

重点2 》》》 ConfigurationClassPostProcessor  implements  BeanFactoryPostProcessor

   特征方法 postProcessBeanFactory(beanFactory.)  对 @Configuration 类型 (full 类型)  的 BeanDefinition  进行 增强处理

enhanceConfigurationClasses(beanFactory)

遍历所有spring管理的的BeanDefinition  收集 full ,使用CGLIB生成代理类型的 子类  并设置 为 @Configuraion的 BeanDefinition的 BeanClass

涉及的核心类:

(1) ConfigurationClassPostProcessor 作为注解形式beanDefinition 注册到Spring的入口

          a> BeanDefinitionRegistryPostProcessor . postProcessBeanDefinitionRegistry(registry) 收集并注册BeanDefinition到spring

           b> BeanFactoryPostProcessor  postProcessBeanFactory(beanFactory)  对 @Confiuguration 即 full 类型 并且 有@Bean 类型的方法 进行生成增强的 BeanClass 字节码的子类型并设置为 @Configuration BeanDefinition的BeanClass 

(2)ConfigurationClassParser 进行解析收集

         ConfigurationClassBeanDefinitionRender loadBeanDefinition()进行BeanDefinition的注册

         ConfigurationClassBeanDefinition @Bean 方法注册的bean的BeanDefinition的类型

         ConfigurationClassEnhancer @Configuration的增强类型  使用CGLIB 生成的字节码类的子类

(3)实例化 CallBackFilter 拦截类 分 3 个

        a> BeanMethodInterceptor             

              切面通知:

                  (1) 拦截 FactoryBean 拦截 getObject() 方法,通过 beanFactory.getBean() 尝试从缓存中获取类的实例对象,防止了 @Configuration 配置类中 @Bean 类型的方法相互调用产生多个不同的实例

                  (2) @Bean  factoryMethod 直接反射调用即可

        b> BeanFactoryAwareMethodInterceptor 

        c> NoOp.INSTANCE

NoOp.INSTANCE

         

源码位置:

 

      

 

    

       

       

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值