Grails:仅当所有组件都通过验证时才将父级和子级保存到数据库的方法

Grails:仅当所有组件都通过验证时才将父级和子级保存到数据库的方法,grails,gorm,Grails,Gorm,我有一个只有在子对象有效时才能创建的父对象。子项只能在保存后按id引用父项(因为id是自动递增的)。因此,我保存父对象,然后将父对象分配给要保存的子对象。 如果一个子项保存失败,如何回滚所有父项保存和任何子项保存 (这发生在服务层中) 如果在事务服务中抛出未捕获的异常,事务将回滚所有内容。大概是这样的: package com.example class MyService { static transactional = true void myMethod() {

我有一个只有在子对象有效时才能创建的父对象。子项只能在保存后按id引用父项(因为id是自动递增的)。因此,我保存父对象,然后将父对象分配给要保存的子对象。 如果一个子项保存失败,如何回滚所有父项保存和任何子项保存

(这发生在服务层中)


如果在事务服务中抛出未捕获的异常,事务将回滚所有内容。大概是这样的:

package com.example

class MyService {

    static transactional = true

    void myMethod() {
      parent.save(flush:true)
      children.each{child->
        child.parent = parent
        if(!child.save(flush:true)){
          throw new RuntimeException('Rollback')
       }
     }
    }
}

就我个人而言,我不会在生产代码中使用
RuntimeException
。在这种情况下,我会创建自己的异常并避免填写stacktrace。但是,例如,上面演示了您希望执行的操作。

确保上述代码位于服务的事务方法中,并引发未处理的异常。这将导致事务回滚方法中完成的所有保存。非常感谢。普通异常还是RuntimeException?没关系,任何未捕获的异常都可以。您不应该仅仅为了回滚事务而抛出异常。改为使用transaction.setRollbackOnly()。说明:
package com.example

class MyService {

    static transactional = true

    void myMethod() {
      parent.save(flush:true)
      children.each{child->
        child.parent = parent
        if(!child.save(flush:true)){
          throw new RuntimeException('Rollback')
       }
     }
    }
}