You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot JPA一对一共享主键需手动赋值问题及优化诉求

Spring Boot + JPA 共享主键配置及关联优化问题

初始问题:共享主键需手动设置ID的困扰

我使用Spring Boot和JPA创建两张共享同一主键的表,实体代码如下:

UserAccount 实体

public class UserAccount implements Serializable
 {
   @Id
   @GeneratedValue(strategy = GenerationType.IDENTITY)
   private Long id;
   @OneToOne(mappedBy ="user", cascade = {CascadeType.REMOVE, CascadeType.MERGE, 
                                         CascadeType.REFRESH}, fetch=FetchType.LAZY)
   @PrimaryKeyJoinColumn
   private UserLogin login;
 }  

UserLogin 实体

public class UserLogin implements Serializable
  {
    @Id
    private Long user_id;
    @OneToOne(cascade = {CascadeType.MERGE, CascadeType.REFRESH}, 
               fetch=FetchType.LAZY)
   @MapsId("user_id")
   @JoinColumn(name = "user_id", referencedColumnName = "id")
   @Setter(AccessLevel.NONE)
   private UserAccount user;
   public void setUser(UserAccount user)
    {
     this.user = user;
     this.user_id = user.getId();    
    }
  }

目前代码能正常运行,是因为我在setUser方法里手动通过this.user_id = user.getId();设置了UserLogin的ID。如果不这么做,就会抛出错误:

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

我知道可以手动管理ID,但找不到正确的配置方式来替代这种手动赋值的写法。


更新:移除关联时的findById调用

现在我已经解决了共享主键的配置问题,接下来希望优化服务层代码,移除设置用户登录信息时的findById()调用。当前服务代码如下:

// 这些方法定义在专门的@Service类中
@Transactional
public void createLoginInfo(UserAccount user)
{
 UserLogin userlogin=new UserLogin();       
 this.addLoginToUser(userlogin,user);
 loginService.save(userlogin);
}

@Transactional
public void addLoginToUser(UserLogin login, UserAccount account)
{
  // 打开这行注释代码才能正常运行
  //UserAccount acc= this.findById(account.getId());   
  login.setUser(account);      
  account.setLogin(login);
}

// 在事务测试方法中,我先创建用户再调用以下代码
userService.save(theuser);
userService.createLoginInfo(theuser);

内容的提问来源于stack exchange,提问作者Discipulos

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 23:10:53