ZT Process Executor

Continuous Integration

Build Status

Quick Overview

The project was created to merge similar functionality of projects at ZeroTurnaround into a single codebase. It's designed to be powerful but still simple to use. By using a single class ProcessExecutor the user gets the functionality from both java.lang.ProcessBuilder and Apache Commons Exec.

Installation

Maven Central

The project artifacts are available in Maven Central Repository.

To include it in your maven project then you have to specify the dependency.

...
<dependency>
    <groupId>org.zeroturnaround</groupId>
    <artifactId>zt-exec</artifactId>
    <version>1.11</version>
</dependency>
...

Motivation

There are many approaches to take when running external processes from Java. There are the JRE options such as the Runtime.exec() and ProcessBuilder. Also there is the Apache Commons Exec. Nevertheless we created yet another process library (YAPL).

Some of the reasons for this crazy endeavour

Can zt-exec also kill processes?

No. There is zt-process-killer for that.

Examples

new ProcessExecutor().command("java", "-version").execute();

int exit = new ProcessExecutor().command("java", "-version")
                  .execute().getExitValue();

String output = new ProcessExecutor().command("java", "-version")
                  .readOutput(true).execute()
                  .outputUTF8();    

new ProcessExecutor().command("java", "-version")
      .redirectOutput(Slf4jStream.of(LoggerFactory.getLogger(getClass().getName() + ".MyProcess")).asInfo()).execute();

new ProcessExecutor().command("java", "-version")
      .redirectOutput(Slf4jStream.of("MyProcess").asInfo()).execute();

new ProcessExecutor().command("java", "-version")
      .redirectOutput(Slf4jStream.ofCaller().asInfo()).execute();

String output = new ProcessExecutor().command("java", "-version")
        .redirectOutput(Slf4jStream.of(getClass()).asInfo())
        .readOutput(true).execute().outputUTF8();

String output = new ProcessExecutor().command("java", "-version")
        .redirectError(Slf4jStream.of(getClass()).asInfo())
        .readOutput(true).execute()
        .outputUTF8();

try {
  new ProcessExecutor().command("java", "-version")
        .timeout(60, TimeUnit.SECONDS).execute();
}
catch (TimeoutException e) {
  // process is automatically destroyed
}

OutputStream out = ...;
new ProcessExecutor().command("java", "-version")
      .redirectOutput(out).execute();

new ProcessExecutor().command("java", "-version")
    .redirectOutput(new LogOutputStream() {
      @Override
      protected void processLine(String line) {
        ...
      }
    })
    .execute();

new ProcessExecutor().command("java", "-version").destroyOnExit().execute();

new ProcessExecutor().command("java", "-version")
    .environment("foo", "bar").execute();

Map<String, String> env = ...
new ProcessExecutor().command("java", "-version")
    .environment(env).execute();

try {
  new ProcessExecutor().command("java", "-version")
        .exitValues(3).execute();
}
catch (InvalidExitValueException e) {
  System.out.println("Process exited with " + e.getExitValue());
}

String output;
boolean success = false;
try {
  output = new ProcessExecutor().command("java", "-version")
                .readOutput(true).exitValues(3)
                .execute().outputUTF8();
  success = true;
}
catch (InvalidExitValueException e) {
  System.out.println("Process exited with " + e.getExitValue());
  output = e.getResult().outputUTF8();
}

Future<ProcessResult> future = new ProcessExecutor()
                                    .command("java", "-version")
                                    .start().getFuture();
// do some stuff
future.get(60, TimeUnit.SECONDS);

Future<ProcessResult> future = new ProcessExecutor()
                                    .command("java", "-version")
                                    .readOutput(true)
                                    .start().getFuture();
// do some stuff
String output = future.get(60, TimeUnit.SECONDS).outputUTF8();