升级Hibernate Core 6.6.15.Final遇TransientObjectException求解决方案
升级到Hibernate Core 6.6.15.Final后,保存记录时触发以下异常:
org.hibernate.TransientObjectException: persistent instance references an unsaved transient instance of 'com.entityName' (save the transient instance before flushing)
经排查,该问题与Hibernate内部代码变更相关,社区也存在同类问题讨论,但现有方案需修改500+ hbm.xml文件,改动成本过高,以下是更优雅的解决思路及相关说明:
临时配置规避方案
全局回退状态判断逻辑:通过Hibernate配置参数启用旧版行为,避免批量修改实体映射文件:
在hibernate.cfg.xml中添加配置:<property name="hibernate.session.allow_transient_references_in_persistent_state">true</property>或在代码中通过服务注册器设置:
StandardServiceRegistry registry = new StandardServiceRegistryBuilder() .applySetting("hibernate.session.allow_transient_references_in_persistent_state", "true") .build();该参数会让Hibernate回到之前的关联实例状态判断逻辑,绕过当前版本的严格校验。
批量脚本修改映射文件:若不想全局回退,可编写脚本批量更新hbm.xml文件,给需要的关联关系添加
cascade="save-update"或cascade="persist"属性,比如用Python、Groovy或Shell脚本遍历所有hbm.xml文件,针对<many-to-one>、<one-to-many>等关联节点自动插入cascade配置,大幅减少手动工作量。
后续版本修复情况
Hibernate团队已收到该变更引发的兼容性反馈,目前该问题已被纳入后续版本的优化计划,后续版本可能会调整该逻辑的触发条件,或提供更细粒度的配置选项。建议关注Hibernate官方发布日志,及时获取修复进展。
内容的提问来源于stack exchange,提问作者Bhargav Ruparel

