当实体与主键之间存在关联时,必须先手动分配此类的ID,然后再调用save()

时间:2014-07-11 12:19:03

标签: hibernate nhibernate-mapping

我有2个实体,我希望在这两个实体之间创建一个关系,以便共享它们的主键。当我们提交一个实体时,另一个实体也应该使用为第一个实体生成的相同主键提交。

我的第一个实体是用户

    @Entity
@Table(name = "ENDUSER")
public class User extends LongIdBase implements IActivatable, IUser {
    @Column(name = "first_name")
    private String firstName;
    @Column(name = "last_name")
    private String lastName;
     @OneToOne(cascade = { CascadeType.ALL }, fetch = FetchType.LAZY, targetEntity = UserLoginRecord.class)
    @PrimaryKeyJoinColumn(name = "id")
    private UserLoginRecord userLoginRecord;

我的第二个实体是UserLoginrecord

   @Entity
@Table(name = "ENDUSER_TEMP")
public class UserLoginRecord {
    @Id
    @Column(name = "id")
    private Long id;

    public Long getId() {
        return id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    @Column(name = "name")
    private String name;

我希望当我持久保存用户时,也应该创建UserLoginRecord的新行,其中包含与User相同的主行。

但是在尝试坚持时,我收到以下错误。

ids for this class must be manually assigned before calling save():

2 个答案:

答案 0 :(得分:3)

  1. 您会收到该错误,因为除非指定标识符生成器,​​否则"已分配"将假设发电机。分配的标识符要求您手动设置ID,因此我认为您有兴趣自动生成ID。

    尝试将其更改为:

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;
    
  2. 用户应该是user / userLoginRecord关联的所有者,所以:

    @Entity
    @Table(name = "ENDUSER")
    public class User extends LongIdBase implements IActivatable, IUser {
    
        @Id
        @GeneratedValue(strategy = GenerationType.IDENTITY)
        @Column(name = "id")
        private Long id;
    
        public Long getId() {
            return id;
        }
    
        public void setId(Long id) {
            this.id = id;
        }
    
        @Column(name = "first_name")
        private String firstName;
    
        @Column(name = "last_name")
        private String lastName;
    
    }
    
  3. 我认为用户可以拥有更多UserLoginRecords,这意味着用户将与UserLoginRecord建立一对多关联,而UserLoginRecord将与用户建立多对一关联。

    < / LI>
  4. 假设您在User和UserLoginRecord之间存在一对一的关系

    UserLoginRecord看起来像:

    @Entity
    @Table(name = "ENDUSER_TEMP")
    public class UserLoginRecord {
    
        @Id 
        @Column(name="userId", unique=true, nullable=false)
        private Long userId;
    
        @OneToOne(cascade = CascadeType.ALL)
        @JoinColumn(name="userId")
        @MapsId
        private User user;
    
  5. 对于双向一对一关联,用户还可以包含:

        @OneToOne(mappedBy = "user")
        private UserLoginRecord userLoginRecord;
    

    如果您要进行双向关联,请不要在保存之前忘记设置双方:

        user.setUserLoginRecord(userLoginRecord);
        userLoginRecord.setUser(user);
    

    即使userLoginRecord.user端是此关联的所有者,user.userLoginRecord也是&#34;反向&#34;侧。

答案 1 :(得分:0)

2021 JPA 答案:第 4.2 段 here 对此进行了清晰而简单的解释