There exist some JVM objects that have innate special abilities. Although unaware of it now, these objects will not only save the Java world, but change it forever. Special abilities such as spontaneous method generation, the ability to persist oneself permanently, or erase every trace their existence, the ability to intelligently self-organise without recourse to foreign wordy verbosity...

These special Objects have been documented to exist deep within a framework, known to the cognescenti as Grails. Up until now Grails has been hugely popular within the Groovy community. What would happen if the special Objects within Grails could not only teleport across Classloaders and past the Java-Groovy boundary, as many Groovy Objects have done in the past, but also teleport across that boundary with their powers intact? ...

A great job

Jeremie Weldin has done a great job of getting GORM (an excellent wrapper over hibernate) to work outside of Grails. I've been playing about with taking this one step further, and allowing Java code to take advantage of all that GORM goodness (i.e. not only easy configuration, but also the dynamic helper methods). The first step was to create a Groovy DAO class - that would be compiled and managed by the Grails classloader. This could then access all of our GORM domain classes. By implementing a DAO interface defined in Java, and by instantiating our DAO via reflection (after extracting the class from the Grails Class loader) we can now access all of our Grails Domain Objects in Java. So far, so good, but no dynamic helper methods yet.

Simple Beginnings

If you want to follow along download Jeremie's code from his blog and implement the following classes.

Our Java DAO interface ...
public interface IAccess<E> {

  public<T> T access(E key);
  public<T> T access(E key,Object... args);

}
Our Groovy DAO Implementation

This class needs to live inside the Grails world, implement it in a folder under grails-app

public class Access implements IAccess{

  def access = [

    listAllBooks : {Book.list()},
    save : { it.save() },

  ]

  public Object access(String key){

    return access[key].call()
  }

  public Object access(String key,Object [] args){

    return access[key].call(args)
  }

}

NB - in the next Groovy release, which will support enums, we could use enums rather than Strings to configure the DAO

Our code to initialise our DAO
IAccess access = cl.loadClass("Access",false,true).newInstance()

Take a look at Jeremie's Test.groovy class - where he creates the Grails application to load and manage the GORM classes - this is where you will get the Class loader. If you are attempting this from within a standard Grails application you can use the following in your own Java code to get at the Class loader.

Accessing the Grails Classloader
ApplicationContext ctx = WebApplicationContextUtils.getWebApplicationContext(request.getSession().getServletContext());
ClassLoader cl = (ClassLoader)ctx.getBean("classLoader");

Beware the automatic compilation by the Groovy Eclipse plugin - it seems to be important that Grails - and not the plugin - compiles the Grails classes!

Retaining the powers

By defining all of the Grails data access methods we want to leverage in our DAO we can take advantage of the full power of GORM, indirectly. The next level however, would be to help those Grails managed GORM objects cross-over into the standard Java world while still retaining their full range of powers. We can do this with the help of plain old Java interfaces, JDK dynamic proxies and the power of the Groovy language (libraries!)..

To be continued...

Resources

Jeremie Weldin's GORM outside of Grails' tutorial Java on Grails pilot Java on Grails : Genesis episode 2 Java on Grails : Save the bean, save the world putting it all together

Downloads

Java on Grails mini-framework Java on Grails demo app
Note the source is stored in jars due to upload file extension restrictions. Vote for or against this entry on Dzone.com!