Spring Boot升级至2.6.0后出现Hibernate ClassCastException问题求助
问题原因与解决方法
为什么升级后出现ClassCastException?
Spring Boot 2.6.x同步将Hibernate从5.4.x升级到5.6.x后,Hibernate对单表继承结构的代理生成逻辑发生了变化:针对抽象父类Parent,现在生成的是父类的代理对象(如Parent$HibernateProxy$xxx),而非对应数据库记录的子类(Child1/Child2)代理。这种父类代理无法直接强转为子类,因此抛出类型转换异常。
升级前(Hibernate 5.4.x)为什么可行?
在Hibernate 5.4.x版本中,对于单表继承的实体,框架会根据数据库中classType字段的鉴别器值,直接生成对应子类的代理对象。此时父类类型的引用实际指向子类代理,强转自然可以成功。
恢复升级前行为的方案
方案1:替换Spring Data JPA方法
将getById()替换为findById(),因为findById()默认会立即加载真实实体实例(而非代理),返回的对象本身就是对应子类类型,无需强转或处理代理:
Child1 child1 = repo.findById(id).orElseThrow(() -> new EntityNotFoundException("Child1 not found"));
方案2:修改Hibernate配置
通过配置让Hibernate恢复5.4.x的代理生成逻辑,在application.properties(或application.yml)中添加:
spring.jpa.properties.hibernate.proxy.pojo.class_loader.enabled=true
该配置会启用支持子类代理的类加载器,让Hibernate根据鉴别器值生成对应子类的代理,这样getById()返回的代理可以直接强转为子类。
不推荐的方案(关闭延迟加载)
在父类Parent上添加@Proxy(lazy = false),强制关闭延迟加载,此时getById()会直接返回真实实体。但这会失去延迟加载的性能优势,仅适合不需要延迟加载的场景:
@Entity @Inheritance(strategy = InheritanceType.SINGLE_TABLE) @DiscriminatorColumn(name = "classType", discriminatorType = DiscriminatorType.STRING) @Proxy(lazy = false) public abstract class Parent { // ... }
内容的提问来源于stack exchange,提问作者L_G
相关产品推荐
相关产品推荐

