Java 更新Hibernate上分离对象的某些字段的最佳方法?

Java 更新Hibernate上分离对象的某些字段的最佳方法?,java,hibernate,orm,Java,Hibernate,Orm,我想知道在Java上使用HB更新被删除对象的某些字段的最佳方法是什么。特别是当对象具有子对象属性时。例如(删除注释并减少字段数量以减少噪音): 在MVC webapp中更新父对象时,我可以使用Session.get(Parent.class,123)调用父对象实例,使用它填充表单并显示它。没有DTO,只是将已删除的父对象传递给视图并绑定到表单。现在,我只想允许用户更新父级的field2属性。因此,当用户发布表单时,我会得到一个id和field2已填充的父实例(我认为mvc框架在这里并不重要,在绑

我想知道在Java上使用HB更新被删除对象的某些字段的最佳方法是什么。特别是当对象具有子对象属性时。例如(删除注释并减少字段数量以减少噪音):

在MVC webapp中更新父对象时,我可以使用Session.get(Parent.class,123)调用父对象实例,使用它填充表单并显示它。没有DTO,只是将已删除的父对象传递给视图并绑定到表单。现在,我只想允许用户更新父级的field2属性。因此,当用户发布表单时,我会得到一个id和field2已填充的父实例(我认为mvc框架在这里并不重要,在绑定时,所有的行为基本相同)。
现在,执行实体更新的最佳策略是什么?我可以考虑几种选择,但我想听听专家的意见:)(记住,我不想失去父母和孩子之间的关系)

A)再次从会话中检索父实例,并手动替换更新的字段

Parent pojoParent; //binded with the data of the Form.
Parent entity = Session.get(Parent.class,pojoParent.getId());
entity.setField2(pojoParent.getField2()).          
我经常用这个。但pojoParent似乎被用作卧底DTO。如果要更新的字段数量变大,情况也会变得糟糕

B)将子项存储在某个位置(httpSession?)并与后者关联

Parent parent = Session.get(Parent.class,123);
//bind the retrieved parent to the form
// store the Child from parent.getChild() on the httpSession
...
//when the users submits the form...
pojoParent.setChild(someHttpSessionContext.getAttribute('Child'))
Session.save(pojoParent);
我认为这是废话,但我在一些项目中看到了

C)将父级和子级之间的关系设置为不可变。在关系上使用updateable=false,我可以更新任何父字段,而不用担心失去子字段。无论如何,这是相当严格的关系,永远不会更新

那么,你认为解决这种情况的最好办法是什么


提前谢谢你

您可以直接修改分离的对象,然后使用会话上的方法将对象重新附加到会话

加载父对象后,您说

现在,我只想允许用户更新父对象的field2属性

根据用例,您可以使用UpdateableParent对象

public class UpdateableParent {

   private String field2;

   // getter's and setter's

}
现在,我们的父存储库

@Repository
public class ParentRepositoryImpl implements ParentRepository {

    @Autowired
    private SessionFactory sessionFactory;


    public void updateSpecificUseCase(UpdateableParent updateableParentObject) {

        Parent parent = sessionFactory.getCurrentSession().load(Parent.class, updateableParentObject.getId());

        try {
            // jakarta commons takes care of copying Updateable Parent object to Parent object

            BeanUtils.copyProperties(parent, updateableParentObject);
        } catch (Exception e) {
            throw new IllegalStateException("Error occured when updating a Parent object", e);
        }

    }

}
它的优点

  • 它是安全的:你只需更新你真正想要的
  • 您不必担心MVC框架(一些MVC框架允许您设置allowedFields属性)。如果您忘记了一些允许的字段,会发生什么情况
虽然这不是一个与技术相关的问题,但框架只允许您更新所需的内容。因此,您不必担心使用什么模式

问候,

A) 从中检索父实例 再次进行会话并手动替换 更新的字段

Parent pojoParent; //binded with the data of the Form.
Parent entity = Session.get(Parent.class,pojoParent.getId());
entity.setField2(pojoParent.getField2()).          
这似乎是我在过去几年中使用的最实用的版本

B) 把孩子放在什么地方 (httpSession?)并将其关联 后者

我建议您不要这样做,特别是如果您希望遵循REST范式,这会使服务器端状态成为一个完全不允许的状态,并且最终会使用堆空间来存放分离的对象,尽管启动会话的用户离开去喝咖啡:)

C) 设置父对象和子对象之间的关系 孩子是不可变的

IMHO这也不是一个好方法,尽管它适合于具有小型持久性模型的小型项目。但是,即使在一个小的应用程序中,当试图修改代码时,也可能导致头痛