配置类:
@Component @ComponentScan @Configuration @Import(本身的类是配置类,引入的类也会当成配置类,不管被引入的类有没有注解) @ImportResource @Bean加载方法上的类
怎么查找配置类:
找出所有的beandefinition,根据注解等规则找出所有的配置类,---->生成ConfigurationClass,配置信息都设置到此类的属性中---->找出所有的beandefinition注册到beanfactory中
如何解析:
ConfigurationClassParse.
1. @Component注解底层工作原理
有没有内部类,有的话就递归处理内部类配置类
2. @ComponentScan注解底层工作原理
1)解析属性
2)componentScanParser,处理注解的时候扫描。
扫描后得到beandefinition,如果也有配置类,会再调用处理配置类的方法。
@ComponentScan可以使用includeFilter增加没有注解的,而且想加载的类,也可以使用excluedeFilter排除不想加载的类
@ComponentScan lazyinit 使加载的所有的类都是懒加载
扫描定时的路径:
多个路径使用循环处理
获取每个路径下所有的资源,把class文件拿到,每个class文件生成一个MetadataReader
手动注册的比扫描的优先:扫描时如果已经存在了beandefinition了,而且不是扫描得到的就不覆盖了。
3. @Bean注解底层工作原理
@Bean(name={"name1","name2","name3"})
public User user(){
return new User();
}
这个时候,user不是名字了,主名字是"name1",别名是name2和name3
4. @Configuration注解底层工作原理
proxyBeanMethods默认是true,
5. @Import注解底层工作原理
多个配置文件有同一个配置项是覆盖存储的么?还是分别存储,然后根据优先级获取?
解析过程:
找出PropertySource
找出路径--->解析占位符--->把文件解析成PropertySource
spring提供了字节码工具类 asm.ClassLoader
@Component 和 @Bean 哪个优先:
Component优先。@Bean
问题: 默认会把扫描@Component注解得到的覆盖掉吗? 应该不会
使用@Bean 定义了多个,会以第一个扫描到的注解为主
@Bean 注解会解析成一个Factorybean,类是当前类,factory的方法是加了@Bean的方法
在下面的过程中,只有在扫描的时候产生了beandefinition,@Import不会产生beandefinition
1)Component注解
可能生成配置类,生成的配置类放到configurationClass(是个map)中
2)PropertySource注解
不会生成配置类
3)ComponentScan
可能生成配置类,生成的配置类放到configurationClass(是个map)中
4)Import
可能生成配置类,找到的类也会被当成配置类放到configurationClass(是个map)中
导入的类有三种类型:
(1)实现ImportSelector接口导入的类
生成ImportSelector的实例,执行selectImports找出所有类的名字,把类名当成Import再递归调用selectImports
(2)ImportBeanDefinitionRegistar
生成ImportBeanDefinitionRegistar累的对象,加到ConfigurationClass中,后面再执行对象的方法
会把导入的类当成配置类
(3)普通类型
importBy
递归调用processConfigrationOnClass
5)@ImportResource
解析占位符
解析出资源的路径,生成ConfigurationClass,把路径放到ConfigurationClass属性中
6)@Bean
解析出生成 ConfigurationClass,把bean注册的方法设置到ConfigurationClass的beanMethod属性上
7)接口 jdk 8
看类有没有实现接口,看接口有没有默认方法,方法上是不是有注解
8)有没有父类,
解析ConfigurationClass生成Beandefinition并注册到单例池中
(1)解析Import
生成bd,然后注册
(2)解析 @bean
(3)解析加载的配置文件
(4)解析ImportBeanDefinitionRegistar