当我使用merge时,我希望hibernate将非空值复制到持久化实体并更新数据库。因此,在下面的use-case中,我预计合并将使lastName
保持值Last_0
并将firstName
更改为值First_1
。
但实际上,hibernate只是更新,这意味着lastName
在代码执行后变为null
@Transactional
public void create() {
SomeEntity create = new SomeEntity();
create.setFirstName("First_0");
create.setLastName("Last_0");
this.getSession().save(create);
//now in the database id:1, firstName:First_0, lastName:Last_0
}
@Transactional
public void merge() {
SomeEntity merge = new SomeEntity();
merge.setId(1);
merge.setFirstName("First_1");
this.getSession().merge(merge);
// now in the database id:1, firstName:First_1, lastName:null
}
create();
merge();
我希望lastName
具有Last_0
的值,因为它正在合并。但它是空的。
谢谢
分析解答
您对Hibernate的merge()
在实践中的实现方式感到困惑。在这种情况下,merge()
通过SQL UPDATE
在引擎盖下实现,意思如下:
UPDATE some_entity
SET
firstName = 'First_1',
lastName = NULL
WHERE
id = 1;
也就是说,它将覆盖所有分区实体碰巧拥有的所有字段值。请注意,如果不存在具有此主键id=1
的记录,那么Hibernate将完成INSERT
,而不是更新。
如果你想从实体的原始值开始,那么你应该使用get:
SomeEntity merge = (SomeEntity) this.getSession().get(SomeEntity.class, 1);
merge.setFirstName("First_1");
this.getSession().merge(merge);
现在原始值将是"stick,",除了第一个名称,它被覆盖到其他名称。