2013-08-22 30 views
0

我想更新一个事务内的实体,首先我选择使用它的主键的实体,然后懒惰地加载它的子实体并通过setter方法对其属性进行更改。之后,当我合并父对象,自动其所有的子对象与OneToMany关系得到更新。虽然这是必需的功能,但我对这种行为有点困惑,因为我没有为子实体指定任何级联选项。为了确保,我甚至尝试了一个非关系表,只是使用查找JPAQL来查询并更改了它的属性。当主实体合并操作之后提交事务时,此非关系实体也会与其他人一起更新。我不确定这是正确的行为,还是它理解JPA和交易内合并操作的问题。JPA被管实体合并操作没有级联选项

我父类

class Student 
@Id 
@GeneratedValue(strategy = GenerationType.IDENTITY) 
@Basic(optional = false) 
@Column(name = "id", nullable = false) 
private Integer id; 

private String name; 
@OneToMany(mappedBy = "student") 
private List<Subjects> subjects; 

public Integer getId(){ 
return id; 
} 
public void setId(Integer id){ 
this.id=id; 
} 
public String getName(){ 
return name; 
} 
public void setName(String name){ 
this.name=name; 
} 

我的孩子类

Class Subjects 

@Id 
@GeneratedValue(strategy = GenerationType.IDENTITY) 
@Basic(optional = false) 
@Column(name = "id", nullable = false) 
private Integer id; 

@JoinColumn(name = "student", referencedColumnName = "id", nullable = false) 
@ManyToOne(optional = false) 
private Student student; 

public Integer getId(){ 
return id; 
} 
public void setId(Integer id){ 
this.id=id; 
} 

public String getCourse(){ 
return course; 
} 
public void setCourse(String course){ 
this.course=course; 
} 

非关联实体仅仅是没有这个选择的实体类的任何关系的实体类。我添加它来检查更新是否由于实体类中指定的任何关系而发生(即使没有级联选项)。

我的交易更新功能。

Object obj1 = this.transactionTemplate.execute(new TransactionCallback() { 
public Object doInTransaction(TransactionStatus status) { 

Category category=findById('2'); //Non-Related entity with Student or Subject 
category.setName('new category'); 

Student student=findStudentById(1); 
for(Subjects subjects:student.getSubjects()){ 
subjects.setCourse("test"); 
} 
student.setName("student1"); 
entityManager.merge(student); 

    return true; 
    } 
}); 

所以合并和事务提交后的最终结果是,所有表(学生,主题和类别)更新。

+0

发布代码而不是描述它。并定义一个非关系表是什么。 –

+0

@JBNizet,感谢您的回复,我还添加了相关代码。 – Krishna

回答

1

好的,所以你很惊讶,对实体所做的更改仍然存在,甚至不需要调用merge()或任何其他方法。这些是JPA/Hibernate和附属实体的主要观点之一:你修改它们,并且由于它们附加到持久性上下文,所有这些更改都在需要时透明地持久化(至多,在交易)。

merge()用于将分离实体的状态复制到附加实体的状态。

阅读this part of the documentation了解更多详情。

+0

谢谢你已经清除了我的疑惑。所以,即使我没有为父实体类调用合并,当事务被提交时,对实体类所做的所有更改都会持久保存到数据库中。 – Krishna

+0

是的,你知道了。一旦实体管理器关闭(通常在事务结束时发生),这些实体就会分离,并且对这些实体所做的更改不会再透明地持续下去。 –

+0

@JBNizet请问你对这个问题的帮助[链接](http://stackoverflow.com/questions/21550585/properly-modify-object-with-manytoone-relationship-in-spring-mvc-hibernate-ap )。我一直在阅读类似问题上的许多答案,但无法自行找到答案。 –