【发布时间】:2022-06-13 14:53:46
【问题描述】:
我正在使用弹簧数据 jpa。 当我想克隆一个具有一对多关系的实体时,
fun clonePurchaseOrder(purchaseOrder: PurchaseOrder, operator: String): PurchaseOrder {
//prepare data
val items = purchaseOrder.items
//detach
items.forEach { entityManager.detach(it) }
purchaseOrder.costRevise?.let { entityManager.detach(it) }
entityManager.detach(purchaseOrder)
purchaseOrder.id = null
//modify
items.forEach {
it.id = null
it.purchaseOrder = purchaseOrder
}
//modify purchaseOrder
val now = Date()
return purchaseOrder.apply {
number = null
costRevise = null
paymentHistories = mutableListOf()
status = PurchaseOrder.Status.DRAFT
createTime = now
creator = operator
modifyTime = now
submitTime = null
submitOperator = null
closeOperator = null
closeReason = null
closeTime = null
}.save()
}
我设置purchaseOrder id =null,每件商品id = null,但是得到以下异常
org.springframework.orm.jpa.JpaSystemException: Don't change the reference to a collection with delete-orphan enabled : com.hkmci.web.bms2.backend.database.entity.PurchaseOrder.items; nested exception is org.hibernate.HibernateException: Don't change the reference to a collection with delete-orphan enabled : com.hkmci.web.bms2.backend.database.entity.PurchaseOrder.items
这里是 purchaseOrder 实体和 items 实体
@Entity
class PurchaseOrder(
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
var id: Long? = null,
...(other Column)
@OneToMany(mappedBy = "purchaseOrder", cascade = [CascadeType.ALL], orphanRemoval = true)
var items: MutableList<PurchaseOrderItem> = mutableListOf(),
...(other Column)
@Entity
class PurchaseOrderItem(
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
var id: Long? = null,
@ManyToOne(fetch = FetchType.LAZY)
var purchaseOrder: PurchaseOrder,
...(other column)
有人可以帮忙吗?
【问题讨论】:
-
您没有克隆项目。您应该为每个对象创建新实例并将字段设置为原始值(ID 除外)
-
但是我的物品是先一个一个分离,然后设置id=null,再设置purchaseOrder指向没有id的新的。我还看到了 purchaseOrder 和 items 的控制台打印插入查询。
-
在我的项目中,还有其他地方使用了这种方法并且克隆成功。代码逻辑看起来一样,但只有一个区别:父实体主键是String,是从头开始生成的,而不是设置为null。这是根本案例吗?