18

我有两个类 A 和 B。许多 B 可以与单个 A 关联,因此从 B 到 A 是多对一关系。我将关系映射为:

<class name="A" table="tbl_A">
  <property name="propA" column="colA"/>
</class>
<class name="B" table="tbl_B">
  <property name="propB" column="colB"/>
  <many-to-one name="a" class="A" column="col1" cascade="delete"/>
</class>

A 没有映射到 B。记住这一点,我们打算在 B 关联的 A 被删除时删除它。如果我可以在 B 中的多对一关联上定义一个 inverse="true" ,这可能是可能的,但休眠不允许这样做。

有人能帮忙吗?我们不想为此在 A 中写任何东西。

4

2 回答 2

24

Hibernate 仅沿定义的关联级联。如果 A 对 Bs 一无所知,那么您对 ​​A 所做的任何事情都不会影响 Bs。

因此,帕斯卡的建议是做你想做的最简单的方法:

<class name="A" table="tbl_A">
  ...
  <set name="myBs" inverse="true" cascade="all,delete-orphan">
    <key column="col1"/>
    <one-to-many class="B"/>
  </set>
</class>

<class name="B" table="tbl_B">
  ...
  <many-to-one name="a" class="A" column="col1" not-null="true"/>
</class>

请注意,在您的原始代码中设置cascade="delete"B不会做您想要的 - 它告诉 Hibernate“如果 B 被删除,则删除 A”,这可能会导致违反约束(如果有任何其他 B 链接到该 A )。

如果您绝对不能将 B 的集合添加到 A(尽管我真的想不出会出现这种情况的情况),那么您唯一的另一种选择是在外键级别定义从 A 到 B 的级联删除;当您的 A 被删除时,您的 Bs 将被删除。

然而,这是一个相当丑陋的解决方案,因为您必须非常小心如何在 Hibernate 中删除 A:

  1. 必须在删除 A 之前刷新会话(对 B 进行挂起的更新可能会导致错误或 A 和一些 B 在幕后重新插入)
  2. 必须从所有活动会话和二级缓存中逐出所有链接到 A 的 B(并且由于您没有维护 A 方面的关系,这意味着所有B)。
于 2009-11-11T17:25:03.203 回答
7

我认为你需要cascade="all,delete-orphan"从 A 到 B 的一个one-to-many关联。

于 2009-11-11T14:29:46.130 回答