Pumpinglemma
Pumpinglemma

Reputation: 113

Modeling a many-to-one tree in grails

I'm attempting to model an organizational tree in grails. What I have works, but I have a couple of questions about it.

Here's my 'Organization' class:

class Organization {

  String title
  Organization parentOrg

  static hasMany = [ childOrg: Organization ]

  static mappedBy = [ 
    childOrg: 'parentOrg',
    parentOrg: 'childOrg'
  ]

  static constraints = {
    parentOrg nullable: true
  }
}

Now, when I create a new 'Organization' like this:

def newOrg = new Organization(
    title: 'New Organization',
    parentOrg: oldOrg).save()

Everything works well, and the relationship to the parent seems modeled correctly.

But if I try to call something like oldOrg.childOrg.each I will get no results unless I have also called oldOrg.addToChildOrg(newOrg).

Furthermore, when I check the tables that are generated, the only reference to this relation is the parent_org_id column on the Organization table.

Now, I realize that this is all that is necessary to also determine the childOrg relations, but I don't notice ANY change in the database from before I call oldOrg.addToChildOrg(newOrg) to after!

So where is this relation getting stored when I call addToChildOrg when I don't see anything change in the database?

Also, how can I have this relation setup to automatically create the childOrg relation when I add the parentOrg? I don't think I should have to call addToChildOrg when I'm adding the parentOrg. It should be implied.

Thanks!

Upvotes: 2

Views: 111

Answers (2)

Chetan
Chetan

Reputation: 1707

Use a hasOne association to store the foreign key reference in a bidirectional one-to-one.

Since you don't want to add the relationship from other side each time so you can make a setter to ease your work, like-

setParentOrg(parentInstance){
   this.parentOrg = parentInstance
   parentInstance.childOrg = this
}

Now when you do organisationInstance.parentOrg = parentInstance, the setter gets invoked for you, and the relationship is setup the way you want.

Upvotes: 2

hoppo
hoppo

Reputation: 13

if I'm correct you're missing belongsTo definition, because you need to define that every instance of Organization is owned by its parentOrg instance.

try this class declaration:

class Organization {

  String title
  Organization parentOrg

  static belongsTo = [parentOrg: Organization]
  static hasMany = [ childOrg: Organization ]
  static mappedBy = [ childOrg: 'parentOrg']

  static constraints = {
    parentOrg nullable: true
  }
}

Upvotes: 0

Related Questions