-
-
Notifications
You must be signed in to change notification settings - Fork 1.6k
devtools
最早在 Spring Boot 中使用 Devtools 时,使用通用 Mapper 会报错: can't cast x.y.Z to x.y.Z
,
包名和类名完全一样,为什么会出现这个错误呢?
最早有人通过 issue 提出了一个解决方案,就是增加下面这个配置(spring-devtools.properties):
restart.include.mapper=/mapper-[\\w-\\.]+jar
在一段时间内,这个配置解决了前面遇到的问题,但是 4.0 版本发布后,又发现有人遇到了类似问题。
后来发现 core
下面并没有 spring-devtools.properties 配置文件,我还以为缺了,还在 4.0.2 中增加了这个,
实际上这个文件一直都没少,在 spring
子模块中一直都有这个文件,而且放在 spring
子模块也是最合适的位置。
为什么一直都有这个配置,还会出错呢?
实际上在后来发生的下面两个症状很可能都是 Devtools 导致的:
Error invoking SqlProvider method (tk.mybatis.mapper.provider.SpecialProvider.dynamicSQL)
java.lang.NoSuchMethodException: tk.mybatis.mapper.provider.SpecialProvider.<init>()
在 faq 中专门介绍了这两个错误的解决办法,但是一直没有完全处理所有的情况。
并且由于 Devtools 导致通用 Mapper 无法正常启动,因此也很难出现 can't cast x.y.Z to x.y.Z
。
详细分析看这里:https://github.com/abel533/mapper-cast-exception
没有增加时,因为 IDE 运行时,通用 Mapper 的 mapper-x.x.x.jar 会被 AppClassLoader 加载,
因此会出现 can't cast x.y.Z to x.y.Z
。
当增加上面的配置后,mapper-x.x.x.jar 会被 RestartClassLoader 加载,此时他们就一致了, 表面上解决了这个问题。
就是因为这个配置导致的。
前面使用时,有可能你所有的 XXMapper 都在当前的 IDE 中,因此这些 XXMapper 都会使用 RestartClassLoader 加载。
但是如果你依赖的项目(包含 XXMapper)不在当前的 IDE 中,那么该 XXMapper 就会使用 AppClassLoader 加载。
因此就会出现 AppClassLoader 加载的 XXMapper 获取 RestartClassLoader 加载的 @RegisterMapper
注解时,
就会找不到,因此该 XXMapper 就无法初始化,调用 XXMapper 的方法时就会报下面的错:
Error invoking SqlProvider method (tk.mybatis.mapper.provider.SpecialProvider.dynamicSQL)
同样 XXMapper 对应 XX 使用 Example(XX.class)
时,就报错找不到 XX
对应的表名。
最合理的情况就是没有 spring-devtools.properties 配置文件。
1. 集成通用 Mapper || 2. 对象关系映射 || 3. 配置介绍