tags:

views:

83

answers:

2

Hi, is there a special way with gorm to map a three domain classes relationship like this:

1 person belongs to N companies with M given roles (one or more roles for a given company)

Thanks in advance.

+1  A: 

look at http://www.grails.org/Many-to-Many+Mapping+without+Hibernate+XML (i think it's up to date).

be aware of: http://codedumpblog.blogspot.com/2010/02/grails-many-to-many-with-lists.html

the code below works for me using grails 1.2.0. but it seems like i had to do a lot of save()'s. don't forget to make the controllers and set scaffold=domain_class

package p

class Company {
    String toString() { "$name"
    }
    static hasMany=[roles:Role]
    static constraints = {
    }
    String name
}

package p

class Role {
    String toString() { "$name"
    }
    static belongsTo=[company:Company]
    static hasMany=[personRoleAssociations:PersonRoleAssociation]
    static constraints = {
    }
    String name
}

package p

class Person {
    String toString() { "$name"
    }
    static hasMany=[personRoleAssociations:PersonRoleAssociation]
    static constraints = {
    }
    String name
}

package p

class PersonRoleAssociation {
    String toString() { "${person.name} as ${role.name}"
    }
        static belongsTo=[person:Person,role:Role]
    static constraints = {
    }
}


import p.*
class BootStrap {

    def init = { servletContext ->
        Person dick=new Person(name:'dick')
        Person jane=new Person(name:'jane')
        dick.save()
        jane.save()
        Company ibm=new Company(name:'ibm')
        ibm.save()
        Role ibmManager=new Role(name:'ibmmanager')
        Role ibmPeon=new Role(name:'ibmpeon')
        ibm.addToRoles(ibmManager)
        ibmManager.save()
        ibm.addToRoles(ibmPeon)
        ibmPeon.save()
        ibm.save()
        Company sun=new Company(name:'sun')
        sun.save()
        Role sunManager=new Role(name:'sunmanager')
        Role sunPeon=new Role(name:'sunpeon')
        sun.addToRoles(sunManager)
        sunManager.save()
        sun.addToRoles(sunPeon)
        sunPeon.save()
        sun.save()
        PersonRoleAssociation dickManager=new PersonRoleAssociation()
        dick.addToPersonRoleAssociations(dickManager)
        ibmManager.addToPersonRoleAssociations(dickManager)
        PersonRoleAssociation dickPeon=new PersonRoleAssociation()
        dick.addToPersonRoleAssociations(dickPeon)
        sunPeon.addToPersonRoleAssociations(dickPeon)
        PersonRoleAssociation janeManager=new PersonRoleAssociation()
        jane.addToPersonRoleAssociations(janeManager)
        sunManager.addToPersonRoleAssociations(janeManager)
        PersonRoleAssociation janePeon=new PersonRoleAssociation()
        jane.addToPersonRoleAssociations(janePeon)
        ibmPeon.addToPersonRoleAssociations(janePeon)
    }
    def destroy = {
    }
} 
Ray Tayek
A: 

I would try :

class Person {
  String name
  Set<Role> roles
  Set<Company> companies

  public String toString() {
    return name + " roles : " + (roles.collect { it.name }).toString() + " - companies : " + (companies.collect { it.name }).toString()
  }

  static hasMany = [companies:Company, roles:Role]
  static constraints = {
    name (unique:true)
    roles (nullable:true)
  }
}


class Role {
  String name
  String toString() {
    return name + " companies : " + (companies.collect { it.name }).toString() 
  }
  static hasMany = [companies : Company]
  static belongsTo = Company
  static constraints = {
    name (unique:true)
    companies (nullable:false)
  }
}

class Company {
  String name
  String toString() {
    return name + " roles : " + (roles.collect { it.name }).toString()
  }
  static hasMany = [roles : Role]
  static constraints = {
    name (unique:true)
    roles (nullable:true)
  }
}

Didn't test though... I'd be interested in knowing if my solution has any problems and what they can be...

Philippe