Maven 2 JAR Fetch Trick

July 09, 2007

This tip probably belongs under the category "stupid Maven 2 tricks." While writing a tutorial that uses Maven 2, I thought to myself, "There must be a way to pull an artifact into the local Maven 2 repository without a build script." Unfortunately, a build script is required, but with a little shell magic, we can hide those details.

So what's the basic premise? First, you need to create a minimalistic Maven 2 POM file (pom.xml). The next step is to add the dependency that you would like to fetch. Finally, you execute the dependency:resolve Maven 2 goal. (By the way, I highly recommend checking out the dependency plugin. It can produce very useful output in a pinch.)

Here is the minimalistic POM file that you can use to pull down the H2 database jar file.

<project>
    <modelVersion>4.0.0</modelVersion>
    <groupId>null</groupId>
    <artifactId>null</artifactId>
    <version>0</version>
    <dependencies>
        <dependency>
            <groupId>com.h2database</groupId>
            <artifactId>h2</artifactId>
            <version>1.0.20070429</version>
        </dependency>
    </dependencies>
</project>

Now execute the Maven 2 goal to resolve artifacts, which will download the dependencies declared in this project file and place them into the local repository . I have also added the flag to display the absolute paths to those files, just in case you need to copy it for use in a configuration wizard.

mvn dependency:resolve -DoutputAbsoluteArtifactFilename=true

But if you use the groovy script below, you can get this all done in one line without having to create a POM file at all.

mvnfetch -a com.h2database -g h2 -v 1.0.20070429

#!/usr/bin/env groovy

def cli = new CliBuilder(usage: 'mvnfetch [OPTION]')
cli.a(longOpt:'artifactId', args:1, required:true)
cli.g(longOpt:'groupId', args:1, required:true)
cli.v(longOpt:'version', args:1, required:true)

def options = cli.parse(args)

def artifactId = options.a;
def groupId = options.g;
def version = options.v;

new File('.mvnfetch.xml').write("""
<project>
  <modelVersion>4.0.0</modelVersion>
  <groupId>none</groupId>
  <artifactId>none</artifactId>
  <version>1.0</version>
  <dependencies>
    <dependency>
      <groupId>${groupId}</groupId>
      <artifactId>${artifactId}</artifactId>
      <version>${version}</version>
    </dependency>
  </dependencies>
</project>""")

def proc = "mvn -f .mvnfetch.xml dependency:resolve".execute()
proc.in.eachLine { println it }
proc.waitFor()

"/bin/rm .mvnfetch.xml".execute()
Once again, Groovy comes in handy for its scripting magic.

Posted at 12:26 AM in Java | Permalink Icon Permalink

4 Comments from the Peanut Gallery

1 | Posted by Jeremy Leipzig on September 10, 2008 at 01:48 PM EST

Awesome script. Is there a way to have it maven simply fetch the latest version of a dependency without me having to know what the version # is?

2 | Posted by Dan Allen on September 10, 2008 at 01:55 PM EST

I believe that you set the version to RELEASE, but I must warn you that this is highly dependent on the POM metadata in the repository, which is...well...not always reliable.

3 | Posted by Jeremy Leipzig on September 24, 2008 at 05:04 PM EST

I experienced a couple errors with this script - not sure why but the following changes seemed to clear it up for me and may help others.

1. clis needed more explicit arguments:

cli.a(argName:'artifactId', longOpt:'artifactId', args:1, required:true,'artifact id')

cli.g(argName:'groupId',longOpt:'groupId', args:1, required:true,'group id')

cli.v(argName:'version',longOpt:'version', args:1, required:true,'version')

2.proc.in changed to proc.text

proc.text.eachLine { println it }

BTW I am using Groovy Version: 1.5.5 JVM: 1.6.0_03-b05

4 | Posted by IC on June 12, 2012 at 12:37 PM EST

You can actutally do this without a POM - try

mvn dependency:get -DrepoUrl= [url] -Dartifact=[group]:[artifact]:[version]