我有双向 OneToOne 关联
Account <-> Budget
。
根据this,我尝试延迟加载关联:
对于
Account.java
:
@Audited
@Entity
public class Account {
@Id
@GeneratedValue(strategy = GenerationType.TABLE)
protected long id;
@OneToOne(mappedBy = "account", cascade = CascadeType.ALL, orphanRemoval=true, fetch=FetchType.LAZY)
private Budget mainBudget;
}
...
}
对于
Budget.java
:
@Audited
@Entity
public class Budget {
@Id
@GeneratedValue(strategy = GenerationType.TABLE)
protected long id;
@OneToOne(fetch=FetchType.LAZY)
@MapsId
private Account account;
@OneToMany(targetEntity = Budget.class, cascade = CascadeType.ALL,
mappedBy = "parentBudget", orphanRemoval=true)
@Fetch(value = FetchMode.SUBSELECT)
private List<Budget> subBudget;
...
}
现在我正在尝试使用 DAOClass 中的
create
-方法创建一个新预算的新帐户,如下所示:
@Resource(name = "DBRouter", type = DatabaseRouter.class)
protected DatabaseRouter router;
@PersistenceContext
protected EntityManager em;
@Transactional
public D create(D d, boolean flush, String resource) {
router.setDataSource(resource);
if (flush) {
em.flush();
}
D obj = em.merge(d);
if (flush) {
em.flush();
}
return obj;
}
这给了我以下例外:
javax.persistence.EntityExistsException: A different object with the same identifier value was already associated with the session : [[PACKACKENAMES].Account#50](31 internal lines)
at org.apache.openejb.persistence.JtaEntityManager.merge(JtaEntityManager.java:203)
at [PACKACKENAMES].DAOClass.create(DaoClass.java:75)
at [PACKACKENAMES].DaoClass.create(DaoClass.java:66)
...
如果我删除
@MapsId
注释,那么我就没有这个问题,尽管延迟加载无法正常工作。这个异常是什么原因,如何解决?
在您的案例中,Account 是 Budget 的父实体。 @MapsId 注释表示 JPA 使用父实体的 id 来映射带注释的一对一关系。关联实体(行)的两个 ID 将相同。无需为预算生成单独的 ID。正如我们从异常中看到的那样,它甚至无法工作。
解决方案 - 从预算实体中删除@GeneratedValue 注释。
public class Budget {
@Id
private long id;
@OneToOne(fetch=FetchType.LAZY)
@MapsId
private Account account;
...
}