Quantcast

How can I create domain class instances dynamically?

classic Classic list List threaded Threaded
3 messages Options
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

How can I create domain class instances dynamically?

mschneider01
Hi,

I'm looking for a way to create domain class instances dynamically.
But there is no need to compile new domain classes at runtime.
I hope the following code gives an idea what I'm trying to achive:

Domain:
---
Person {
        String name
        Integer age
}


Controller
---
public void saveDomainClassProperties(def domainClass, def newProperties) {
        log.info("domainClass :" + domainClass)
        def grailsApplication = applicationContextHolderBean.getGrailsApplication()
        def domainClassInstance = grailsApplication.getArtefact(DomainClassArtefactHandler.TYPE,domainClass)
        domainClassInstance.properties.each { property ->
                log.info("property.name: " + property.name)
                domainClassInstance.property = newProperties."${property.name}"
                domainClassInstance.save(flush: true)
        }
}

saveDomainClassProperties('Person',[name:"max",age:20])

It's clear that 'grailsApplication.getArtefact(DomainClassArtefactHandler.TYPE,domainClass)' it's not
the right method here, but has anybody an idea how to handle this?

Thanks in advance.
-markus
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: How can I create domain class instances dynamically?

burtbeckwith
There's a dynamic method here that's less verbose - getDomainClass(). All artifacts have a getXXXClass() method, e.g. getControllerClass(), etc. Also controllers already have a 'grailsApplication' variable in scope, so no need for a holder. You'll need to make the method private since public methods are exposed as actions, and it's just a helper method anyway so it should be private. Also I typed the 1st argument since when I first looked at it I assumed based on the name that you'd be passing in either a Class or a DomainClass, but not a String. Not too hard to type the 3 extra chars in 'String' vs 'def' :)

If 'newProperties' is a Map (more mystery; a good argument for typing vars in method signatures -
mystery is fun in novels but less so when coding) then you can just do this:

private void saveDomainClassProperties(String domainClassName, Map newProperties) {
        log.info "domainClass : $domainClassName"
        def domainClassInstance = grailsApplication.getDomainClass(domainClassName).newInstance()
        domainClassInstance.properties = newProperties
        domainClassInstance.save(flush: true)
}

Note that the class name has to include the full package and name, i.e. 'com.foo.bar.Person'.

Burt

mschneider-1 wrote
Hi,

I'm looking for a way to create domain class instances dynamically.
But there is no need to compile new domain classes at runtime.
I hope the following code gives an idea what I'm trying to achive:

Domain:
---
Person {
        String name
        Integer age
}


Controller
---
public void saveDomainClassProperties(def domainClass, def newProperties) {
        log.info("domainClass :" + domainClass)
        def grailsApplication = applicationContextHolderBean.getGrailsApplication()
        def domainClassInstance = grailsApplication.getArtefact(DomainClassArtefactHandler.TYPE,domainClass)
        domainClassInstance.properties.each { property ->
                log.info("property.name: " + property.name)
                domainClassInstance.property = newProperties."${property.name}"
                domainClassInstance.save(flush: true)
        }
}

saveDomainClassProperties('Person',[name:"max",age:20])

It's clear that 'grailsApplication.getArtefact(DomainClassArtefactHandler.TYPE,domainClass)' it's not
the right method here, but has anybody an idea how to handle this?

Thanks in advance.
-markus
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate
star

Re: How can I create domain class instances dynamically?

mschneider01
Hi Burt,

thank you very much for your help. That is exactly what I was looking for.  In my example I've written that I use the code in a controller but the true story is that it is used in a groovy class lib, so I think the 'holder' is necessary - (based on your blog post http://burtbeckwith.com/blog/?p=1017 - also, thank you for this example).
Also, I'll improve my style of coding - promised

Regards,

-markus
Loading...