简体   繁体   English

如何将Hibernate中的一对多关联添加到嵌入式类型?

[英]How to add one-to-many association in Hibernate to an embedded type?

I have an Entity that holds the last instance of a Component: 我有一个实体,它持有Component的最后一个实例:

@Entity
public class Customer {
  ...
  @Embedded
  public ServiceCall getLastServiceCall() {...}
  ...
}

@Embeddable
public class ServiceCall() {
  public Date getDate();
  public Status getStatus();
}

The ServiceCall is embedded in order to call customer.getLastServiceCall().getDate() without requiring another table join. 嵌入ServiceCall是为了调用customer.getLastServiceCall().getDate()而不需要另一个表联接。

I want to make that association one-to-many, and start saving all ServiceCall s, while holding one embedded in the customer. 我想使该关联一对多,并开始保存所有ServiceCall ,同时在客户中保留一个。

Hibernate's Docs (v3.6, which I'm using) states: Hibernate的文档 (我正在使用v3.6)指出:

You can also use association annotations in an embeddable object (ie @OneToOne, @ManyToOne, @OneToMany or @ManyToMany). 您还可以在可嵌入对象(即@ OneToOne,@ ManyToOne,@ OneToMany或@ManyToMany)中使用关联注释。 To override the association columns you can use @AssociationOverride. 要覆盖关联列,可以使用@AssociationOverride。

and it seem that all I should do is add @OneToMany to the LastServiceCall association. 似乎我应该做的就是将@OneToMany添加到LastServiceCall关联中。

Will that work for me? 那对我有用吗? If not, what are my alternatives? 如果没有,我有什么选择? If yes, how will that affect 2nd level cache, and is there a limitation on updating that embedded instance (I can live with an immutable objects)? 如果是,那么这将对二级缓存有何影响?在更新该嵌入式实例方面是否存在限制(我可以使用不可变的对象)?

@Embeded types are not supposed to have their own identity in the database, so I don't think you can add @OneToMany to the Customer class on the ServiceCall. @Embeded类型不应该在数据库中具有自己的标识,因此我认为您不能在ServiceCall的Customer类中添加@OneToMany。

  @OneToMany 
  @Embedded
  public ServiceCall getLastServiceCall() {...}

However you can add an association to the @Embeded Service call element like so. 但是,您可以像这样将关联添加到@Embeded Service调用元素。

@Entity 
pubic class HistoricalServiceCall extends ServiceCall 
{
   @Id 
   private String id; 

}


@Embeddable 
public class ServiceCall {

   @OneToMany(fetch=FetchType.LAZY)
   @JoinColumn(name="join_column_defined_on_customer_table")
   List<HistoricalServiceCall> getServiceCallHistory(); 
}

Update: putting FetchType.LAZY on the getServiceCallHistory() is a hint to the JPA provider to wait until you call getServiceCallHistory before it does another select to pull in that association. 更新:将FetchType.LAZY放在getServiceCallHistory()上是向JPA提供程序的提示,提示您等待直到调用getServiceCallHistory之前,它再进行一次选择以拉入该关联。

So with the setup I am describing if you do customer.getLastServiceCall().getDate() it will not pull in the ServiceCallHistory before the relationship is lazy. 因此,对于安装程序,我要描述的是如果您执行customer.getLastServiceCall()。getDate(),则在关系变得懒惰之前它不会拉入ServiceCallHistory。

What you need is the following: 您需要以下内容:

  • A Customer entity 客户实体
  • An embeddable ServiceCall 嵌入式服务电话
  • A HistoricalServiceCall entity. HistoricalServiceCall实体。

The Customer should contain an embedded ServiceCall field (the last service call). 客户应包含一个嵌入式ServiceCall字段(最后一个服务调用)。

The HistoricalServiceCall entity should have an ID, an embedded ServiceCall field (the data of the HistoricalServiceCall), and, potentially, a ManyToOne association to Customer if you want the OneToMany to be bidirectional. 如果您希望OneToMany是双向的,HistoricalServiceCall实体应具有ID,嵌入式ServiceCall字段(HistoricalServiceCall的数据),以及可能与客户的ManyToOne关联。

The Customer should have a OneToMany association to HistoricalServiceCall. 客户应具有与HistoricalServiceCall的OneToMany关联。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM