root/trunk/src/java/org/jcoderz/commons/util/FileUtils.java

Revision 1011, 11.5 kB (checked in by amandel, 7 months ago)

Aligned svn keyword settings.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
Line 
1/*
2 * $Id$
3 *
4 * Copyright 2006, The jCoderZ.org Project. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions are
8 * met:
9 *
10 *    * Redistributions of source code must retain the above copyright
11 *      notice, this list of conditions and the following disclaimer.
12 *    * Redistributions in binary form must reproduce the above
13 *      copyright notice, this list of conditions and the following
14 *      disclaimer in the documentation and/or other materials
15 *      provided with the distribution.
16 *    * Neither the name of the jCoderZ.org Project nor the names of
17 *      its contributors may be used to endorse or promote products
18 *      derived from this software without specific prior written
19 *      permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS "AS IS" AND
22 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
23 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
24 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS AND CONTRIBUTORS
25 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
26 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
27 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
28 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
29 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
30 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
31 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
32 */
33package org.jcoderz.commons.util;
34
35import java.io.File;
36import java.io.FileInputStream;
37import java.io.FileNotFoundException;
38import java.io.FileOutputStream;
39import java.io.IOException;
40import java.io.InputStream;
41import java.io.OutputStream;
42import java.io.Reader;
43import java.io.Writer;
44import java.util.ArrayList;
45import java.util.List;
46import java.util.logging.Level;
47
48
49/**
50 * This class collects some nifty file utility functions.
51 *
52 * TODO: Cleanup check vs. IoUtil
53 *
54 * @author Michael Griffel
55 * @author Andreas Mandel
56 */
57public final class FileUtils
58{
59   private static final int RND_FILENAME_FACTOR = 100000;
60
61   private static final int BUFFER_SIZE = 4096;
62
63   /**
64    * Only utility functions -- no instances allowed.
65    */
66   private FileUtils ()
67   {
68      // no instances allowed - provides only static utility functions
69   }
70
71   /**
72    * Copies the file or directory <code>src</code> to the
73    * directory <code>destinationDir</code>.
74    *
75    * @param src the source file or directory.
76    * @param destinationDir the destination directory.
77    * @throws IOException in case of an I/O error.
78    */
79   public static void copy (File src, File destinationDir)
80         throws IOException
81   {
82      if (src.isFile())
83      {
84         copyFile(src, destinationDir);
85      }
86      else if (src.isDirectory())
87      {
88         final File subdir = new File(destinationDir, src.getName());
89         if (!subdir.exists())
90         {
91            if (!subdir.mkdir())
92            {
93               throw new IOException("Failed to create subdir '" + subdir
94                     + "'.");
95            }
96         }
97         final File [] files = src.listFiles();
98         for (int i = 0; i < files.length; i++)
99         {
100            copy(files[i], subdir);
101         }
102      }
103   }
104
105   /**
106    * Copies the file <code>src</code> to the file or directory
107    * <code>dest</code>.
108    *
109    * @param src The source file.
110    * @param dest The destination file or directory.
111    * @throws FileNotFoundException if the source file does not exists.
112    * @throws IOException in case of an I/O error.
113    */
114   public static void copyFile (File src, File dest)
115         throws FileNotFoundException, IOException
116   {
117      FileInputStream in = null;
118      FileOutputStream out = null;
119      try
120      {
121         in = new FileInputStream(src);
122         if (dest.isDirectory())
123         {
124            out = new FileOutputStream(new File(dest, src.getName()));
125         }
126         else
127         {
128            out = new FileOutputStream(dest);
129         }
130         copy(in, out);
131      }
132      finally
133      {
134         close(in);
135         close(out);
136      }
137   }
138
139
140   /**
141    * Copy from an input stream to an output stream.
142    *
143    * @param in The input stream.
144    * @param out The output stream.
145    * @throws IOException when an error happens during a read or a write
146    *       operation.
147    */
148   public static void copy (InputStream in, OutputStream out)
149         throws IOException
150   {
151      final byte[] buffer = new byte[BUFFER_SIZE];
152      int read;
153      while ((read = in.read(buffer)) != -1)
154      {
155         out.write(buffer, 0, read);
156      }
157   }
158
159
160   /**
161    * Copy all files under <code>srcDir</code> to the directory
162    * <code>dst</code>.
163    *
164    * Unix command:
165    * <pre>
166    * $ cp "$scrDir/*" "$dst"
167    * </pre>
168    *
169    * @param srcDir the source directory.
170    * @param dst the destination directory.
171    * @throws IOException in case of an I/O error.
172    */
173   public static void copySlashStar (File srcDir, File dst)
174         throws IOException
175   {
176      if (srcDir.isDirectory())
177      {
178         final File[] files = srcDir.listFiles();
179         for (int i = 0; i < files.length; i++)
180         {
181            copy(files[i], dst);
182         }
183      }
184      else
185      {
186         throw new IllegalArgumentException("Souce must be a directory. ('"
187               + srcDir + "')");
188      }
189   }
190
191   /**
192    * Creates a temporary directory.
193    * @param baseDir the base directory.
194    * @param prefix prefix for the temporary directory.
195    * @return a temporary directory.
196    * @throws IOException in case of an I/O error.
197    */
198   public static File createTempDir (File baseDir, String prefix)
199         throws IOException
200   {
201      final String dirname = prefix
202            + String.valueOf((int) (Math.random() * RND_FILENAME_FACTOR));
203
204      final File tempDir = new File(baseDir, dirname);
205
206      if (! tempDir.mkdir())
207      {
208         throw new IOException("Cannot create temp directory '"
209               + tempDir + "'");
210      }
211      return tempDir;
212   }
213
214   /**
215    * Closes the input stream (safe).
216    *
217    * This method tries to close the given input stream and
218    * if an IOException occurs a message with the level
219    * {@link Level#FINE} is logged. It's safe to pass a
220    * <code>null</code> reference for the argument.
221    *
222    * @param in the input stream that should be closed.
223    * @deprecated use IoUtil.close(InputStream)
224    */
225   public static void close (InputStream in)
226   {
227       IoUtil.close(in);
228   }
229
230   /**
231    * Closes the output stream (safe).
232    *
233    * This method tries to close the given output stream and
234    * if an IOException occurs a message with the level
235    * {@link Level#FINE} is logged. It's safe to pass a
236    * <code>null</code> reference for the argument.
237    *
238    * @param out the output stream that should be closed.
239    * @deprecated use IoUtil.close(OutputStream)
240    */
241   public static void close (OutputStream out)
242   {
243       IoUtil.close(out);
244   }
245
246   /**
247    * Closes the reader (safe).
248    *
249    * This method tries to close the given reader and if an IOException occurs
250    * a message with the level {@link Level#FINE} is logged. It's safe
251    * to pass a <code>null</code> reference for the argument.
252    *
253    * @param reader the reader that should be closed.
254    * @deprecated use IoUtil.close(Reader)
255    */
256   public static void safeClose (Reader reader)
257   {
258       IoUtil.close(reader);
259   }
260
261   /**
262    * Closes the writer (safe).
263    *
264    * This method tries to close the given writer and if an IOException occurs
265    * a message with the level {@link Level#FINE} is logged. It's safe
266    * to pass a <code>null</code> reference for the argument.
267    *
268    * @param writer the writer that should be closed.
269    * @deprecated use IoUtil.close(Writer)
270    */
271   public static void safeClose (Writer writer)
272   {
273       IoUtil.close(writer);
274   }
275
276
277   /**
278    * Search for files in a directory hierarchy.
279    *
280    * Unix command:
281    * <pre>
282    * find path -name pattern
283    * </pre>
284    * @param path root directory.
285    * @param pattern filename pattern.
286    * @return a list of files matching the given <code>pattern</code>
287    *         under <code>path</code>.
288    */
289   public static List findFile (File path, String pattern)
290   {
291      final List ret = new ArrayList();
292
293      // Check whether the path exists
294      if (!path.exists())
295      {
296         throw new IllegalArgumentException(
297               "The specified path does not exist! ('"
298               + path + "')");
299      }
300
301      findFile(path, pattern, ret);
302
303      return ret;
304   }
305
306   private static void findFile (File file, String pattern, List found)
307   {
308      if (file.isDirectory())
309      {
310         final File[] files = file.listFiles();
311         for (int i = 0; i < files.length; i++)
312         {
313            findFile(files[i], pattern, found);
314         }
315      }
316      else
317      {
318         if (file.getName().matches(pattern))
319         {
320            found.add(file);
321         }
322      }
323   }
324
325   /**
326    * Remove file or directory.
327    *
328    * Unix command:
329    * <pre>
330    * rm -rf file
331    * </pre>
332    * @param file the file or directory to delete.
333    * @throws IOException in case of an I/O error.
334    */
335   public static void rmdir (File file)
336         throws IOException
337   {
338      if (file == null)
339      {
340         // done...
341      }
342      else if (file.isDirectory())
343      {
344         final File [] files = file.listFiles();
345         for (int i = 0; i < files.length; i++)
346         {
347            rmdir(files[i]);
348         }
349         if (!file.delete())
350         {
351            throw new IOException("Failed to delete directory " + file + ".");
352         }
353      }
354      else
355      {
356         if (!file.delete())
357         {
358            throw new IOException("Failed to delete file " + file + ".");
359         }
360      }
361   }
362
363   /**
364    * Returns the relative path of <code>file</code> to the file
365    * <code>basedir</code>.
366    * @param baseDir the base directory or file.
367    * @param file the file.
368    * @return the relative path of the file to the basedir.
369    * @throws IOException in case of an I/O error.
370    */
371   public static String getRelativePath (File baseDir, File file)
372         throws IOException
373   {
374      final String base = baseDir.getCanonicalPath();
375      String fileName = file.getCanonicalPath();
376
377      if (fileName.startsWith(base))
378      {
379         fileName = fileName.substring(base.length());
380         if (fileName.charAt(0) == '/')
381         {
382            fileName = fileName.substring(1);
383         }
384      }
385      else
386      {
387         throw new RuntimeException("Cannot add file '" + file
388               + "' with different baseDir '" + baseDir + "'.");
389      }
390      return fileName;
391   }
392
393   /**
394    * Renames the file <code>aFile</code>.
395    *
396    * @param  aFile The file to be renamed.
397    * @param  dest  The new abstract pathname for the named file
398    * @throws IOException if the the renaming was not successful.
399    */
400   public static void rename (File aFile, File dest)
401         throws IOException
402   {
403      if (!aFile.renameTo(dest))
404      {
405         throw new IOException("Failed to rename " + aFile + " to " + dest);
406      }
407   }
408
409   /**
410    * Deletes the given file <code>aFile</code>.
411    *
412    * @param  aFile The file to be deleted.
413    * @throws IOException if the the deletion was not successful.
414    */
415   public static void delete (File aFile)
416         throws IOException
417   {
418      if (aFile.exists())
419      {
420         if (!aFile.delete())
421         {
422            throw new IOException("Failed to delete " + aFile);
423         }
424      }
425   }
426}
Note: See TracBrowser for help on using the browser.