Mybatis 返回结果映射类实体异常

Mybatis 返回结果映射类实体异常

问题现象

org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.reflection.ReflectionException: Error instantiating class com.xxx.*.xxxEntity with invalid types () or values (). Cause: java.lang.InstantiationException

org.mybatis.spring.MyBatisSystemException: nested exception is org.apache.ibatis.reflection.ReflectionException: Error instantiating class com.xxx.*.xxxEntity with invalid types () or values (). Cause: java.lang.InstantiationException

原因一

实体类 com.xxx..xxxEntity 就是你返回结果实际的实体类。
这种情况下是因为实体类 com.xxx.
.xxxEntity 没有无参数的构造函数,一般是定义了有参数的构造函数,但没有添加无参构造函数,这种情况下添加一个无参构造函数即可解决。

原因二

实体类 com.xxx.*.xxxEntity 是你的泛型的类,并不是你实际返回的实体类。
这时,意味着 mybatis 解决 dao 层返回结果类里,未能根据泛型找到对应类,这个问题的重现方式是使用
mybatis 3.4.6 然后 泛型 dao 层继承三层以上。

如:
public interface BaseDao{
E get(String id);
}
public interface BaseDaoC extends BaseDao{}
public interface BaseDaoCC extends BaseDaoC{}
public interface TestDao extends BaseDaoCC{}

这时使用 TestDao 调用 get 方法就会报
class BaseEntity with invalid types () or values (). Cause: java.lang.InstantiationException

这时返回的实体类是泛型类 BaseEntity;并不是你定义的 TestEntity;这时如果把 BaseDao 的 get 方法移到 BaseDaoC 中,就不会报错了。
看到这我就开始怀疑是 Mybatis 结果映射解析出错了,查看原码;

在结果映射解析中 是 方法 resolveTypeVar 和 scanSuperTypes 相结合完成的

Mybatis 返回结果映射类实体异常_第1张图片
Mybatis 返回结果映射类实体异常_第2张图片

跟踪源码你会发现
result = ((ParameterizedType) srcType).getActualTypeArguments()[j];
中取到的还是泛型,srcType 值会是 BaseDaoC 类,这时泛型找不到实际类,就会使用 BaseEntity 来代替。

于是我更新了 mybatis 的版本为 3.5.6 问题解决了!于是我去跟踪源码发现,版本3.4.6 与 版本3.5.6 中 scanSuperTypes 方法不同
版本3.5.6 中的 scanSuperTypes 方法:

Mybatis 返回结果映射类实体异常_第3张图片

Mybatis 修复了这个 BUG !
在 版本3.4.6 到 版本3.5.6 中间有没有其他版本修复了这个 BUG 我不知道,我这边问题出现是在 版本3.4.6 上出现的,然后我确认修复 BUG 的版本是 3.5.6


若有凝问或错误,请指出,我好及时改正,让我们一起进步!
email : [email protected]
qq : 103 586 2795
敲门砖: 代码谱写人生

你可能感兴趣的:(Mybatis,mybatis,mysql,java,spring,bug)