一旦你看到我在代码块中发布的复合密钥和使用它们的实体,请参考我需要在数据库中为地址实体提供的下一个伪代码:
地址表:
ADDRESS
-------------------------------
DOCUMENTTYPE INT2 PK
DOCUMENTNR VARCHAR(10) PK
ALIAS VARCHAR(20) PK
FULLADDRESS VARCHAR(100)
...
实体&复合键:
@Embeddable
public class Document implements Serializable {
private DocumentType documentType;
private String documentNr;
...
@Entity
@IdClass(Document.class)
public class Person {
@Id
private DocumentType documentType;
@Id
private String documentNr;
private String fullName;
...
@Embeddable
public class AddressId implements Serializable {
private DocumentType documentType;
private String documentNr;
private String alias;
...
@Entity
@IdClass(AddressId.class)
public class Address {
@Id
@ManyToOne
private Person person;
@Id
private String alias;
private String fullAddress;
...
注意: DocumentType 是枚举。
好吧,我正在尝试为地址实体设置映射,但它不起作用,我不知道为什么。它一直在说(EclipseLink)我遇到名称和类型不匹配的问题。我不明白为什么如果 AddressId IdClass没有alias属性(当然也没有 Address 实体),那么它就像魅力一样,以及使用完整的 AddressId IdClass(使用alias属性)但使用EmbeddedId。我需要的是像我发布的那样拥有地址实体。
映射错误在哪里?
提前谢谢!
答案 0 :(得分:0)
我认为您必须将@Enumerated(EnumType.STRING)
添加到enum
字段
像这样:
@Id
@Enumerated(EnumType.STRING)
private DocumentType documentType;
答案 1 :(得分:0)
我无法直接回答你的问题。但是,这是一个可能有帮助的观察结果:
我认为您的数据库架构在将其映射到Java之前需要工作。以下是一些建议:
1:每个数据库表应该只有一个主键(通常是long类型),主键应该没有业务含义。任何地方都没有复合键由于没有复合键,原始问题不再是问题。
2:主键通常以带有ID的表名命名(从不使用'ID'作为名称)。
实施例: 地址 addressID long primaryKey
3:您调用主键的其他字段应该是引用其他表主键的外键(类型为long,后面带有ID)。
4:您需要正确规范化数据库表。示例:列'fullAddress'可能应该分为streetAddress,city,stateID,countryID,zipcode。另一个例子:ADDRESS表应该只包含地址信息。为什么它有DOCUMENTTYPE?这与地址有什么关系?
5:应清楚地理解数据库表和列的名称。 “DOCUMENTNR”栏对我没有任何意义。
6:您的数据库表和列应该是nowns,它们通常应该映射到具有相同名称的java类。相反,你有一个名为AddressId的类,它显然映射到地址数据库表。将类重命名为Address。
7:您需要确定哪些列是唯一的而不是可空的。
您可以与友好的邻居数据库管理员联系,以获取有关创建数据库架构的帮助。
答案 2 :(得分:0)
地址的派生ID必须包含来自person的id,即文档而不是其组件。 http://wiki.eclipse.org/EclipseLink/Development/JPA_2.0/mappedbyid显示了一些示例,但更多的是针对嵌入式,但idclasses的概念是相同的。尝试
public class AddressId implements Serializable {
private Document person;
private String alias;