From 41987c9acd2db4ac4a00eb8443c1a2a7e1900e69 Mon Sep 17 00:00:00 2001 From: Georg Seibt <seibt@fim.uni-passau.de> Date: Wed, 4 May 2016 23:05:38 +0200 Subject: [PATCH] read stdout/stderr at the same time if error output is not being redirected --- .../gitwrapper/process/ProcessExecutor.java | 40 +++++++++++++++++-- 1 file changed, 36 insertions(+), 4 deletions(-) diff --git a/src/de/uni_passau/fim/seibt/gitwrapper/process/ProcessExecutor.java b/src/de/uni_passau/fim/seibt/gitwrapper/process/ProcessExecutor.java index 2ea20f8..7cffbb9 100644 --- a/src/de/uni_passau/fim/seibt/gitwrapper/process/ProcessExecutor.java +++ b/src/de/uni_passau/fim/seibt/gitwrapper/process/ProcessExecutor.java @@ -2,17 +2,21 @@ package de.uni_passau.fim.seibt.gitwrapper.process; import java.io.File; import java.io.IOException; -import java.nio.charset.StandardCharsets; import java.util.Collections; import java.util.LinkedList; import java.util.List; import java.util.Optional; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; import java.util.logging.Level; import java.util.logging.Logger; import org.apache.commons.io.IOUtils; import static de.uni_passau.fim.seibt.gitwrapper.repo.GitWrapper.EXIT_FAIL; +import static java.nio.charset.StandardCharsets.UTF_8; import static java.util.logging.Level.WARNING; /** @@ -21,6 +25,7 @@ import static java.util.logging.Level.WARNING; public class ProcessExecutor { private static final Logger LOG = Logger.getLogger(ProcessExecutor.class.getCanonicalName()); + private static final ExecutorService exService = Executors.newCachedThreadPool(); /** * The result of a process execution. @@ -78,8 +83,35 @@ public class ProcessExecutor { try { Process p = builder.start(); - String stdOut = IOUtils.toString(p.getInputStream(), StandardCharsets.UTF_8).trim(); - String stdErr = IOUtils.toString(p.getErrorStream(), StandardCharsets.UTF_8).trim(); + String stdOut; + String stdErr; + + if (builder.redirectErrorStream()) { + stdOut = IOUtils.toString(p.getInputStream(), UTF_8).trim(); + stdErr = IOUtils.toString(p.getErrorStream(), UTF_8).trim(); + } else { + Future<String> outF = exService.submit(() -> IOUtils.toString(p.getInputStream(), UTF_8).trim()); + Future<String> errF = exService.submit(() -> IOUtils.toString(p.getErrorStream(), UTF_8).trim()); + + try { + stdOut = outF.get(); + stdErr = errF.get(); + } catch (InterruptedException e) { + LOG.log(WARNING, e, () -> String.format("Interrupted while waiting for '%s' to finish.", cmd)); + + outF.cancel(true); + errF.cancel(true); + p.destroyForcibly(); + return Optional.empty(); + } catch (ExecutionException e) { + LOG.log(WARNING, e, () -> String.format("Exception while reading the output of '%s'.", cmd)); + + outF.cancel(true); + errF.cancel(true); + p.destroyForcibly(); + return Optional.empty(); + } + } IOUtils.closeQuietly(p.getInputStream()); IOUtils.closeQuietly(p.getErrorStream()); @@ -93,7 +125,7 @@ public class ProcessExecutor { LOG.log(WARNING, e, () -> String.format("Interrupted while waiting for '%s' to finish.", cmd)); p.destroyForcibly(); - exitCode = EXIT_FAIL; + return Optional.empty(); } ExecRes res = new ExecRes(exitCode, stdOut, stdErr); -- GitLab