Search code examples
hibernategrailsgrails-orm

Grails one-to-many delete without cascade


I'm trying to create a bi-directional many-to-one relationship in Grails with NON-cascading deletes in both directions. My domain looks like:

class Asset {
  static hasMany = [ hosts: Host ]

  static mapping = {
      hosts cascade: 'save-update'
  }
}

class Host {
  Asset asset
}

This works fine when deleting a Host (the Asset remains), but when I try to delete the Asset, I get an integrity constraint error from the DB. I've tried changing the Host class definition to use a belongsTo, but can't get this to work. Any help would be great! Thanks!


Solution

  • I ended up finding a solution by writing my own delete() action for the Asset controller that deletes all the references to the Asset from all hosts before deleting the Asset itself:

    def delete() {
        def assetInstance = Asset.get(params.id)        
        assetInstance.hosts.each { theHost ->
            theHost.asset = null
            theHost.save()
        }
        if(!assetInstance.hasErrors() && assetInstance.delete()) {
            redirect(action: "list")
        }
        else {
            redirect(url: "/asset/show?id=${assetInstance.id}")
        }
    }
    

    This eliminates the error and also prevents children (Hosts) from being deleted when the parent (Asset) is deleted.