11

我有一个只包含 2 个字段的表。该表具有由这两个字段组成的复合 PK。

当使用 Netbeans 从数据库创建实体 bean 时,实体 bean 不会像其他具有 2 个以上字段的表一样自动创建。

所以我想我需要自己创建实体bean。创建此实体 bean 的最佳实践是什么?它是否必须包含COMPOSITE KEY对象?

4

2 回答 2

30

我不使用 NetBeans,所以我不能真正谈论它的映射工具。

对于映射复合键,有几个选项。你可以

  • @Embeddable使用 PK 字段定义一个单独的对象,并@EmbeddedId 在您的@Entity类中使用它

    @Embeddable
    public class MyCompositePK { 
        @Column
        private String fieldA;
        @Column
        private String fieldB;
    }
    @Entity 
    public class MyBean { 
        @EmbeddedId
        private MyCompositePK id;
        @Column
        private String fieldC;
    }
    
  • 使用 PK 字段定义一个非映射 POJO,并像@IdClass@Entity.

    @Entity
    @IdClass(value=ClassAB.ClassABId.class)
    public class ClassAB implements Serializable {
        private String idA;
        private String idB;
    
        @Id
        @Column(name="ID_A")
        public String getIdA(){ return idA; }
        public void setIdA(String idA){ this.idA = idA; }
    
        @Id
        @Column(name="ID_B")
        public String getIdB(){ return idB; }
        public void setIdB(String idB){ this.idB = idB; }
    
        static class ClassABId implements Serializable {
            private String idA;
            private String idB;
    
            public String getIdA(){ return idA; }
            public void setIdA(String idA){ this.idA = idA; }
    
            public String getIdB(){ return idB; }
            public void setIdB(String idB){ this.idB = idB; }
    
            // implement equals(), hashcode()
        }
    }
    

    在这个例子ClassABId中是一个静态内部类只是为了方便。

Pascal Thivent 对这个问题的出色回答也解释了这些选项:如何使用 Hibernate 映射复合键?.

这个相关问题讨论了这些方法之间的差异:我应该使用哪个注释:@IdClass 或 @EmbeddedId。请注意,字段的声明与该@IdClass方法重复。

无论如何,我认为除了创建两个类之外别无选择。这就是我问这个问题的原因:映射一个只包含没有 @IdClass 或 @EmbeddedId 的复合 PK 的类。似乎有一个特定于休眠的功能。

附带说明一下,如果您可以控制数据库结构,您还可以考虑避免使用复合键。有一些理由这样做

于 2013-02-06T12:45:17.327 回答
0

谢谢@XaviLópez。您的解释修复了我的代码,该代码被声明为@Tom Anderson 提到的自己的 IdClass。当我声明它自己的具有 2 个 @Id 列的 IdClass 时,获取该实体列表的 JPA 查询在结果列表中返回预期的“n”个项目,但该列表中的每个项目都是空的。但是这个大小“n”是预期的。更改为较少重构的静态内部类后,它能够返回正确的结果集。

据我说:自我引用 IdClass 不会起作用,因为自我已经是一个实体,需要在持久性上下文中。如果我还有一个相同类型的主键对象,那么持久化上下文中就会有两个“相同”的对象。所以,它不应该被允许。因此,我们不应该使用自引用@IdClass。创建一个静态内部类作为侵入性较小的主键类型。

于 2013-11-07T13:39:21.427 回答