【发布时间】:2012-03-27 02:38:07
【问题描述】:
我在尝试在 Hibernate 中创建的一对一双向关系时遇到问题。在创建和保存新的子项和父项时,它会尝试使用对父项的空引用来保持子项。查看休眠日志,它会为两个表生成 id,然后将子级对父级的引用设置为 null 并执行查询。我完全糊涂了。
在父类的注释类中,我有:
@OneToOne
@JoinColumn(name = "CHILD_ID")
@Cascade(CascadeType.ALL)
private Child child;
在孩子的注释类中,我有:
@OneToOne
@JoinColumn(name = "PARENT_ID")
private Parent parent;
为了创建/持久化,我有:
Parent p = new Parent();
Child c = new Child();
p.setChild(c);
c.setParent(p);
getHibernateTemplate().save(p);
Hibernate 日志,有趣的行以粗体显示:
[org.springframework.orm.hibernate3.SessionFactoryUtils] [打开休眠会话] [org.hibernate.impl.SessionImpl] [在时间戳打开会话:13313040615] [org.hibernate.event.def.DefaultSaveOrUpdateEventListener] [保存瞬态实例] [org.hibernate.jdbc.AbstractBatcher] [打开JDBC连接] [org.hibernate.SQL] [select UNQE_KEY_VALU from where UNQE_KEY_NAME = '' for update] [org.hibernate.jdbc.AbstractBatcher] [关闭 JDBC 连接(打开 PreparedStatements:0,全局:0)(打开 ResultSets:0,全局:0)] [org.hibernate.id.MultipleHiLoPerTableGenerator] [新喜值:1413946] [org.hibernate.event.def.AbstractSaveEventListener] [生成标识符:14139460,使用策略:org.hibernate.id.MultipleHiLoPerTableGenerator] [org.hibernate.event.def.AbstractSaveEventListener] [保存 [Parent#14139460]] [org.hibernate.engine.Cascade] [处理级联 ACTION_SAVE_UPDATE 为:父级] [org.hibernate.engine.CascadingAction] [级联到 saveOrUpdate: Child] [org.hibernate.engine.IdentifierValue] [id unsaved-value: 0] [org.hibernate.event.def.AbstractSaveEventListener] [瞬态实例:子] [org.hibernate.event.def.DefaultSaveOrUpdateEventListener] [保存瞬态实例] [org.hibernate.jdbc.AbstractBatcher] [打开JDBC连接] [org.hibernate.SQL] [select UNQE_KEY_VALU from where UNQE_KEY_NAME = '' for update] [org.hibernate.jdbc.AbstractBatcher] [关闭 JDBC 连接(打开 PreparedStatements:0,全局:0)(打开 ResultSets:0,全局:0)] [org.hibernate.id.MultipleHiLoPerTableGenerator] [新喜值:1413947] [org.hibernate.event.def.AbstractSaveEventListener] [生成标识符:14139470,使用策略:org.hibernate.id.MultipleHiLoPerTableGenerator] [org.hibernate.event.def.AbstractSaveEventListener] [保存 [Child#14139470]] [org.hibernate.engine.Cascade] [为:子级完成处理级联 ACTION_SAVE_UPDATE] [org.hibernate.engine.Cascade] [处理级联 ACTION_SAVE_UPDATE 为:父级] [org.hibernate.engine.Cascade] [完成处理级联 ACTION_SAVE_UPDATE 为:父] [org.springframework.orm.hibernate3.HibernateTemplate] [急切刷新 Hibernate 会话] [org.hibernate.event.def.AbstractFlushingEventListener] [刷新会话] [org.hibernate.event.def.AbstractFlushingEventListener] [处理刷新时间级联] [org.hibernate.engine.Cascade] [处理级联 ACTION_SAVE_UPDATE 为:父级] [org.hibernate.engine.CascadingAction] [级联到 saveOrUpdate: Child] [org.hibernate.event.def.AbstractSaveEventListener] [持久实例:子] [org.hibernate.event.def.DefaultSaveOrUpdateEventListener] [忽略持久实例] [org.hibernate.event.def.DefaultSaveOrUpdateEventListener] [对象已与会话关联:[Child#14139470]] [org.hibernate.engine.Cascade] [完成处理级联 ACTION_SAVE_UPDATE 为:父] [org.hibernate.event.def.AbstractFlushingEventListener] [脏检查集合] [org.hibernate.event.def.AbstractFlushingEventListener] [刷新实体和处理引用的集合] [org.hibernate.persister.entity.AbstractEntityPersister] [Child.parent 很脏] [org.hibernate.event.def.DefaultFlushEntityEventListener] [更新实体:[Child#14139470]] [org.hibernate.event.def.AbstractFlushingEventListener] [处理未引用的集合] [org.hibernate.event.def.AbstractFlushingEventListener] [调度集合删除/(重新)创建/更新] [org.hibernate.event.def.AbstractFlushingEventListener] [刷新:2 次插入,1 次更新,0 次删除到 2 个对象] [org.hibernate.event.def.AbstractFlushingEventListener] [刷新:0 次(重新)创作,0 次更新,0 次删除到 0 次收藏] [org.hibernate.pretty.Printer] [列出实体:] [org.hibernate.pretty.Printer] [父{child=Child#14139470, parentId=14139460}] [org.hibernate.pretty.Printer] [子{parent=Parent#14139460, childId=14139470}] [org.hibernate.event.def.AbstractFlushingEventListener] [执行刷新] [org.hibernate.jdbc.ConnectionManager] [注册刷新开始] [org.hibernate.persister.entity.AbstractEntityPersister] [插入实体:[Child#14139470]] [org.hibernate.jdbc.AbstractBatcher] [即将开启PreparedStatement(开启PreparedStatements:0,全局:0)] [org.hibernate.jdbc.ConnectionManager] [打开JDBC连接] [org.hibernate.SQL] [插入 CHILD_TABLE (PARENT_ID, CHILD_ID) 值 (?, ?)] [org.hibernate.jdbc.AbstractBatcher] [准备声明] [org.hibernate.persister.entity.AbstractEntityPersister] [脱水实体:[Child#14139470]] [org.hibernate.type.LongType] [将 null 绑定到参数:1] [org.hibernate.type.LongType] [绑定'14139470'到参数:2] [org.hibernate.persister.entity.AbstractEntityPersister] [插入实体:[Parent#14139460]] [org.hibernate.jdbc.AbstractBatcher] [执行批处理大小:1] [org.hibernate.jdbc.AbstractBatcher] [即将关闭PreparedStatement(打开PreparedStatements:1,全局:1)] [org.hibernate.jdbc.AbstractBatcher] [结束声明] [DEBUG] [org.hibernate.util.JDBCExceptionReporter] [无法执行 JDBC 批量更新 [插入 CHILD_TABLE (PARENT_ID, CHILD_ID) 值 (?, ?)]] java.sql.BatchUpdateException: ORA-01400: 无法将 NULL 插入 ("CHILD_TABLE"."PARENT_ID")在前两行粗体中,父母知道孩子的 id,反之亦然。但是,在生成孩子的sql时,它会将父母的id设置为null。怎么回事?
编辑: 作为参考,我正在使用以下休眠罐子: org.hibernate:hibernate-annotations:jar:3.3.1.GA org.hibernate:hibernate:jar:3.2.6.ga
【问题讨论】: