in src/main/java/org/apache/maven/shared/utils/cli/CommandLineUtils.java [218:342]
public static CommandLineCallable executeCommandLineAsCallable(
@Nonnull final Commandline cl,
@Nullable final InputStream systemIn,
final StreamConsumer systemOut,
final StreamConsumer systemErr,
final int timeoutInSeconds,
@Nullable final Runnable runAfterProcessTermination,
@Nullable final Charset streamCharset)
throws CommandLineException {
//noinspection ConstantConditions
if (cl == null) {
throw new IllegalArgumentException("cl cannot be null.");
}
final Process p = cl.execute();
final Thread processHook = new Thread() {
{
this.setName("CommandLineUtils process shutdown hook");
this.setContextClassLoader(null);
}
@Override
public void run() {
p.destroy();
}
};
ShutdownHookUtils.addShutDownHook(processHook);
return new CommandLineCallable() {
@Override
public Integer call() throws CommandLineException {
StreamPollFeeder inputFeeder = null;
StreamPumper outputPumper = null;
StreamPumper errorPumper = null;
try {
if (systemIn != null) {
inputFeeder = new StreamPollFeeder(systemIn, p.getOutputStream());
inputFeeder.setName("StreamPollFeeder-systemIn");
inputFeeder.start();
}
outputPumper = new StreamPumper(p.getInputStream(), systemOut);
outputPumper.setName("StreamPumper-systemOut");
outputPumper.start();
errorPumper = new StreamPumper(p.getErrorStream(), systemErr);
errorPumper.setName("StreamPumper-systemErr");
errorPumper.start();
if (timeoutInSeconds > 0 && !p.waitFor(timeoutInSeconds, TimeUnit.SECONDS)) {
throw new CommandLineTimeOutException(
String.format("Process timed out after %d seconds.", timeoutInSeconds));
}
int returnValue = p.waitFor();
// TODO Find out if waitUntilDone needs to be called using a try-finally construct. The method may
// throw an
// InterruptedException so that calls to waitUntilDone may be skipped.
// try
// {
// if ( inputFeeder != null )
// {
// inputFeeder.waitUntilDone();
// }
// }
// finally
// {
// try
// {
// outputPumper.waitUntilDone();
// }
// finally
// {
// errorPumper.waitUntilDone();
// }
// }
if (inputFeeder != null) {
inputFeeder.waitUntilDone();
}
outputPumper.waitUntilDone();
errorPumper.waitUntilDone();
if (inputFeeder != null && inputFeeder.getException() != null) {
throw new CommandLineException("Failure processing stdin.", inputFeeder.getException());
}
if (outputPumper.getException() != null) {
throw new CommandLineException("Failure processing stdout.", outputPumper.getException());
}
if (errorPumper.getException() != null) {
throw new CommandLineException("Failure processing stderr.", errorPumper.getException());
}
return returnValue;
} catch (InterruptedException ex) {
Thread.currentThread().interrupt();
throw new CommandLineTimeOutException(
"Error while executing external command, process killed.", ex);
} finally {
if (outputPumper != null) {
outputPumper.disable();
}
if (errorPumper != null) {
errorPumper.disable();
}
try {
if (runAfterProcessTermination != null) {
runAfterProcessTermination.run();
}
} finally {
ShutdownHookUtils.removeShutdownHook(processHook);
processHook.run();
}
}
}
};
}