【发布时间】:2011-11-30 00:53:25
【问题描述】:
我有一个实体 Task 和一个用于它的 dao:TaskDao。 Task 实体具有到 Category 的 ManyToOne 映射。当我删除一个任务时,我还需要从类别中的集合中删除该任务:
// remove() method in TaskDao
public void remove (Task p_task) {
// p_task is Detached, p_task.getCategory() is Detached
p_task = em.merge(p_task);
// p_task is Attached, p_task.getCategory() is Attached
em.remove(p_task);
// p_task is Detached, p_task.getCategory() is Attached
p_task.getCategory().removeTask(p_task);
}
cmets 指示(此时)p_task 和/或 p_task.category 是否已附加/分离。首先让我解释一下为什么我选择这种陈述顺序。首先,我需要合并 p_task,以便附加 p_task.category,并且为了删除它需要合并的 p_task。 p_task 会在最后从类别集合中移除,因为 em.remove(p_task) 会抛出一个 ConstraintException,在这种情况下不应将任务从类别集合中移除。
这是正确的方法吗?另外,我很惊讶在 em.remove(p_task) 之后,p_task.category 仍然附加。
编辑:我应该给出一些实体类的代码。
public class Task implements Serializable {
@JoinColumn(name = "category_id", referencedColumnName = "id")
@ManyToOne(cascade = CascadeType.MERGE, optional = false)
private Category category;
}
public class Category implements Serializable {
@OneToMany(cascade = CascadeType.MERGE, mappedBy = "category")
private List<Task> taskCollection;
public void addTask (Task p_task) {
if (taskCollection == null) {
taskCollection = new ArrayList<>();
}
if (!taskCollection.contains(p_task)) {
taskCollection.add(p_task);
}
}
public void removeTask (Task p_task) {
taskCollection.remove(p_task);
}
}
在下面的代码中,p_task 被从 category.taskCollection 中移除,同时事务被回滚:
// remove() method in TaskDao
public void remove (Task p_task) {
p_task = em.merge(p_task);
p_task.getCategory().removeTask(p_task); // will not be rolled back if em.remove(p_task) throws an exception
em.remove(p_task);
}
【问题讨论】: