private static void verifyGobbler(Command command, StreamGobbler gobbler, String type) { if (gobbler.getException() != null) { throw new CommandException(command, "Error inside " + type + " stream", gobbler.getException()); } }
private void consumeLine(String line) { if (exception == null) { try { consumer.consumeLine(line); } catch (Exception e) { exception = e; } } }
/** * Create a command line without any arguments * * @param executable */ public static Command create(String executable) { return new Command(executable, System2.INSTANCE); }
@Test(timeout = 6000L) public void should_stop_after_timeout_and_new_shell() throws IOException { try { String executable = getScript("forever"); CommandExecutor.create().execute(Command.create(executable).setNewShell(true).setDirectory(workDir), 1000L); fail(); } catch (TimeoutException e) { // ok } }
@Test public void should_use_working_directory_to_store_argument_and_environment_variable() throws Exception { Command command = Command.create(getScript("echo")) .setDirectory(workDir) .addArgument("1") .setEnvironmentVariable("ENVVAR", "2"); int exitCode = CommandExecutor.create().execute(command, 1000L); assertThat(exitCode).isEqualTo(0); File logFile = new File(workDir, "echo.log"); assertThat(logFile).exists(); String log = FileUtils.readFileToString(logFile); assertThat(log).contains(workDir.getAbsolutePath()); assertThat(log).contains("Parameter: 1"); assertThat(log).contains("Environment variable: 2"); }
@Test public void toString_is_the_command_line() { Command command = Command.create("java"); command.addArgument("-Xmx512m"); assertThat(command.toString()).isEqualTo(command.toCommandLine()); }
/** * Execute command and display error and output streams in log. * Method {@link #execute(Command, StreamConsumer, StreamConsumer, long)} is preferable, * when fine-grained control of output of command required. * @param timeoutMilliseconds any negative value means no timeout. * * @throws CommandException */ public int execute(Command command, long timeoutMilliseconds) { LOG.info("Executing command: " + command); return execute(command, new DefaultConsumer(), new DefaultConsumer(), timeoutMilliseconds); }
@Test public void initialize_with_current_env() { Command command = Command.create("java"); assertThat(command.getEnvironmentVariables()).isNotEmpty(); }
@Test public void fail_if_null_executable() { thrown.expect(IllegalArgumentException.class); Command.create(null); }
@Test public void shouldnt_use_new_shell_by_default() { Command command = Command.create("foo.sh"); assertThat(command.isNewShell()).isFalse(); } }
@Override public String toString() { return Joiner.on(" ").join(toStrings(true)); } }
private static void waitUntilFinish(@Nullable StreamGobbler thread) { if (thread != null) { try { thread.join(); } catch (InterruptedException e) { // considered as finished, restore the interrupted flag Thread.currentThread().interrupt(); } } }
@Override public void run() { try (BufferedReader br = new BufferedReader(new InputStreamReader(is, StandardCharsets.UTF_8))) { String line; while ((line = br.readLine()) != null) { consumeLine(line); } } catch (IOException ioe) { exception = ioe; } }
@Test(timeout = 6000L) public void should_stop_after_timeout() throws IOException { try { String executable = getScript("forever"); CommandExecutor.create().execute(Command.create(executable).setDirectory(workDir), 1000L); fail(); } catch (TimeoutException e) { // ok } }
@Test public void fail_if_blank_executable() { thrown.expect(IllegalArgumentException.class); Command.create(" "); }
public String toCommandLine() { return Joiner.on(" ").join(toStrings(false)); }
@Test(timeout = 3000L) public void stdOut_consumer_can_throw_exception() throws Exception { Command command = Command.create(getScript("output")).setDirectory(workDir); thrown.expect(CommandException.class); thrown.expectMessage("Error inside stdOut stream"); CommandExecutor.create().execute(command, BAD_CONSUMER, NOP_CONSUMER, 1000L); }
@Test(timeout = 3000L) public void stdErr_consumer_can_throw_exception() throws Exception { Command command = Command.create(getScript("output")).setDirectory(workDir); thrown.expect(CommandException.class); thrown.expectMessage("Error inside stdErr stream"); CommandExecutor.create().execute(command, NOP_CONSUMER, BAD_CONSUMER, 1500L); }
@Test public void should_fail_if_script_not_found() { thrown.expect(CommandException.class); CommandExecutor.create().execute(Command.create("notfound").setDirectory(workDir), 1000L); }
@Test(timeout = 3000L) public void should_consume_StdOut_and_StdErr() throws Exception { // too many false-positives on MS windows if (!SystemUtils.IS_OS_WINDOWS) { final StringBuilder stdOutBuilder = new StringBuilder(); StreamConsumer stdOutConsumer = new StreamConsumer() { public void consumeLine(String line) { stdOutBuilder.append(line).append(SystemUtils.LINE_SEPARATOR); } }; final StringBuilder stdErrBuilder = new StringBuilder(); StreamConsumer stdErrConsumer = new StreamConsumer() { public void consumeLine(String line) { stdErrBuilder.append(line).append(SystemUtils.LINE_SEPARATOR); } }; Command command = Command.create(getScript("output")).setDirectory(workDir); int exitCode = CommandExecutor.create().execute(command, stdOutConsumer, stdErrConsumer, 1000L); assertThat(exitCode).isEqualTo(0); String stdOut = stdOutBuilder.toString(); String stdErr = stdErrBuilder.toString(); assertThat(stdOut).contains("stdOut: first line"); assertThat(stdOut).contains("stdOut: second line"); assertThat(stdErr).contains("stdErr: first line"); assertThat(stdErr).contains("stdErr: second line"); } }