spring源码之Mybatis扫描器

2023年7月22日12:06:11

点进MapperScan这个注解,可以看到注入了这个类MapperScannerRegistrar
spring源码之Mybatis扫描器
点进这个类,可以看到继承了ImportBeanDefinitionRegistrar接口,实现了regidterBeanDefinition()方法,也就是说在spring容器扫描完,处理BeanDefinitionMap的时候,调用了这个扩展接口。
spring源码之Mybatis扫描器
而这个方法主要做的就是向beanDefinitionMap中添加了一个类,叫MapperScannerConfigurer
spring源码之Mybatis扫描器
点进这个类MapperScannerConfigurer,可以看到它继承了BeanDefinitionRegistryPostProcessor,
spring源码之Mybatis扫描器
那就以为意味着,一定会执行这个方法postProcessBeanDefinitionRegistry()
这个方法的主要作用是构造了一个mybatis的扫描器
其中需要注意的点就是这个方法
spring源码之Mybatis扫描器
这个方法是在扫描器中添加了几个过滤器,
第一个annotationClass:是指在扫描的注解中如果有annotationClass属性的话,那么扫描到的类,就必须要添加属性中指定的注解,才会被处理。 如:@MapperScan(value = “com.spring.batis.dao”, annotationClass = Mapper.class) ,只有扫描到的类,都加了Mapper注解的话,才会被mybatis代理

第二个markerInterface:这个里面直接返回了false,包下面所有的接口都不扫描了

第三个是acceptAllInterfaces:这个里面直接返回了true,意思是所有扫描到的接口全都处理。这可以解释一下这个lambda表达式。它传入的是 TypeFilter类,所以这行代码等同于

addIncludeFilter((metadataReader, metadataReaderFactory) -> true);

//等同于

addIncludeFilter(new TypeFilter() {
			@Override
			public boolean match(MetadataReader metadataReader, MetadataReaderFactory metadataReaderFactory) throws IOException {
				return true;
			}
		});

第四个一般都是没有这个类,可以忽略。
spring源码之Mybatis扫描器

再回到postProcessBeanDefinitionRegistry()方法中,看他的scan()方法
spring源码之Mybatis扫描器
scan()方法是在父类ClassPathBeanDefinitionScanner中执行,而其中的doScan()方法又到了子类过滤器ClassPathMapperScanner中执行。
spring源码之Mybatis扫描器
虽然最终执行的还是父类doScan()方法,但是这个下面的代码是很重要的。
spring源码之Mybatis扫描器
那这个doScan()方法又回到了spring的源码中了,我们已经分析过如何扫描个过滤的。
spring源码之Mybatis扫描器

spring boot如何扩展mybatis

按照上面的源码分析,也就是说,如果MapperScan注解中不加annotation这个属性去指定Mapper注解的话,就可以扫描指定包下面的所有接口。
那么为什么springBoot不需要写MapperScan注解,但是需要将mybatis接口类上写@Mapper注解呢,如果不写的话这个mapper接口就不会生效。

大概说一下,就是springboot不需要手动添加MapperScan,它会自动通过mybatis-spring-boot-starter中的配置类,进行扫描,而扫描的时候,添加了一个Mapper注解的过滤器。也就是说,扫描到的接口类,只有添加了@Mapper注解的才会作为mapper来处理。
所以我们在使用springBoot进行开发的时候,尽量把mapper接口文件放在同一个中,并且统一添加mapper注解。

  • 作者:木小同
  • 原文链接:https://blog.csdn.net/weixin_41011482/article/details/124900269
    更新时间:2023年7月22日12:06:11 ,共 1619 字。