java - Hibernate 自引用父子

标签 java sql spring hibernate one-to-many

我知道有很多关于这个主题的条目。我已经阅读了所有这些内容以寻找我面临的问题。

我有一个带有自引用的类/表。这是类

public class Comment {

    private Integer id;
    private Comment parent;
    private Issue   issue;
    private User    author;
    private String  body;
    private Date    created;
    private Date    updated;

    private Set<Comment> childs;

    // All setters and getters
}

在这里你可以看到 hbm.xml 文件:

<hibernate-mapping>
 <class name="Comment" table="COMMENTS">

  <id name="id" type="java.lang.Integer">
   <column name="ID"/>
   <generator class="native"/>
  </id>

  <many-to-one cascade="all"
   class="Comment" fetch="join" name="parent">
   <column name="PARENT" not-null="false"/>
  </many-to-one>

  <many-to-one class="Issue"
   fetch="join" name="issue">
   <column name="ISSUE" not-null="true"/>
  </many-to-one>

  <many-to-one class="User"
   fetch="join" name="author">
   <column name="AUTHOR" not-null="true"/>
  </many-to-one>

  <property generated="never" lazy="false" name="body" type="java.lang.String">
   <column name="BODY" not-null="true"/>
  </property>

  <property generated="never" lazy="false" name="created" type="java.util.Date">
   <column name="CREATED"/>
  </property>

  <property generated="never" lazy="false" name="updated" type="java.util.Date">
   <column name="UPDATED"/>

  </property>
  <set cascade="delete" fetch="select" inverse="true" lazy="true"
   name="childs" sort="unsorted" table="COMMENTS">
   <key>
    <column name="ID" not-null="true"/>
   </key>
   <one-to-many class="Comment"/>
  </set>

 </class>

</hibernate-mapping>

目前一切正常。但是我一定在某处出错了,因为当我运行这个单元测试时

Session session = sessionFactory.getCurrentSession();

User user = new User("loginName", "password", "firstName", "lastName", "eMail");
session.save(user);
session.flush();
session.clear();

Issue issue = new Issue();
session.save(issue);
session.flush();
session.clear();

Comment parent = new Comment(issue, user, "body_parent");
session.save(parent);

Comment child = new Comment(issue, user, "body_child_1");
child.setParent(parent);
parent.getChilds().add(child);
session.save(child);
session.flush();
session.clear();

parent = (Comment) session.createQuery("from Comment comment where comment.body='body_parent'").uniqueResult();

System.out.println(parent);
System.out.println(parent.getChilds().iterator().next());

我添加最后两行是为了向您展示我现在面临的问题:

COMMENT = [id=1, parentId=<root>, issueId=1, authorId=1, body=body_parent, created=2014-03-08 19:28:54.832, updated=2014-03-08 19:28:54.832, numChilds=1]
COMMENT = [id=1, parentId=<root>, issueId=1, authorId=1, body=body_parent, created=2014-03-08 19:28:54.832, updated=2014-03-08 19:28:54.832, numChilds=1]

parent 和 child 都是一样的!我真的不明白这里的问题。 当我通过查询检索 child 时,结果是正确的,但是当我通过 getChild() 获取 child 时,没有检索其 child 的查询。

你有什么想法吗?有什么线索吗?我在这里看不到隧道尽头的光:-/

提前致谢!

最佳答案

我终于明白问题出在哪里了!嗯,有几个问题。

首先,数据库和类中都没有parent_id 字段。 其次,没有异常(exception),因为我激活了集合的 inverse 属性。

这两个问题的结合就是问题所在。

下面,我发布了工作解决方案。

评论.java

public class Comment {
    private Integer      id;
    private Integer      parentId; // Parent ID was missing
    private Issue        issue;
    private User         author;
    private String       body;
    private Date         created;
    private Date         updated;

    private Comment      parent; // Reference to parent though parentId
    private Set<Comment> childs = new HashSet<Comment>(0);


    protected Comment () {

    }

   // All setters and getters
}

评论.hbm.xml

<hibernate-mapping>
 <class name="es.kazbeel.geckobugtracker.model.Comment" table="COMMENTS">

  <id name="id" type="java.lang.Integer">
   <column name="ID"/>
   <generator class="native"/>
  </id>

  <property name="parentId" type="java.lang.Integer" update="false" insert="false" column="PARENT_ID" />

  <many-to-one class="es.kazbeel.geckobugtracker.model.Issue"
   fetch="join" name="issue">
   <column name="ISSUE"/>
  </many-to-one>

  <many-to-one class="es.kazbeel.geckobugtracker.model.User"
   fetch="join" name="author">
   <column name="AUTHOR"/>
  </many-to-one>

  <property generated="never" lazy="false" name="body" type="java.lang.String">
   <column name="BODY"/>
  </property>

  <property generated="never" lazy="false" name="created" type="java.util.Date">
   <column name="CREATED"/>
  </property>

  <property generated="never" lazy="false" name="updated" type="java.util.Date">
   <column name="UPDATED"/>
  </property>

  <many-to-one name="parent" class="es.kazbeel.geckobugtracker.model.Comment" column="PARENT_ID" not-null="false" />

  <set name="childs" table="COMMENTS"  lazy="false" cascade="all-delete-orphan" inverse="false">
   <key column="PARENT_ID" />
   <one-to-many class="es.kazbeel.geckobugtracker.model.Comment"/>
  </set>

 </class>
</hibernate-mapping>

我希望这对将来的人有所帮助。这是我第一次发布 self 解决方案:)

关于java - Hibernate 自引用父子,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22273391/

相关文章:

sql - 在插入之前检查 SQL Server 表中是否已存在记录

java - JsonView 无法与 Spring 一起正常工作

java - 使用反射将值设置到对象中

java - 通过java套接字传输文件客户端-服务器

mysql - 如何更新 JOIN 上的 SQL

sql - 将 json 列转换为新的 json 列

java - 将原始文本添加到 SOAP header

java - 如何更改我的 Eclipse 控制台结果行颜色。使用 java selenium 对于每行不同的颜色

java - 未应用 Spring 模型

java - 如何将堆栈跟踪作为来自 spring Controller 的响应作为 JSON 对象发送