21

Is it possible to call Maven goals from Java, for instance, can I do the equivalent of:

mvn clean package

from a Java class?

thanks, Nick

eldoctoro
  • 893
  • 2
  • 10
  • 15

3 Answers3

19

absolutely, you need to use the Maven Embedder API.

Updated link is http://maven.apache.org/ref/3-LATEST/maven-embedder/index.html

Paul Verest
  • 60,022
  • 51
  • 208
  • 332
dfa
  • 114,442
  • 31
  • 189
  • 228
  • 5
    This might no longer be the correct answer. It seems that maven-embedder is gone from Maven3: http://stackoverflow.com/questions/4206679/can-anyone-give-a-good-example-of-using-org-apache-maven-cli-mavencli-programatt – jbandi Sep 20 '12 at 21:12
3

This is easy :)

Java code

MavenCli cli = new MavenCli();
cli.doMain(new String[]{"clean", "package"}, "project_dir", System.out, System.out);

Project configuration:

<dependencies>
    <dependency>
        <groupId>org.apache.maven</groupId>
        <artifactId>maven-embedder</artifactId>
        <version>3.1.1</version>
    </dependency>
    <dependency>
        <groupId>org.eclipse.aether</groupId>
        <artifactId>aether-connector-wagon</artifactId>
        <version>0.9.0.M2</version>
    </dependency>
    <dependency>
        <groupId>org.apache.maven.wagon</groupId>
        <artifactId>wagon-http-lightweight</artifactId>
        <version>2.5</version>
    </dependency>
</dependencies>

Fully working example: https://github.com/mariuszs/maven-cli-example

MariuszS
  • 30,646
  • 12
  • 114
  • 155
1

I would not recommend to use MAVEN CLI because it works differently comparing to command line alternative. For example:

With CLI, I want to reproduce "mvn dependency:resolve validate"

cli.doMain(
  new String[]{
       "dependency:resolve",     // download deps if needed
        "validate"},              // just validates, no need even to compile
         projectPath ...

But actually it will go all over the folders (recursively) and will try to validate all projects there even if I don't want it. If if something wrong - it fails.

If, though, you try to do the same just with command line - it will invoke only pom.xm and will finish successfully (even if some project inside 'projectPath' is not resolvable.

With CLI I could NOT manage to use "-f " flag to specify particular pom.xml!

This is quite good for me:

private int resolveAsCommandLine() {
        try {

        String command =  "mvn " +
                            "-f " + projectPath + "\\pom.xml " +
                            "-Dmaven.repo.local=" + localRepoPath + "\\repository " +
                            "-Dmaven.test.skip=true " + // ignore tests
                            "dependency:resolve " +     // download deps if needed
                            "validate";

            System.out.println("%> Executing command: '" + command + "'...");

            Process p = Runtime.getRuntime().exec( // "cmd - for windows only"
                    "cmd /c " + command

            );


            BufferedReader in = new BufferedReader(
                    new InputStreamReader(p.getInputStream()) );

            String line = "";
            while ((line = in.readLine()) != null) {
                System.out.println(line);
                if(line.contains("[ERROR]")) return ERROR_STATUS;
                if(line.contains("BUILD FAILURE")) return ERROR_STATUS;
                if(line.contains("BUILD SUCCESS")) return OK_STATUS;
            }
            in.close();

        } catch (IOException e) {
            e.printStackTrace();
            return ERROR_STATUS;
        }

        return ERROR_STATUS;
    }
ses
  • 13,174
  • 31
  • 123
  • 226
  • Your answer is old, so likely embedded maven has improved. Now, the `-f` option works fantastically, even with embedded maven. I used an absolute path (haven't ever tried a relative path). – djeikyb Jul 17 '15 at 16:19