Grails 3.2.10,Gorm 6.1.4,Hibernate 5.2.9
我有一个grails域对象和一个执行基本crud操作的相应控制器(它不是脚手架)。将Command对象提交给控制器的更新方法时,控制器按预期执行(所有日志消息都按照应用的方式打印)并且不会抛出任何错误。显示重定向页面就像您期望显示的Flash消息一样(即使使用更新的数据)。但是,数据库值实际上不会更新。我可以创建对象,它只会用于更新。
答案 0 :(得分:1)
在经历了很多挫折之后,似乎最新的Gorm或Hibernate正在监视域对象上的setXXX
方法,如果这些方法没有被调用,那么hibernate将不会看到对象被修改并且不会更新任何变化。调高日志级别帮助我看到hibernate没有看到对象被修改,因此无视它。
我的问题集中在调用setData(CommandObject)
的域对象中有this.xxx = CommandObject.xxx;
个方法,因此通过生成的setter并导致hibernate认为对象没有被修改。
直接从控制器调用setter是解决此问题的方法。
示例(不起作用):
class Person {
String name
//...typical constraints, methods, etc...
void setData(PersonCommand c){
this.name = c.name;
}
}
class PersonController {
//...typical list, show, create methods...
def update(PersonCommand pc){
//... validation ...
Person p = Person.get(pc.personId);
p.setData(pc);
p.save(failOnError: true);
flash.message = "Successfully saved person ${p.name}"
redirect(action: 'show', id: p.id)
}
}
固定示例(可行):
class Person {
String name
//...typical constraints, methods, etc...
}
class PersonController {
//...typical list, show, create methods...
def update(PersonCommand pc){
//... validation ...
Person p = Person.get(pc.personId);
p.name = pc.name;
//... set other fields ...
p.save(failOnError: true);
flash.message = "Successfully saved person ${p.name}"
redirect(action: 'show', id: p.id)
}
}
答案 1 :(得分:0)
这是一个众所周知的域类问题。你必须在其他域类的方法中明确地调用setter或getter:
class Person {
String name
void setData(PersonCommand c){
setName c.name
}
}
此外,我将setData()
重命名为applyData()
,以避免与POGO方法发生冲突