You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by sg...@apache.org on 2007/12/04 13:11:06 UTC

svn commit: r600905 - in /commons/sandbox/exec/trunk/src: changes/ changes/changes.xml main/java/org/apache/commons/exec/ExecuteWatchdog.java test/java/org/apache/commons/exec/DefaultExecutorTest.java

Author: sgoeschl
Date: Tue Dec  4 04:11:05 2007
New Revision: 600905

URL: http://svn.apache.org/viewvc?rev=600905&view=rev
Log:
SANDBOX-193 Adding a ExecuteWatchdog.destroy() to kill an aysnc process on behalf of the user

Added:
    commons/sandbox/exec/trunk/src/changes/
    commons/sandbox/exec/trunk/src/changes/changes.xml
Modified:
    commons/sandbox/exec/trunk/src/main/java/org/apache/commons/exec/ExecuteWatchdog.java
    commons/sandbox/exec/trunk/src/test/java/org/apache/commons/exec/DefaultExecutorTest.java

Added: commons/sandbox/exec/trunk/src/changes/changes.xml
URL: http://svn.apache.org/viewvc/commons/sandbox/exec/trunk/src/changes/changes.xml?rev=600905&view=auto
==============================================================================
--- commons/sandbox/exec/trunk/src/changes/changes.xml (added)
+++ commons/sandbox/exec/trunk/src/changes/changes.xml Tue Dec  4 04:11:05 2007
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<document>
+  <properties>
+    <title>commons-exec</title>
+    <author email="sgoeschl@apache.org">Siegfried Goeschl</author>
+  </properties>
+  <body>
+    <release version="1.0-SNAPSHOT" date="as in SVN" description="Sandbox release">
+      <action dev="sgoeschl" type="add" issue="SANDBOX-193">
+        Exposing a ExecuteWatchdog.destroy() to kill an asynchrounous process
+        manually. This formalizes a workaround described in the JIRA
+      </action>
+      <action dev="sgoeschl" type="add" issue="SANDBOX-203">
+      	Extending exit value handling to support applications returning an error
+      	code.
+      </action>    
+      <action dev="sgoeschl" type="fix" issue="SANDBOX-204">
+        Cleaned up the source code to get rid of javadoc errors and
+        unused imports.
+      </action>    
+      <action dev="sgoeschl" type="add" issue="SANDBOX-204">
+        Added a few regression tests for the watchdog since they were missing.
+      </action>    
+    </release>
+  </body>
+</document>

Modified: commons/sandbox/exec/trunk/src/main/java/org/apache/commons/exec/ExecuteWatchdog.java
URL: http://svn.apache.org/viewvc/commons/sandbox/exec/trunk/src/main/java/org/apache/commons/exec/ExecuteWatchdog.java?rev=600905&r1=600904&r2=600905&view=diff
==============================================================================
--- commons/sandbox/exec/trunk/src/main/java/org/apache/commons/exec/ExecuteWatchdog.java (original)
+++ commons/sandbox/exec/trunk/src/main/java/org/apache/commons/exec/ExecuteWatchdog.java Tue Dec  4 04:11:05 2007
@@ -42,13 +42,13 @@
     private Process process;
 
     /** Say whether or not the watchdog is currently monitoring a process. */
-    private boolean watch = false;
+    private boolean watch;
 
     /** Exception that might be thrown during the process execution. */
-    private Exception caught = null;
+    private Exception caught;
 
     /** Say whether or not the process was killed due to running overtime. */
-    private boolean killedProcess = false;
+    private boolean killedProcess;
 
     /** Will tell us whether timeout has occurred. */
     private Watchdog watchdog;
@@ -61,8 +61,10 @@
      *            greater than 0.
      */
     public ExecuteWatchdog(final long timeout) {
-        watchdog = new Watchdog(timeout);
-        watchdog.addTimeoutObserver(this);
+        this.killedProcess = false;
+        this.watch = false;
+        this.watchdog = new Watchdog(timeout);
+        this.watchdog.addTimeoutObserver(this);
     }
 
     /**
@@ -99,17 +101,27 @@
     }
 
     /**
+     * Destroys the running process manually.
+     */
+    public synchronized void destroy() {
+        this.timeoutOccured(new Watchdog(1));
+        this.stop();
+    }
+
+    /**
      * Called after watchdog has finished.
      */
