]> source.dussan.org Git - sonar-scanner-cli.git/commitdiff
SONARPLUGINS-2574 ability to subscribe to output
authorSimonBrandhof <simon.brandhof@gmail.com>
Thu, 4 Apr 2013 14:30:01 +0000 (16:30 +0200)
committerSimonBrandhof <simon.brandhof@gmail.com>
Thu, 4 Apr 2013 14:30:01 +0000 (16:30 +0200)
sonar-runner-api/src/main/java/org/sonar/runner/api/CommandExecutor.java
sonar-runner-api/src/main/java/org/sonar/runner/api/ForkedRunner.java
sonar-runner-api/src/main/java/org/sonar/runner/api/PrintStreamConsumer.java [new file with mode: 0644]
sonar-runner-api/src/main/java/org/sonar/runner/api/StreamConsumer.java [new file with mode: 0644]
sonar-runner-api/src/test/java/org/sonar/runner/api/CommandExecutorTest.java

index e3ac4703cc2be3fd9d70d3f0194ed3ebac93a0ac..4c87cfe49c842a6bdb00e804f3a4fdec2b9fa1b6 100644 (file)
@@ -25,12 +25,7 @@ import java.io.BufferedReader;
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.InputStreamReader;
-import java.util.concurrent.Callable;
-import java.util.concurrent.ExecutorService;
-import java.util.concurrent.Executors;
-import java.util.concurrent.Future;
-import java.util.concurrent.TimeUnit;
-import java.util.concurrent.TimeoutException;
+import java.util.concurrent.*;
 
 /**
  * Synchronously execute a native command line. It's much more limited than the Apache Commons Exec library.
@@ -109,15 +104,6 @@ class CommandExecutor {
     }
   }
 
-  /**
-   * 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.
-   */
-  int execute(Command command, long timeoutMilliseconds) {
-    return execute(command, new DefaultConsumer(), new DefaultConsumer(), timeoutMilliseconds);
-  }
-
   private void closeStreams(Process process) {
     if (process != null) {
       IOUtils.closeQuietly(process.getInputStream());
@@ -181,15 +167,4 @@ class CommandExecutor {
       return exception;
     }
   }
-
-
-  interface StreamConsumer {
-    void consumeLine(String line);
-  }
-
-  private static class DefaultConsumer implements StreamConsumer {
-    public void consumeLine(String line) {
-      System.out.println(line);
-    }
-  }
 }
