使用 @EmbeddedId 映射时出现 Eclipse 错误

Posted

技术标签:

【中文标题】使用 @EmbeddedId 映射时出现 Eclipse 错误【英文标题】:Eclipse error on mapping with @EmbeddedId 【发布时间】:2012-08-19 19:47:20 【问题描述】:

我有一个带有复合键的实体,所以我使用了@Embeddable 和@EmbeddedId 注释。 可嵌入类看起来像这样:

@Embeddable
public class DitaAdminAccountSkillPK implements Serializable 

  @ManyToOne
  @JoinColumn(name = "admin_id")
  private DitaAdmin admin;

  @ManyToOne
  @JoinColumn(name = "account_id")
  private DitaAccount account;

  //constructor, getters, setters...

以及使用它的实体:

@Entity
public class DitaAdminAccountSkill 

  @EmbeddedId
  private DitaAdminAccountSkillPK id;

  //constructor, getters, setters...

现在我想像这样将实体映射到另一个实体中:

@OneToMany(fetch = FetchType.LAZY, mappedBy = "id.admin")
private List<DitaAdminAccountSkill> accountSkills;

注意 mappedBy = "id.admin" 使用 id 引用 DitaAdminAccountSkillPK 中的 admin 字段DitaAdminAccountSkill 的字段。

这编译并运行得很好。但是,在 Eclipse 中会显示一条错误消息: 在属性“accountSkills”中,“映射者”值“id.admin”无法解析为目标实体上的属性。

请注意,这是一个 JPA 问题,表示 JPA 方面正在抱怨。 现在,我知道我可以改用@IdClass,但我只是想知道为什么它认为这是一个错误。或者我做错了什么?

【问题讨论】:

【参考方案1】:

根据JPA 2.0 specification 的第 11.1.15 节:不支持在嵌入式 id 类中定义的关系映射。但是,JPA可能支持这一点您正在使用的实现,即使它没有得到标准本身的正式支持。

如果是这种情况,您可能希望在 Eclipse 中的 Window -&gt; Preferences -&gt; Java Persistence -&gt; JPA -&gt; Errors/Warnings -&gt; Attributes -&gt; Cannot resolve attribute name 下关闭对此的验证。

【讨论】:

有没有 JPA 2.0 规范支持的方法? 回答了我自己的问题。 JPA 2.0 规范的第 2.4.1.3 节(找到 here)列出了一些非常有用的示例。我的解决方案是使用@EmbeddedID@MapsId 找到对 JPA 2.0 友好的解决方案:***.com/questions/10078224/…【参考方案2】:

在我的情况下,直到我将以下内容设置为Ignore,问题才得到解决:

Project Facets > JPA > Errors/Warnings > Type > Mapped Java Class is a member class

【讨论】:

【参考方案3】:

我想我会发布我发现的符合 JPA 2.0 规范并且功能似乎相同的解决方案。

首先,JPA 2.0 规范可以在这里找到:JSR-000317 Persistence Specification for Eval 2.0 Eval。相关部分将是 2.4.1“对应于派生身份的主键”

这是一个使用您指定的类的示例:

嵌入式 Id 类:

@Embeddable
public class DitaAdminAccountSkillPK implements Serializable 

    //No further annotations are needed for the properties in the embedded Id.

    //Needs to match the type of the id of your DitaAdmin object. I added 'Id' to the end of the property name to be more explicit.
    //Making the assumption here that DitaAdmin has a simple Integer primary key.
    private Integer adminId;

    //Needs to match the type of the id of your DitaAccount object. I added 'Id' to the end of the property name to be more explicit.
    //Making the assumption here that DitaAccount has a simple Integer primary key.
    private Integer accountId;


    //I'm adding a third property to the primary key as an example
    private String accountName;

    //constructor, getters, setters...

    //hashCode() and equals() overrides

“依赖”实体类:

@Entity
public class DitaAdminAccountSkill 

    @EmbeddedId
    //Any overrides to simple Id properties should be handled with an attribute override
    @AttributeOverride(name = "accountName", column = @Column(name = "account_name"))
    private DitaAdminAccountSkillPK id;

    //MapsId refers to the name of the property in the embedded Id
    @MapsId("adminId")
    @JoinColumn(name="admin_id")
    @ManyToOne
    private DitaAdmin admin;

    @MapsId("accountId")
    @JoinColumn(name="account_id")
    @ManyToOne
    private DitaAccount account;

    //constructor, getters, setters...

“父”实体类:

public class DitaAdmin 

    @Id
    private Integer id;

    //...

    //Now your mappedBy attribute can refer to the admin object defined on DitaAdminAccountSkill which is also part of the Primary Key
    @OneToMany(fetch = FetchType.LAZY, mappedBy="admin")
    private List<DitaAdminAccountSkill> accountSkills;

    //...

【讨论】:

使用这两个选项(mappedBy="id.admin" 或 mappedBy="admin").. 当我尝试映射“Non Lazy Collection”时,我会收到以下错误。错误:resql.util.PSQLException:错误:列 workflowst0_.stepseqno 不存在。请看***.com/questions/23312951/…。提前致谢。【参考方案4】:

在尝试任何以前的解决方案之前,请先检查您的 persistence.xml 并确保 exclude-unlisted-classes 设置为 true 或您的所有映射类都列在您的 persistence-unit 中。

【讨论】:

【参考方案5】:

Preferences -> Java Persistence -> JPA -> Errors/Warnings -> Attribute -> Embedded ID 类不应包含关系映射:(忽略)

【讨论】:

以上是关于使用 @EmbeddedId 映射时出现 Eclipse 错误的主要内容,如果未能解决你的问题,请参考以下文章

Embeddable 和 EmbeddedId 之间的 JPA 映射 @ManyToOne

我应该使用哪个注释:@IdClass 或 @EmbeddedId

使用 Hibernate 从 DB 检索数据时出现映射错误

定义映射时出现休眠异常

RPC:端口映射运行时出现超时错误

使用一对多映射保存对象时出现 Spring + Hibernate id 问题