休眠。一个表中的几个外键

时间:2015-11-04 11:42:53

标签: java sql hibernate foreign-keys

在SQL模式中有下一个表结构:客户端,员工,订单。 相应的java代码中的3个实体类:Client,Employee,Order。

来自客户端和员工的主要id字段都在Orders表中作为外键。

问题是它应该如何在java代码中显示?  正如我在这里所理解的那样,应该像使用@OneToMany注释的客户和员工添加Set字段一样。

但是在Order Entity中应该做些什么,也许我必须添加除@OneToMany之外的任何其他注释?

1 个答案:

答案 0 :(得分:1)

我认为你对Hibernate的关系映射有一些误解。

如果您的Orders表实际上有Clients和Employees的外键,那么您要查找的注释是@ManyToOne

当您的实体具有目标实体引用的多个记录时使用@OneToMany注释,而当您的实体只有一个记录引用目标实体时使用@ManyToOne。

例如:

订单实体具有来自客户的一个引用和来自Employees实体的一个引用。

在这种情况下,可以通过以下方式映射Orders实体:

@Entity
@Table(name = "Orders")
public class Order implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    @ManyToOne
    private Client client;
    @ManyToOne
    private Employee employee;

    //getters and setters
}

@Entity
@Table(name = "Clients")
public class Client implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String attribute1;

    //getters and setters
}

@Entity
@Table(name = "Employees")
public class Employee implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String attribute1;

    //getters and setters
}

通过上面给出的示例,您应该能够使用Hibernate使您的架构正常工作,但为了理解,让我们想象一下您需要从客户端获取所有订单的场景,当然您可以做它只有一个查询,只选择Client表中的Orders,但是Hibernate提供了@OneToMany注释,这使您可以从客户端访问所有订单,而无需单独的查询,只需通过映射即可!我们来看一个例子:

@Entity
@Table(name = "Orders")
public class Order implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    @ManyToOne
    private Client client;

    //getters and setters
}

@Entity
@Table(name = "Clients")
public class Client implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    private String attribute1;
    @OneToMany(mappedBy = "client")
    private List<Order> orders;

    //getters and setters
}

在此示例中,您应该只需调用“orders”属性的get即可从客户端获取所有订单。请注意,在@OneToMany映射中,我们将“mappedBy”属性指定为“client”,因为我们在Client和Order之间有一个双向映射,所以需要@OneToMany的简单用法,你不需要这个映射。

重要提示:使用@OneToMany映射时,您最终会遇到一些延迟提取问题,在这种情况下,我强烈建议您查看以下问题:

Solve “failed to lazily initialize a collection of role” exception

另外,我认为你应该开始阅读更多有关Hibernate的内容以了解它的基本概念,请查看关于Hibernate的@OneToMany和@ManyToOne注释的另一个问题:

Hibernate/JPA ManyToOne vs OneToMany