Hi

I've just started playing around with the myrmidon Ant2 proposal, as I'm 
hoping to get involved. While running a few of the sample targets, I noticed 
that after any <exec> task, no further messages are logged. This is due to 
the fact that o.a.aut.nativelib.impl.ProcessMonitor is shutting down all 
streams after the Process has been executed.  Because 
o.a.myrmidon.framework.Execute.executeNativeProcess() is passing in 
System.out, this is being closed, preventing any further messages to the 
console.

The supplied patch fixes this by making the code that creates the Stream 
responsible for closing them. I added a flag to ProcessMonitor to optionally 
force it close the Streams when the Process terminates, but I would imagine 
that this would be only used for monitoring an asynchronous Process.

However, an alternative would be to make the ExecManager.execute() contract 
clearly specify that all Streams will be closed, and make sure that 
o.a.myrmidon.framework.Execute.executeNativeProcess() doesn't pass in 
System.out, but instead passes in an OutputStream that can be safely closed.

If the latter is a preferable solution, I'd be happy to do up a patch for 
that.

ciao
Daz
? patch.txt
Index: org/apache/aut/nativelib/impl/DefaultExecManager.java
===================================================================
RCS file: /home/cvs/jakarta-ant/proposal/myrmidon/src/java/org/apache/aut/nativelib/impl/DefaultExecManager.java,v
retrieving revision 1.7
diff -u -r1.7 DefaultExecManager.java
--- org/apache/aut/nativelib/impl/DefaultExecManager.java	2 Feb 2002 06:38:07 -0000	1.7
+++ org/apache/aut/nativelib/impl/DefaultExecManager.java	21 Feb 2002 06:22:28 -0000
@@ -116,7 +116,7 @@
         final CommandLauncher launcher = getLauncher( metaData );
         final Process process = launcher.exec( metaData );
         final ProcessMonitor monitor =
-            new ProcessMonitor( process, input, output, error, timeout );
+            new ProcessMonitor( process, input, output, error, timeout, false );
 
         final Thread thread = new Thread( monitor, "ProcessMonitor" );
         thread.start();
Index: org/apache/aut/nativelib/impl/Environment.java
===================================================================
RCS file: /home/cvs/jakarta-ant/proposal/myrmidon/src/java/org/apache/aut/nativelib/impl/Environment.java,v
retrieving revision 1.2
diff -u -r1.2 Environment.java
--- org/apache/aut/nativelib/impl/Environment.java	2 Feb 2002 06:38:07 -0000	1.2
+++ org/apache/aut/nativelib/impl/Environment.java	21 Feb 2002 06:22:28 -0000
@@ -19,6 +19,7 @@
 import org.apache.aut.nativelib.ExecMetaData;
 import org.apache.aut.nativelib.Os;
 import org.apache.avalon.excalibur.util.StringUtil;
+import org.apache.avalon.excalibur.io.IOUtil;
 
 /**
  * This is the class that can be used to retrieve the environment
@@ -157,13 +158,17 @@
         final ExecMetaData metaData = new ExecMetaData( command, null, workingDirectory, false );
 
         final ByteArrayOutputStream output = new ByteArrayOutputStream();
-        final int retval = m_execManager.execute( metaData, null, output, output, 0 );
-        if( retval != 0 )
-        {
-            // Just try to use what we got
-        }
+        try {
+            final int retval = m_execManager.execute( metaData, null, output, output, 0 );
+            if( retval != 0 )
+            {
+                // Just try to use what we got
+            }
 
-        return output.toString();
+            return output.toString();
+        } finally {
+            IOUtil.shutdownStream( output );
+        }
     }
 
     /**
Index: org/apache/aut/nativelib/impl/ProcessMonitor.java
===================================================================
RCS file: /home/cvs/jakarta-ant/proposal/myrmidon/src/java/org/apache/aut/nativelib/impl/ProcessMonitor.java,v
retrieving revision 1.5
diff -u -r1.5 ProcessMonitor.java
--- org/apache/aut/nativelib/impl/ProcessMonitor.java	6 Feb 2002 13:34:46 -0000	1.5
+++ org/apache/aut/nativelib/impl/ProcessMonitor.java	21 Feb 2002 06:22:29 -0000
@@ -72,11 +72,33 @@
      */
     private final OutputStream m_error;
 
+    /**
+     * Specifies whether the monitor should shutdown
+     * input, output and error Streams when it finishes execution.
+     * This should be set to <code>true</code> for processes which
+     * will run asynchronously.
+     */
+    private final boolean m_shutdownStreams;
+
+    /**
+     * Creates a monitor for a given [EMAIL PROTECTED] java.lang.Process}, which pipes
+     * input from the given input stream to the process, and pipes the process
+     * output to the given OutputStreams.
+     *
+     * @param process the Process to be monitored
+     * @param input is read into the Process' stdin
+     * @param output receives the Process' stdout
+     * @param error receives the Process' stderr
+     * @param timeoutDuration how long to let the Process run before killing it.
+     * @param shutdownStreams specifies if the monitor should shutdown the
+     *             streams when the Process exits.
+     */
     public ProcessMonitor( final Process process,
                            final InputStream input,
                            final OutputStream output,
                            final OutputStream error,
-                           final long timeoutDuration )
+                           final long timeoutDuration,
+                           final boolean shutdownStreams )
     {
         if( null == process )
         {
@@ -100,6 +122,7 @@
         m_output = output;
         m_error = error;
         m_timeout = timeout;
+        m_shutdownStreams = shutdownStreams;
     }
 
     /**
@@ -139,9 +162,18 @@
         //that we have got all the data
         processStreams();
 
-        IOUtil.shutdownStream( m_input );
-        IOUtil.shutdownStream( m_output );
-        IOUtil.shutdownStream( m_error );
+        cleanupStreams();
+    }
+
+    /**
+     * Utility method which cleans up all IO Streams, if required.
+     */
+    private void cleanupStreams() {
+        if ( m_shutdownStreams ) {
+            IOUtil.shutdownStream(m_input);
+            IOUtil.shutdownStream(m_output);
+            IOUtil.shutdownStream(m_error);
+        }
     }
 
     /**
--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to