Tuesday, April 5, 2011

Transitive Dependency Management in Groovy Grape / @Grab via @GrabExclude

Sébastien Launay provided a better solution for Fixing Slow @Grab Dependencies Issue with Groovy/Grape Scripts.

I didn't know that Groovy's Grape / @Grab supports transitive dependency management features (that Apache Ivy underneath is actually very good at). (where are the @Grab/@GrabExclude docs???) So this is very new to me.

Below is his post copied verbatim:

. . .

Actually I think a more sexier way would be to provide explicitly the version of groovy or even exclude the dependency it as it is provided by the application classloader.

So the following examples work and do not need to create a file:

@Grab(group="org.codehaus.groovy.modules.http-builder",
  module="http-builder", version="0.5.1")
@Grab(group="org.codehaus.groovy", module="groovy", version="1.7.10")

or

@Grab(group="org.codehaus.groovy.modules.http-builder",
  module="http-builder", version="0.5.1")
@GrabExclude("org.codehaus.groovy:groovy")

All of these are workarounds, the problem IMHO still lies in the usage of a version range dependency.

I am not sure what happens when the application classloader has let's say Groovy 1.7.0 and the Grape classloader (asuming there is a nested classloader) provides Groovy 1.8.0, I would say that Grape comes from Groovy 1.7.0 but the target script is compiled and executed with Groovy 1.8.0, am I right?