【问题标题】:Trouble with a mapped class (OneToMany) containing OneToOne mappings包含 OneToOne 映射的映射类 (OneToMany) 出现问题
【发布时间】:2014-04-02 19:50:57
【问题描述】:

我一直在尝试通过一个名为 Guardian 的中间类来映射两个用户之间的一些“OneToOne”关系。当我尝试检索用户(及其监护人)时,我收到 Glassfish(开放版 v4.0)返回的内部服务器错误。但是,日志中没有显示任何类型的堆栈跟踪或任何错误。我怀疑问题是我在 JPA 类中的映射。

启动服务器时,我收到两个与 Guardian 类相关的警告,但我不太了解:

警告:映射到元素 [method getGuardianUserBean] 上的引用列名称 [GUARDIAN] 与映射引用上的有效 id 或基本字段/列不对应。将使用提供的引用列名。

警告:在元素 [method getOwnerUserBean] 上映射的引用列名称 [OWNER] 与映射引用上的有效 id 或基本字段/列不对应。将使用提供的引用列名。

SQL 创建语句:

create table HOMEFREE."user" (
    userid integer GENERATED ALWAYS AS IDENTITY,
    name varchar(255) not null,
    displayname varchar(255) unique not null,
    password varchar(255) not null,
    tlf integer,
    facebookID varchar(255),
    googleid varchar(255),
    authtoken varchar(255),
    email varchar(255) unique not null,
    primary key(userid)
);

create table HOMEFREE."guardian" (
    guardianId integer GENERATED ALWAYS AS IDENTITY,
    owner integer not null,
    guardian integer not null,
    confirmed boolean not null,
    primary key(guardianId),
    foreign key(owner) references homeFree."user"(userid),
    foreign key(guardian) references homeFree."user"(userid)
);

实体类中的相关字段/注解:

@Entity
@Table(name = "\"user\"", schema = "HOMEFREE")
public class User implements Serializable {
    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private int userId;

    @OneToMany(mappedBy = "ownerUserBean", fetch = FetchType.EAGER)
    private List<Guardian> guardians;
}

@Entity
@Table(name="\"guardian\"", schema="HOMEFREE")
public class Guardian implements Serializable {
    private static final long serialVersionUID = 1L;

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private int guardianId;

    @OneToOne
    @PrimaryKeyJoinColumn(name="OWNER", referencedColumnName="USERID")
    private User ownerUserBean;

    @OneToOne
    @PrimaryKeyJoinColumn(name="GUARDIAN", referencedColumnName="USERID")
    private User guardianUserBean;

    private boolean confirmed;  
}

【问题讨论】:

    标签: java jpa eclipselink glassfish-4


    【解决方案1】:

    尝试使用@JoinColumn 而不是@PrimaryKeyJoinColumn

    @OneToOne
    @JoinColumn(name="OWNER", referencedColumnName="USERID")
    private User ownerUserBean;
    
    @OneToOne
    @JoinColumn(name="GUARDIAN", referencedColumnName="USERID")
    private User guardianUserBean;
    

    根据规范,后者应该用于将JOINED映射策略中实体子类的主表连接到其超类的主表(确切定义可用here

    【讨论】:

    • 这删除了最初的警告。服务器仍然抛出 500 的 HTTP 状态。在日志文件中仍然没有错误的迹象。
    • 好吧,那么我想您的应用程序或服务器本身还有其他问题。您是否能够访问应用程序的某些部分,或者它甚至没有成功部署?
    • 我想我找到了问题所在。只有拥有监护人的用户才会导致服务器崩溃。这会导致无限递归,因为监护人列表保留在监护人对象本身的所有者值中。我需要找到一种方法在不保留监护人列表的情况下将用户保留在 Guardian 中。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-01-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多