解决Spring使用@MapperScan问题

这篇文章主要介绍了解决Spring使用@MapperScan问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教

问题场景

今天小编在MyBatis 整合Spring 的时候,使用到了@MapperScan,在启动期出现了一个错误:

Invalid default: public abstract java.lang.Class org.mybatis.spring.annotation.MapperScan.factoryBean()

对于这个错误,小编也是倍感无奈,怎么会出现这个错误呢,看一下我的依赖有没有错误:

 compile(project(":spring-context")) //    compile(project(":spring-instrument")) // https://mvnrepository.com/artifact/cglib/cglib compile group: 'cglib', name: 'cglib', version: '2.2.2' // https://mvnrepository.com/artifact/mysql/mysql-connector-java compile group: 'mysql', name: 'mysql-connector-java', version: '8.0.21' // https://mvnrepository.com/artifact/org.mybatis/mybatis compile group: 'org.mybatis', name: 'mybatis', version: '3.5.2' // https://mvnrepository.com/artifact/org.mybatis/mybatis-spring compile group: 'org.mybatis', name: 'mybatis-spring', version: '2.0.2' 

完全没得毛病呀,他妈的,究竟是哪里出现了问题呢,小编这时将SpringFramework 源码从github 上clone 下来了,导入idea 开始寻找问题所在。。。

问题根源

经过不懈的努力,小编终于找到了问题根源,在AnnotationsScanner 类中的这个方法:

 static Annotation[] getDeclaredAnnotations(AnnotatedElement source, boolean defensive) { boolean cached = false; Annotation[] annotations = declaredAnnotationCache.get(source); if (annotations != null) { cached = true; } else { // 使用@MapperScan 的时候会报错,引入spring-jdbc 即可 // 具体原因暂时还不清楚 // Invalid default: public abstract java.lang.Class org.mybatis.spring.annotation.MapperScan.factoryBean() annotations = source.getDeclaredAnnotations(); if (annotations.length != 0) { boolean allIgnored = true; for (int i = 0; i 

AnnotatedElement 对于这个类,小编也是不太清楚,这时也倍感无奈,这个方法主要做的事情就是将Appconfig 配置类中的注解扫描下来,那会不会是注解的问题呢,在@MapperScan 注解的注释中发现小编的代码与MyBatis-Spring 开发团队提供的实例代码一致,这就让人想不明白了:

 * 
 * @Configuration * @MapperScan("org.mybatis.spring.sample.mapper") * public class AppConfig { * *   @Bean *   public DataSource dataSource() { *     return new EmbeddedDatabaseBuilder().addScript("schema.sql").build(); *   } * *   @Bean *   public DataSourceTransactionManager transactionManager() { *     return new DataSourceTransactionManager(dataSource()); *   } * *   @Bean *   public SqlSessionFactory sqlSessionFactory() throws Exception { *     SqlSessionFactoryBean sessionFactory = new SqlSessionFactoryBean(); *     sessionFactory.setDataSource(dataSource()); *     return sessionFactory.getObject(); *   } * } * 

问题追溯

我这个时候被起疯了都,从GitHub 上由把mybatis-spring 的源码clone 了下来,导入idea,首先看一下mybatis-spring 的依赖:

   org.mybatismybatis${mybatis.version}provided org.springframeworkspring-context${spring.version}provided org.springframeworkspring-jdbc${spring.version}provided org.springframework.batchspring-batch-infrastructure${spring-batch.version}provided

从依赖中看到了什么,tmd,provided,这个怎么讲,太无语了,其中它引入了spring-jdbc 的依赖。想象一下,@MapperScan 注解中是不是也使用到了spring-jdbc 的类,然后在使用@MapperScan 的时候没有加入spring-jdbc 的依赖,导致注解在扫描期间的错误,没毛病解释的通,找一下@MapperScan 中是否使用到了spring-jdbc 的依赖。

问题解决

果不其然,下面用一张图来看吧。

所以呢,在项目中加入spring-jdbc 完美解决。

SpringBoot  @MapperScan的注意事项

错误代码如下:

[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.builder.BuilderException: Error invoking SqlProvider method (tk.mybatis.mapper.provider.base.BaseSelectProvider.dynamicSQL). Cause: java.lang.InstantiationException: tk.mybatis.mapper.provider.base.BaseSelectProvider] with root cause

检查@MapperScan导入的包是否为

 import tk.mybatis.spring.annotation.MapperScan;

切记不要导成

 import org.mybatis.spring.annotation.MapperScan

以上为个人经验,希望能给大家一个参考,也希望大家多多支持0133技术站。

以上就是解决Spring使用@MapperScan问题的详细内容,更多请关注0133技术站其它相关文章!

赞(0) 打赏
未经允许不得转载:0133技术站首页 » Java