JPA 中的深度拷贝

2022-09-03 15:09:32

我想在JPA中制作一个实体的深度副本。我在这里发现了一个有趣的讨论:http://forums.java.net/jive/thread.jspa?messageID=253092&tstart=0

听起来,所提出的解决方案是将所有@Id设置为零。这是我的基本代码:


//Start a JPA session.
EntityManager em= emf.createEntityManager();
em.getTransaction().begin();

//Get the object I want to copy.
MyClass myObject=em.find(MyClass.class,id);

//Use reflection to find @Id's and set them to zero for all @OneToMany and @OneToOne relations.
//TODO:  write the ugly recursive code to do this.

//Hoping this will create a deep copy.
em.merge(myObject);

//Close the session.
em.getTransaction().commit();
em.close();

这是一个好的策略吗?有没有人已经编写了这个TODO代码,他们可以分享???

谢谢!


答案 1

我解决了这个问题。

我创建了一个组件,它根据包的注释为您制作了整个过程()。javax.persistence

组件已将实体的 id 设置为 null。他根据每个属性关系的类型对要应用的算法进行所有分析,或者。@OneToMany@OneToOne@ManyToMany

Person person = personDAO.find(1);
PersistenceCloner cloner = new PersistenceCloner(person); 
Person personCopy = cloner.generateCopyToPersist();

下载JAR 和 SOURCE: jpa-entitycloner


答案 2

我不太确定将已托管对象的 ID 归零是否是一个好主意,特别是当您的实体没有定义为 ID 相等时。JPA 实现可能已将托管对象放在某个缓存中,并且在使用其中对象的 ID 时会变得 beserk。equals()

我相信遵循R.K.的答案并真正复制对象会更安全。


推荐