Spring Data JPA:一对一实例化问题:PersistentObjectException:分离实体传递给持久化
Posted
技术标签:
【中文标题】Spring Data JPA:一对一实例化问题:PersistentObjectException:分离实体传递给持久化【英文标题】:Spring Data JPA: one-to-one instantiation problem: PersistentObjectException: detached entity passed to persist 【发布时间】:2019-12-10 10:50:13 【问题描述】:我正在编写一个简单的 Order-Payment 一对一关联:
订单类相关代码:
@Entity
public class Order implements Serializable
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
(...)
@OneToOne(cascade=CascadeType.ALL, mappedBy="order")
private Payment payment;
支付类相关代码:
@Entity
public class Payment implements Serializable
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private Long id;
@OneToOne
@MapsId
private Order order;
然后我想实现一个基本方法来使用 Spring Data JPA 存储库为我的测试数据库播种,但如果我尝试以下代码,我会得到一个 PersistentObjectException
说 detached entity passed to persist
:
Order o1 = new Order(null, Instant.parse("2019-06-20T19:53:07Z"));
orderRepository.save(o1);
Payment p1 = new Payment(null, Instant.parse("2019-06-23T13:02:55Z"), o1);
paymentRepository.save(p1);
如果我尝试这种方式也会出现同样的问题:
Order o1 = new Order(null, Instant.parse("2019-06-20T19:53:07Z"));
Payment p1 = new Payment(null, Instant.parse("2019-06-23T13:02:55Z"), o1);
orderRepository.save(o1);
paymentRepository.save(p1);
它的唯一工作方式如下:
Order o1 = new Order(null, Instant.parse("2019-06-20T19:53:07Z"));
Payment p1 = new Payment(null, Instant.parse("2019-06-23T13:02:55Z"), o1);
o1.setPayment(p1);
orderRepository.save(o1);
paymentRepository.save(p1);
我想了解为什么只有最后一种方法有效。在多对一关联中,我不必在保存之前设置双向关联即可工作。在这种情况下,我对分离实体的行为缺少什么?谢谢。
【问题讨论】:
【参考方案1】:试试这个,
Order o1 = new Order(null, Instant.parse("2019-06-20T19:53:07Z"));
Payment p1 = new Payment(null, Instant.parse("2019-06-23T13:02:55Z"), o1);
o1.setPayment(p1);
orderRepository.save(o1);
付款不需要保存方法。因为您使用了@OneToOne(cascade=CascadeType.ALL, mappedBy="order")
之类的级联类型,所以每当您保存订单时,付款也会保存。
【讨论】:
【参考方案2】:因为我们必须像您使用的那样为父实体设置子实体
o1.setPayment(p1);
不需要将 id 传递为 null,因为它将是 @GeneratedValue
。您可能需要为它们创建一个合适的构造函数。
当您使用cascade=CascadeType.ALL
时,您可以保存父母和孩子
如下 两个实体都不需要使用 save()
//save Parent-Child at same
@PostMapping(value = "/onetoone")
public String OneToOne(@RequestBody ParentOne parent)
ChildOne childOne = parent.getChildOne();
childOne.setParentOne(parent);
parent.setChildOne(childOne);
parentOneRepository.save(parent);
return "saved";
/*
"parentName":"Parent Name",
"childOne":
"childName":"Child Name"
*/
Discussion
【讨论】:
以上是关于Spring Data JPA:一对一实例化问题:PersistentObjectException:分离实体传递给持久化的主要内容,如果未能解决你的问题,请参考以下文章
Spring-Data-Jpa 中一对多映射的 JSON 结果错误
Spring Data JPA - 防止一对一关系的双重表单提交