How do I clear and replace a collection in a one-to-many relationship in Grails/Groovy

醉酒当歌 提交于 2019-12-03 11:45:55

Clearing Collection approach didn't worked for me:

activePerson.locations.clear()

Just try iterate over collection with avoiding ConcurrentModificationException by calling collect():

activePerson.locations.collect().each {
    item.removeFromLocations(it)
}

And after that save the entity to execute SQL statement:

activePerson.save flush:true

Link to article to read more: http://spring.io/blog/2010/07/02/gorm-gotchas-part-2/

For #1 you can clear the collection (it's a Set by default):

activePerson.locations.clear()

For #2 use addToLocations:

activePerson.addToLocations(location)

and when you save the person the location<->person relationship will be updated.

While this is an older question, I ran into a very similar situation in which I wanted to update a set of child records. Here's how I chose to resolve it. For simplicity, I'll use the same object/relation names as the asker of the question.

  1. In the mapping block of the parent domain, add:

    static mapping = {
        locations(cascade: "all-delete-orphan")
    }
    
  2. In the child domain, add the @EqualsAndHashCode annotation (just in case there's another one lurking about, I'm referring to groovy.transform.EqualsAndHashCode).

  3. Add all of the children elements to the parent domain using the Grails addTo methods (e.g. addToLocations) and then save the parent domain.

While this approach does require saving the parent domain (which the asker didn't want to do), it seems like it's the most appropriate approach given the clear belongsTo definition in the model. I would therefore answer the asker's numbered questions like this:

  1. Rather than doing it manually, let Grails/Hibernate clear the records by specifying the all-delete-oprhan cascade behavior on the relation.

  2. Don't attempt to save the child records directly, but instead save the parent object to match what Grails seems to expect.

Here's what works for me:

activePerson.locations.clear()
activePerson.properties = params

...

activePerson.save()

This clears the set of locations, then adds back just the ones currently selected in params.

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!