@Mapperscan:标注在 springboot 的启动类上面,配置 basePackages 属性,可以去扫描指定路径下的接口扫描为 Mapper 接口。

@Mapper:标注在接口上,表名这是一个 Mapper 接口。

工作原理:

两者都使普通接口转为 mapper 接口,也即是把接口的beanClass设置为mapperFactoryBean

 @Mapperscan:

@Mapperscan类头有注解@Import(MapperScannerRegistrar.class),MapperScannerRegistrar 因此会被初始化,并执行 registerBeanDefinitions() 方法。在这个方法中重点看这行代码:

它会实例化 MapperScannerConfigurer,然后执行该类的 postProcessBeanDefinitionRegistry() 方法,在这方法中设置了接口的 beanClass 。

@Mapper 

@Mapper 注解是在 mybatis 加载时候起作用的,在 MybatisAutoConfiguration 中有如下代码:

 由该类的头部注解可知,在 spring 上下文中没有 MapperScannerConfigurer 实例时候会进行初始化,而 MapperScannerConfigurer 恰恰是 @Mapperscan 存在的时候才有的实例,由此可知 @Mapper和@Mapperscan只有一个起作用,而 @Mapperscan 优先级较高。因此当 @Mapperscan 不存在时候,有该类的头部注解@import,会实例化 AutoConfiguredMapperScannerRegistrar ,这个类会进行 MapperScannerConfigurer 的实例化。

mapperFactoryBean重写了getObejct()方法。跟踪 getObject() 方法,发现最终实例化接口的代码如下:

也即是我们写 mapper 接口,然后 mybatis 为我们生成一个 MapperProxy 对象去实现 mapper 接口。

Logo

为开发者提供学习成长、分享交流、生态实践、资源工具等服务,帮助开发者快速成长。

更多推荐