【发布时间】:2013-02-14 00:19:44
【问题描述】:
我们正在尝试在 Spring 3.2 中实现一个特殊的部分更新功能。我们使用 Spring 作为后端,并有一个简单的 Javascript 前端。我一直无法找到满足我们要求的直接解决方案,即 update() 函数应该接受任意数量的 field:values 并相应地更新持久性模型。
我们对所有字段进行内联编辑,因此当用户编辑字段并确认时,id 和修改后的字段会以 json 格式传递给控制器。控制器应该能够从客户端接收任意数量的字段(1 到 n)并仅更新这些字段。
例如,当 id==1 的用户编辑他的 displayName 时,发布到服务器的数据如下所示:
{"id":"1", "displayName":"jim"}
目前,我们在 UserController 中有一个不完整的解决方案,如下所述:
@RequestMapping(value = "/{id}", method = RequestMethod.POST )
public @ResponseBody ResponseEntity<User> update(@RequestBody User updateUser) {
dbUser = userRepository.findOne(updateUser.getId());
customObjectMerger(updateUser, dbUser);
userRepository.saveAndFlush(updateUuser);
...
}
这里的代码有效,但有一些问题:@RequestBody 创建一个新的updateUser,填写id 和displayName。 CustomObjectMerger 将此 updateUser 与数据库中对应的 dbUser 合并,更新 updateUser 中包含的唯一字段。
问题在于 Spring 使用默认值和其他自动生成的字段值填充 updateUser 中的某些字段,这些字段在合并时会覆盖 dbUser 中的有效数据。明确声明它应该忽略这些字段不是一种选择,因为我们希望我们的 update 也能够设置这些字段。
我正在寻找某种方法让 Spring 仅将显式发送到 update() 函数的信息自动合并到 dbUser 中(不重置默认/自动字段值)。有什么简单的方法吗?
更新:我已经考虑过以下选项,它几乎可以满足我的要求,但并不完全。问题是它以@RequestParam 的形式获取更新数据,并且(AFAIK)不执行 JSON 字符串:
//load the existing user into the model for injecting into the update function
@ModelAttribute("user")
public User addUser(@RequestParam(required=false) Long id){
if (id != null) return userRepository.findOne(id);
return null;
}
....
//method declaration for using @MethodAttribute to pre-populate the template object
@RequestMapping(value = "/{id}", method = RequestMethod.POST )
public @ResponseBody ResponseEntity<User> update(@ModelAttribute("user") User updateUser){
....
}
我已经考虑重写我的customObjectMerger() 以更适合使用 JSON,计算并让它仅考虑来自HttpServletRequest 的字段。但是,当 spring 提供 几乎正是我正在寻找的东西,减去缺少的 JSON 功能时,即使必须首先使用 customObjectMerger() 也会让人觉得很麻烦。如果有人知道如何让 Spring 做到这一点,我将不胜感激!
【问题讨论】:
-
@SamEsla - 你有没有找到更好的解决方案,特别是在有嵌套对象的情况下?我有同样的问题,在阅读这篇文章之前,做了一些和你类似的事情。如果你有时间请看:stackoverflow.com/questions/16473727/…
标签: java spring spring-mvc