You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@maven.apache.org by be...@apache.org on 2010/08/14 14:12:13 UTC

svn commit: r985474 - in /maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean: CleanMojo.java Cleaner.java

Author: bentmann
Date: Sat Aug 14 12:12:13 2010
New Revision: 985474

URL: http://svn.apache.org/viewvc?rev=985474&view=rev
Log:
[MCLEAN-45] Clean plugin should support a silent retry in case the first attemp fails

o Added parameter to disable re-attempts as suggested by Brett

Modified:
    maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/CleanMojo.java
    maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/Cleaner.java

Modified: maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/CleanMojo.java
URL: http://svn.apache.org/viewvc/maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/CleanMojo.java?rev=985474&r1=985473&r2=985474&view=diff
==============================================================================
--- maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/CleanMojo.java (original)
+++ maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/CleanMojo.java Sat Aug 14 12:12:13 2010
@@ -131,6 +131,16 @@ public class CleanMojo
     private boolean failOnError;
 
     /**
+     * Indicates whether the plugin should undertake additional attempts (after a short delay) to delete a file if the
+     * first attempt failed. This is meant to help deleting files that are temporarily locked by third-party tools like
+     * virus scanners or search indexing.
+     * 
+     * @parameter expression="${maven.clean.retryOnError}" default-value="true"
+     * @since 2.4.2
+     */
+    private boolean retryOnError;
+
+    /**
      * Disables the deletion of the default output directories configured for a project. If set to <code>true</code>,
      * only the files/directories selected via the parameter {@link #filesets} will be deleted.
      * 
@@ -165,7 +175,7 @@ public class CleanMojo
                 File directory = directories[i];
                 if ( directory != null )
                 {
-                    cleaner.delete( directory, null, followSymLinks, failOnError );
+                    cleaner.delete( directory, null, followSymLinks, failOnError, retryOnError );
                 }
             }
 
@@ -179,7 +189,8 @@ public class CleanMojo
                         throw new MojoExecutionException( "Missing base directory for " + fileset );
                     }
                     GlobSelector selector = new GlobSelector( fileset.getIncludes(), fileset.getExcludes() );
-                    cleaner.delete( fileset.getDirectory(), selector, fileset.isFollowSymlinks(), failOnError );
+                    cleaner.delete( fileset.getDirectory(), selector, fileset.isFollowSymlinks(), failOnError,
+                                    retryOnError );
                 }
             }
         }

Modified: maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/Cleaner.java
URL: http://svn.apache.org/viewvc/maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/Cleaner.java?rev=985474&r1=985473&r2=985474&view=diff
==============================================================================
--- maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/Cleaner.java (original)
+++ maven/plugins/trunk/maven-clean-plugin/src/main/java/org/apache/maven/plugin/clean/Cleaner.java Sat Aug 14 12:12:13 2010
@@ -87,9 +87,11 @@ class Cleaner
      *            everything.
      * @param followSymlinks Whether to follow symlinks.
      * @param failOnError Whether to abort with an exception in case a selected file/directory could not be deleted.
+     * @param retryOnError Whether to undertake additional delete attempts in case the first attempt failed.
      * @throws IOException If a file/directory could not be deleted and <code>failOnError</code> is <code>true</code>.
      */
-    public void delete( File basedir, Selector selector, boolean followSymlinks, boolean failOnError )
+    public void delete( File basedir, Selector selector, boolean followSymlinks, boolean failOnError,
+                        boolean retryOnError )
         throws IOException
     {
         if ( !basedir.isDirectory() )
@@ -112,7 +114,7 @@ class Cleaner
 
         File file = followSymlinks ? basedir : basedir.getCanonicalFile();
 
-        delete( file, "", selector, followSymlinks, failOnError );
+        delete( file, "", selector, followSymlinks, failOnError, retryOnError );
     }
 
     /**
@@ -126,10 +128,12 @@ class Cleaner
      *            everything.
      * @param followSymlinks Whether to follow symlinks.
      * @param failOnError Whether to abort with an exception in case a selected file/directory could not be deleted.
+     * @param retryOnError Whether to undertake additional delete attempts in case the first attempt failed.
      * @return The result of the cleaning, never <code>null</code>.
      * @throws IOException If a file/directory could not be deleted and <code>failOnError</code> is <code>true</code>.
      */
-    private Result delete( File file, String pathname, Selector selector, boolean followSymlinks, boolean failOnError )
+    private Result delete( File file, String pathname, Selector selector, boolean followSymlinks, boolean failOnError,
+                           boolean retryOnError )
         throws IOException
     {
         Result result = new Result();
@@ -151,7 +155,8 @@ class Cleaner
                         {
                             String filename = filenames[i];
                             File child = new File( canonical, filename );
-                            result.update( delete( child, prefix + filename, selector, followSymlinks, failOnError ) );
+                            result.update( delete( child, prefix + filename, selector, followSymlinks, failOnError,
+                                                   retryOnError ) );
                         }
                     }
                 }
@@ -183,7 +188,7 @@ class Cleaner
                     logVerbose.log( "Deleting dangling symlink " + file );
                 }
             }
-            result.failures += delete( file, failOnError );
+            result.failures += delete( file, failOnError, retryOnError );
         }
         else
         {
@@ -199,34 +204,42 @@ class Cleaner
      * 
      * @param file The file/directory to delete, must not be <code>null</code>.
      * @param failOnError Whether to abort with an exception in case the file/directory could not be deleted.
+     * @param retryOnError Whether to undertake additional delete attempts in case the first attempt failed.
      * @return <code>0</code> if the file was deleted, <code>1</code> otherwise.
      * @throws IOException If a file/directory could not be deleted and <code>failOnError</code> is <code>true</code>.
      */
-    private int delete( File file, boolean failOnError )
+    private int delete( File file, boolean failOnError, boolean retryOnError )
         throws IOException
     {
         if ( !file.delete() )
         {
-            if ( ON_WINDOWS )
-            {
-                // try to release any locks held by non-closed files
-                System.gc();
-            }
-
             boolean deleted = false;
 
-            int[] delays = { 125, 250, 750 };
-            for ( int i = 0; !deleted && i < delays.length; i++ )
+            if ( retryOnError )
             {
-                try
+                if ( ON_WINDOWS )
                 {
-                    Thread.sleep( delays[i] );
+                    // try to release any locks held by non-closed files
+                    System.gc();
                 }
-                catch ( InterruptedException e )
+
+                int[] delays = { 50, 250, 750 };
+                for ( int i = 0; !deleted && i < delays.length; i++ )
                 {
-                    // ignore
+                    try
+                    {
+                        Thread.sleep( delays[i] );
+                    }
+                    catch ( InterruptedException e )
+                    {
+                        // ignore
+                    }
+                    deleted = file.delete() || !file.exists();
                 }
-                deleted = file.delete() || !file.exists();
+            }
+            else
+            {
+                deleted = !file.exists();
             }
 
             if ( !deleted )