-    public void timeoutOccured(final Watchdog w) {
+    public synchronized void timeoutOccured(final Watchdog w) {
         try {
             try {
                 // We must check if the process was not stopped
                 // before being here
-                process.exitValue();
+                if(process != null) {
+                    process.exitValue();
+                }
             } catch (IllegalThreadStateException itse) {
                 // the process is not terminated, if this is really
-                // a timeout and not a manual stop then kill it.
+                // a timeout and not a manual stop then destroy it.
                 if (watch) {
                     killedProcess = true;
                     process.destroy();
@@ -122,13 +134,6 @@
         }
     }
 
-    /**
-     * reset the monitor flag and the process.
-     */
-    protected void cleanUp() {
-        watch = false;
-        process = null;
-    }
 
     /**
      * This method will rethrow the exception that was possibly caught during
@@ -140,7 +145,7 @@
      *             a wrapped exception over the one that was silently swallowed
      *             and stored during the process run.
      */
-    public void checkException() throws Exception {
+    public synchronized void checkException() throws Exception {
         if (caught != null) {
             throw caught;
         }
@@ -152,17 +157,25 @@
      * @return <tt>true</tt> if the process is still running, otherwise
      *         <tt>false</tt>.
      */
-    public boolean isWatching() {
+    public synchronized boolean isWatching() {
         return watch;
     }
 
     /**
-     * Indicates whether the last process run was killed on timeout or not.
+     * Indicates whether the last process run was killed.
      * 
-     * @return <tt>true</tt> if the process was killed otherwise
+     * @return <tt>true</tt> if the process was killed
      *         <tt>false</tt>.
      */
-    public boolean killedProcess() {
+    public synchronized boolean killedProcess() {
         return killedProcess;
     }
+
+    /**
+     * reset the monitor flag and the process.
+     */
+    protected void cleanUp() {
+        watch = false;
+        process = null;
+    }    
 }

Modified: commons/sandbox/exec/trunk/src/test/java/org/apache/commons/exec/DefaultExecutorTest.java
URL: http://svn.apache.org/viewvc/commons/sandbox/exec/trunk/src/test/java/org/apache/commons/exec/DefaultExecutorTest.java?rev=600905&r1=600904&r2=600905&view=diff
==============================================================================
--- commons/sandbox/exec/trunk/src/test/java/org/apache/commons/exec/DefaultExecutorTest.java (original)
+++ commons/sandbox/exec/trunk/src/test/java/org/apache/commons/exec/DefaultExecutorTest.java Tue Dec  4 04:11:05 2007
@@ -139,6 +139,40 @@
     }
 
     /**
+     * Start a async process and terminate it manually before the
+     * wacthdog timeout occurs. 
+     */
+    public void testExecuteAsyncWithTimelyUserTermination() throws Exception {
+        CommandLine cl = new CommandLine(foreverTestScript);
+        ExecuteWatchdog watchdog = new ExecuteWatchdog(Integer.MAX_VALUE);
+        exec.setWatchdog(watchdog);
+        MockExecuteResultHandler handler = new MockExecuteResultHandler();
+        exec.execute(cl, handler);
+        // wait for script to run
+        Thread.sleep(2000);
+        // teminate it
+        watchdog.destroy();
+        assertTrue(watchdog.killedProcess());
+    }
+
+    /**
+     * Start a async process and try to terminate it manually but
+     * the process was already terminated by the watchdog.
+     */
+    public void testExecuteAsyncWithTooLateUserTermination() throws Exception {
+        CommandLine cl = new CommandLine(foreverTestScript);
+        ExecuteWatchdog watchdog = new ExecuteWatchdog(3000);
+        exec.setWatchdog(watchdog);
+        MockExecuteResultHandler handler = new MockExecuteResultHandler();
+        exec.execute(cl, handler);
+        // wait for script to be terminated by the watchdog
+        Thread.sleep(6000);
+        // try to teminate the already terminated process
+        watchdog.destroy();
+        assertTrue(watchdog.killedProcess());
+    }
+
+    /**
      * Start a scipt looping forever and check if the ExecuteWatchdog
      * kicks in killing the run away process.
      */