index 3e772670628826ccb1100a3e88ebe7ee988bd20f..8dca9fe34df99c29b10f8af6e4c1c3ac3822046e 100644 (file)
@@ -36,7 +36,7 @@ public class ForkedRunner extends Runner<ForkedRunner> {
   private final Map<String, String> jvmEnvVariables = new HashMap<String, String>();
   private final List<String> jvmArguments = new ArrayList<String>();
   private String javaCommand;
-
+  private StreamConsumer stdOut = null, stdErr = null;
   private final JarExtractor jarExtractor;
 
   ForkedRunner(JarExtractor jarExtractor) {
@@ -71,6 +71,22 @@ public class ForkedRunner extends Runner<ForkedRunner> {
     return this;
   }
 
+  /**
+   * Subscribe to the standard output. By default output is {@link System.out}
+   */
+  public ForkedRunner setStdOut(@Nullable StreamConsumer stream) {
+    this.stdOut = stream;
+    return this;
+  }
+
+  /**
+   * Subscribe to the error output. By default output is {@link System.err}
+   */
+  public ForkedRunner setStdErr(@Nullable StreamConsumer stream) {
+    this.stdErr = stream;
+    return this;
+  }
+
   @Override
   protected void doExecute() {
     fork(createCommand());
@@ -108,9 +124,16 @@ public class ForkedRunner extends Runner<ForkedRunner> {
   }
 
   private void fork(Command command) {
-    int status = CommandExecutor.create().execute(command, ONE_DAY_IN_MILLISECONDS);
+    if (stdOut == null) {
+      stdOut = new PrintStreamConsumer(System.out);
+    }
+    if (stdErr == null) {
+      stdErr = new PrintStreamConsumer(System.err);
+    }
+    int status = CommandExecutor.create().execute(command, stdOut, stdErr, ONE_DAY_IN_MILLISECONDS);
     if (status != 0) {
       throw new IllegalStateException("TODO");
     }
   }
+
 }
diff --git a/sonar-runner-api/src/main/java/org/sonar/runner/api/PrintStreamConsumer.java b/sonar-runner-api/src/main/java/org/sonar/runner/api/PrintStreamConsumer.java
new file mode 100644 (file)
index 0000000..e64ba7c
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * Sonar Runner - API
+ * Copyright (C) 2011 SonarSource
+ * dev@sonar.codehaus.org
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02
+ */
+package org.sonar.runner.api;
+
+import java.io.PrintStream;
+
+public class PrintStreamConsumer implements StreamConsumer {
+  private final PrintStream output;
+
+  public PrintStreamConsumer(PrintStream output) {
+    this.output = output;
+  }
+
+  public void consumeLine(String line) {
+    output.println(line);
+  }
+}
diff --git a/sonar-runner-api/src/main/java/org/sonar/runner/api/StreamConsumer.java b/sonar-runner-api/src/main/java/org/sonar/runner/api/StreamConsumer.java
new file mode 100644 (file)
index 0000000..7eac938
--- /dev/null
@@ -0,0 +1,24 @@
+/*
+ * Sonar Runner - API
+ * Copyright (C) 2011 SonarSource
+ * dev@sonar.codehaus.org
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02
+ */
+package org.sonar.runner.api;
+
+public interface StreamConsumer {
+  void consumeLine(String line);
+}
index d63a6a3958aa2b4f154bee6539bed484d7686baf..2d7cb970b29cb0372bf6298189a54a669798bc3c 100644 (file)
@@ -44,7 +44,9 @@ public class CommandExecutorTest {
   @Rule
   public ExpectedException thrown = ExpectedException.none();
 
-  private File workDir;
+  PrintStreamConsumer stdout = new PrintStreamConsumer(System.out);
+  PrintStreamConsumer stderr = new PrintStreamConsumer(System.err);
+  File workDir;
 
   @Before
   public void setUp() throws IOException {
@@ -54,13 +56,13 @@ public class CommandExecutorTest {
   @Test
   public void should_consume_StdOut_and_StdErr() throws Exception {
     final StringBuilder stdOutBuilder = new StringBuilder();
-    CommandExecutor.StreamConsumer stdOutConsumer = new CommandExecutor.StreamConsumer() {
+    StreamConsumer stdOutConsumer = new StreamConsumer() {
       public void consumeLine(String line) {
         stdOutBuilder.append(line).append(System.getProperty("line.separator"));
       }
     };
     final StringBuilder stdErrBuilder = new StringBuilder();
-    CommandExecutor.StreamConsumer stdErrConsumer = new CommandExecutor.StreamConsumer() {
+    StreamConsumer stdErrConsumer = new StreamConsumer() {
       public void consumeLine(String line) {
         stdErrBuilder.append(line).append(System.getProperty("line.separator"));
       }
@@ -93,13 +95,13 @@ public class CommandExecutorTest {
     CommandExecutor.create().execute(command, NOP_CONSUMER, BAD_CONSUMER, 1000L);
   }
 
-  private static final CommandExecutor.StreamConsumer NOP_CONSUMER = new CommandExecutor.StreamConsumer() {
+  private static final StreamConsumer NOP_CONSUMER = new StreamConsumer() {
     public void consumeLine(String line) {
       // nop
     }
   };
 
-  private static final CommandExecutor.StreamConsumer BAD_CONSUMER = new CommandExecutor.StreamConsumer() {
+  private static final StreamConsumer BAD_CONSUMER = new StreamConsumer() {
     public void consumeLine(String line) {
       throw new RuntimeException();
     }
@@ -113,7 +115,7 @@ public class CommandExecutorTest {
         .addArguments("1")
         .setEnvVariable("ENVVAR", "2")
         .build();
-    int exitCode = CommandExecutor.create().execute(command, 1000L);
+    int exitCode = CommandExecutor.create().execute(command, stdout, stderr, 1000L);
     assertThat(exitCode).isEqualTo(0);
     File logFile = new File(workDir, "echo.log");
     assertThat(logFile).exists();
@@ -128,7 +130,8 @@ public class CommandExecutorTest {
     String executable = getScript("forever");
     long start = System.currentTimeMillis();
     try {
-      CommandExecutor.create().execute(Command.builder().setExecutable(executable).setDirectory(workDir).build(), 300L);
+      Command command = Command.builder().setExecutable(executable).setDirectory(workDir).build();
+      CommandExecutor.create().execute(command, stdout, stderr, 300L);
       fail();
     } catch (CommandException e) {
       long duration = System.currentTimeMillis() - start;
@@ -141,7 +144,8 @@ public class CommandExecutorTest {
   @Test
   public void should_fail_if_script_not_found() {
     thrown.expect(CommandException.class);
-    CommandExecutor.create().execute(Command.builder().setExecutable("notfound").setDirectory(workDir).build(), 1000L);
+    Command command = Command.builder().setExecutable("notfound").setDirectory(workDir).build();
+    CommandExecutor.create().execute(command, stdout, stderr, 1000L);
   }
 
   private static String getScript(String name) throws IOException {