1
2
3
4
5
6
7
8
9
10
11 package org.mule.util;
12
13 import org.mule.MuleManager;
14 import org.mule.MuleRuntimeException;
15 import org.mule.config.i18n.MessageFactory;
16
17 import java.io.BufferedOutputStream;
18 import java.io.BufferedWriter;
19 import java.io.File;
20 import java.io.FileInputStream;
21 import java.io.FileOutputStream;
22 import java.io.FileWriter;
23 import java.io.IOException;
24 import java.io.InputStream;
25 import java.io.OutputStream;
26 import java.io.UnsupportedEncodingException;
27 import java.net.JarURLConnection;
28 import java.net.URI;
29 import java.net.URL;
30 import java.net.URLConnection;
31 import java.net.URLDecoder;
32 import java.util.Enumeration;
33 import java.util.jar.JarEntry;
34 import java.util.jar.JarFile;
35 import java.util.zip.ZipEntry;
36 import java.util.zip.ZipFile;
37
38 import org.apache.commons.lang.StringUtils;
39 import org.apache.commons.logging.Log;
40 import org.apache.commons.logging.LogFactory;
41
42
43
44
45
46
47 public class FileUtils extends org.apache.commons.io.FileUtils
48 {
49 private static final Log logger = LogFactory.getLog(FileUtils.class);
50
51 public static synchronized void copyStreamToFile(InputStream input, File destination) throws IOException
52 {
53 if (destination.exists() && !destination.canWrite())
54 {
55 throw new IOException("Destination file does not exist or is not writeable");
56 }
57
58 try
59 {
60 FileOutputStream output = new FileOutputStream(destination);
61 try
62 {
63 IOUtils.copy(input, output);
64 }
65 finally
66 {
67 IOUtils.closeQuietly(output);
68 }
69 }
70 finally
71 {
72 IOUtils.closeQuietly(input);
73 }
74 }
75
76
77 public static File createFile(String filename) throws IOException
78 {
79 File file = FileUtils.newFile(filename);
80 if (!file.canWrite())
81 {
82 String dirName = file.getPath();
83 int i = dirName.lastIndexOf(File.separator);
84 if (i > -1)
85 {
86 dirName = dirName.substring(0, i);
87 File dir = FileUtils.newFile(dirName);
88 dir.mkdirs();
89 }
90 file.createNewFile();
91 }
92 return file;
93 }
94
95
96 public static String prepareWinFilename(String filename)
97 {
98 filename = filename.replaceAll("<", "(");
99 filename = filename.replaceAll(">", ")");
100 filename = filename.replaceAll("[/\\*?|:;\\]\\[\"]", "-");
101 return filename;
102 }
103
104
105 public static File openDirectory(String directory) throws IOException
106 {
107 File dir = FileUtils.newFile(directory);
108 if (!dir.exists())
109 {
110 dir.mkdirs();
111 }
112 if (!dir.isDirectory() || !dir.canRead())
113 {
114 throw new IOException("Path: " + directory + " exists but isn't a directory");
115 }
116 return dir;
117 }
118
119
120
121
122
123
124
125
126
127 public static File stringToFile(String filename, String data) throws IOException
128 {
129 return stringToFile(filename, data, false);
130 }
131
132
133 public static synchronized File stringToFile(String filename, String data, boolean append)
134 throws IOException
135 {
136 return stringToFile(filename, data, append, false);
137 }
138
139
140 public static synchronized File stringToFile(String filename, String data, boolean append, boolean newLine)
141 throws IOException
142 {
143 File f = createFile(filename);
144 BufferedWriter writer = null;
145 try
146 {
147 writer = new BufferedWriter(new FileWriter(f, append));
148 writer.write(data);
149 if (newLine)
150 {
151 writer.newLine();
152 }
153 }
154 finally
155 {
156 if (writer != null)
157 {
158 writer.close();
159 }
160 }
161 return f;
162 }
163
164
165 public static String getResourcePath(String resourceName, Class callingClass) throws IOException
166 {
167 return getResourcePath(resourceName, callingClass, MuleManager.getConfiguration().getEncoding());
168 }
169
170
171 public static String getResourcePath(String resourceName, Class callingClass, String encoding)
172 throws IOException
173 {
174 if (resourceName == null)
175 {
176
177 return null;
178 }
179
180 URL url = IOUtils.getResourceAsUrl(resourceName, callingClass);
181 if (url == null)
182 {
183
184 return null;
185 }
186 return normalizeFilePath(url, encoding);
187 }
188
189
190
191
192
193
194
195
196
197
198 public static String normalizeFilePath(URL url, String encoding) throws UnsupportedEncodingException
199 {
200 String resource = URLDecoder.decode(url.toExternalForm(), encoding);
201 if (resource != null)
202 {
203 if (resource.startsWith("file:/"))
204 {
205 resource = resource.substring(6);
206 }
207 if (!resource.startsWith(File.separator))
208 {
209 resource = File.separator + resource;
210 }
211 }
212 return resource;
213 }
214
215
216
217
218
219
220
221 public static boolean deleteTree(File dir)
222 {
223 return deleteTree(dir, null);
224 }
225
226
227
228
229
230
231
232
233
234
235
236 public static boolean deleteTree(File dir, final String[] topLevelDirsToIgnore)
237 {
238 if (dir == null || !dir.exists())
239 {
240 return true;
241 }
242 File[] files = dir.listFiles();
243 if (files != null)
244 {
245 for (int i = 0; i < files.length; i++)
246 {
247 OUTER:
248 if (files[i].isDirectory())
249 {
250 if (topLevelDirsToIgnore != null)
251 {
252 for (int j = 0; j < topLevelDirsToIgnore.length; j++)
253 {
254 String ignored = topLevelDirsToIgnore[j];
255 if (ignored.equals(FilenameUtils.getBaseName(files[i].getName())))
256 {
257 break OUTER;
258 }
259 }
260 }
261 if (!deleteTree(files[i]))
262 {
263 return false;
264 }
265 }
266 else
267 {
268 if (!files[i].delete())
269 {
270 return false;
271 }
272 }
273 }
274 }
275 return dir.delete();
276 }
277
278
279
280
281 public static void unzip(File archive, File directory) throws IOException
282 {
283 ZipFile zip = null;
284
285 if (directory.exists())
286 {
287 if (!directory.isDirectory())
288 {
289 throw new IOException("Directory is not a directory: " + directory);
290 }
291 }
292 else
293 {
294 if (!directory.mkdirs())
295 {
296 throw new IOException("Could not create directory: " + directory);
297 }
298 }
299 try
300 {
301 zip = new ZipFile(archive);
302 for (Enumeration entries = zip.entries(); entries.hasMoreElements();)
303 {
304 ZipEntry entry = (ZipEntry) entries.nextElement();
305 File f = FileUtils.newFile(directory, entry.getName());
306 if (entry.isDirectory())
307 {
308 if (!f.mkdirs())
309 {
310 throw new IOException("Could not create directory: " + f);
311 }
312 }
313 else
314 {
315 InputStream is = zip.getInputStream(entry);
316 OutputStream os = new BufferedOutputStream(new FileOutputStream(f));
317 IOUtils.copy(is, os);
318 IOUtils.closeQuietly(is);
319 IOUtils.closeQuietly(os);
320 }
321 }
322 }
323 finally
324 {
325 if (zip != null)
326 {
327 zip.close();
328 }
329 }
330 }
331
332
333
334
335
336
337
338
339
340
341
342 public static File newFile(String pathName)
343 {
344 try
345 {
346 return new File(pathName).getCanonicalFile();
347 }
348 catch (IOException e)
349 {
350 throw new MuleRuntimeException(
351 MessageFactory.createStaticMessage("Unable to create a canonical file for " + pathName),
352 e);
353 }
354 }
355
356
357
358
359
360
361
362
363
364
365
366 public static File newFile(URI uri)
367 {
368 try
369 {
370 return new File(uri).getCanonicalFile();
371 }
372 catch (IOException e)
373 {
374 throw new MuleRuntimeException(
375 MessageFactory.createStaticMessage("Unable to create a canonical file for " + uri),
376 e);
377 }
378 }
379
380
381
382
383
384
385
386
387
388
389
390 public static File newFile(File parent, String child)
391 {
392 try
393 {
394 return new File(parent, child).getCanonicalFile();
395 }
396 catch (IOException e)
397 {
398 throw new MuleRuntimeException(
399 MessageFactory.createStaticMessage("Unable to create a canonical file for parent: "
400 + parent + " and child: " + child),
401 e);
402 }
403 }
404
405
406
407
408
409
410
411
412
413
414
415 public static File newFile(String parent, String child)
416 {
417 try
418 {
419 return new File(parent, child).getCanonicalFile();
420 }
421 catch (IOException e)
422 {
423 throw new MuleRuntimeException(
424 MessageFactory.createStaticMessage("Unable to create a canonical file for parent: "
425 + parent + " and child: " + child),
426 e);
427 }
428 }
429
430
431
432
433
434
435
436
437
438
439
440 public static void extractResources(String resourceName, Class callingClass, File outputDir, boolean keepParentDirectory) throws IOException
441 {
442 URL url = callingClass.getClassLoader().getResource(resourceName);
443 URLConnection connection = url.openConnection();
444 if (connection instanceof JarURLConnection)
445 {
446 extractJarResources((JarURLConnection) connection, outputDir, keepParentDirectory);
447 }
448 else
449 {
450 extractFileResources(normalizeFilePath(url, MuleManager.getConfiguration().getEncoding()), outputDir, resourceName, keepParentDirectory);
451 }
452 }
453
454
455
456
457
458
459
460
461
462
463 private static void extractFileResources(String path, File outputDir, String resourceName, boolean keepParentDirectory) throws IOException
464 {
465 File file = FileUtils.newFile(path);
466 if (!file.exists())
467 {
468 throw new IOException("The resource by path " + path + " ");
469 }
470 if (file.isDirectory())
471 {
472 if (keepParentDirectory)
473 {
474 outputDir = FileUtils.newFile(outputDir.getPath() + File.separator + resourceName);
475 if (!outputDir.exists())
476 {
477 outputDir.mkdirs();
478 }
479 }
480 else
481 {
482 outputDir = FileUtils.newFile(outputDir.getPath());
483 }
484 copyDirectory(file, outputDir);
485 }
486 else
487 {
488
489 if (keepParentDirectory)
490 {
491 outputDir = FileUtils.newFile(outputDir.getPath() + File.separator + resourceName);
492 }
493 else
494 {
495 outputDir = FileUtils.newFile(outputDir.getPath() + File.separator + file.getName());
496 }
497 copyFile(file, outputDir);
498 }
499 }
500
501
502
503
504
505
506
507
508
509 private static void extractJarResources(JarURLConnection connection, File outputDir, boolean keepParentDirectory) throws IOException
510 {
511 JarFile jarFile = connection.getJarFile();
512 JarEntry jarResource = connection.getJarEntry();
513 Enumeration entries = jarFile.entries();
514 InputStream inputStream = null;
515 OutputStream outputStream = null;
516 int jarResourceNameLenght = jarResource.getName().length();
517 for (; entries.hasMoreElements();)
518 {
519 JarEntry entry = (JarEntry) entries.nextElement();
520 if (entry.getName().startsWith(jarResource.getName()))
521 {
522
523 String path = outputDir.getPath() + File.separator + entry.getName();
524
525
526 if (!keepParentDirectory)
527 {
528 if (entry.isDirectory())
529 {
530 if (entry.getName().equals(jarResource.getName()))
531 {
532 continue;
533 }
534 path = outputDir.getPath() + File.separator + entry.getName().substring(jarResourceNameLenght, entry.getName().length());
535 }
536 else
537 {
538 if (entry.getName().length() > jarResourceNameLenght)
539 {
540 path = outputDir.getPath() + File.separator + entry.getName().substring(jarResourceNameLenght, entry.getName().length());
541 }
542 else
543 {
544 path = outputDir.getPath() + File.separator + entry.getName().substring(entry.getName().lastIndexOf("/"), entry.getName().length());
545 }
546 }
547 }
548
549 File file = FileUtils.newFile(path);
550 if (!file.getParentFile().exists())
551 {
552 if (!file.getParentFile().mkdirs())
553 {
554 throw new IOException("Could not create directory: " + file.getParentFile());
555 }
556 }
557 if (entry.isDirectory())
558 {
559 if (!file.exists() && !file.mkdirs())
560 {
561 throw new IOException("Could not create directory: " + file);
562 }
563
564 }
565 else
566 {
567 try
568 {
569 inputStream = jarFile.getInputStream(entry);
570 outputStream = new BufferedOutputStream(new FileOutputStream(file));
571 IOUtils.copy(inputStream, outputStream);
572 }
573 finally
574 {
575 IOUtils.closeQuietly(inputStream);
576 IOUtils.closeQuietly(outputStream);
577 }
578 }
579
580 }
581 }
582 }
583
584 public static boolean renameFileHard(String srcFilePath, String destFilePath)
585 {
586 if (StringUtils.isNotBlank(srcFilePath) && StringUtils.isNotBlank(destFilePath))
587 {
588 return renameFileHard(new File(srcFilePath), new File(destFilePath));
589 }
590 else
591 {
592 return false;
593 }
594 }
595
596 public static boolean renameFileHard(File srcFile, File destFile)
597 {
598 boolean isRenamed = false;
599 if (srcFile != null && destFile != null)
600 {
601 logger.debug("Moving file " + srcFile.getAbsolutePath() + " to " + destFile.getAbsolutePath());
602 if (!destFile.exists())
603 {
604 try
605 {
606 if (srcFile.isFile())
607 {
608 logger.debug("Trying to rename file");
609 FileInputStream in = null;
610 FileOutputStream out = null;
611 try
612 {
613 in = new FileInputStream(srcFile);
614 out = new FileOutputStream(destFile);
615 out.getChannel().transferFrom(in.getChannel(), 0, srcFile.length());
616 isRenamed = true;
617 }
618 catch (Exception e)
619 {
620 logger.debug(e);
621 }
622 finally
623 {
624 if (in != null)
625 {
626 try
627 {
628 in.close();
629 }
630 catch (Exception inNotClosed)
631 {
632 logger.debug(inNotClosed);
633 }
634 }
635 if (out != null)
636 {
637 try
638 {
639 out.close();
640 }
641 catch (Exception outNotClosed)
642 {
643 logger.debug(outNotClosed);
644 }
645 }
646 }
647 logger.debug("File renamed: " + isRenamed);
648 if (isRenamed)
649 {
650 srcFile.delete();
651 }
652 else
653 {
654 destFile.delete();
655 }
656 }
657 else
658 {
659 logger.debug(srcFile.getAbsolutePath() + " is not a valid file.");
660 }
661 }
662 catch (Exception e)
663 {
664 logger.debug("Error renaming file from " + srcFile.getAbsolutePath() + " to " + destFile.getAbsolutePath());
665 }
666 }
667 else
668 {
669 logger.debug("Error renaming file " + srcFile.getAbsolutePath() + ". Destination file " + destFile.getAbsolutePath() + " already exists.");
670 }
671 }
672 return isRenamed;
673 }
674
675 public static boolean renameFile(String srcFilePath, String destFilePath)
676 {
677 if (StringUtils.isNotBlank(srcFilePath) && StringUtils.isNotBlank(destFilePath))
678 {
679 return renameFile(new File(srcFilePath), new File(destFilePath));
680 }
681 else
682 {
683 return false;
684 }
685 }
686
687 public static boolean renameFile(File srcFile, File destFile)
688 {
689 boolean isRenamed = false;
690 if (srcFile != null && destFile != null)
691 {
692 logger.debug("Moving file " + srcFile.getAbsolutePath() + " to " + destFile.getAbsolutePath());
693 if (!destFile.exists())
694 {
695 try
696 {
697 if (srcFile.isFile())
698 {
699 logger.debug("Trying to rename file");
700 isRenamed = srcFile.renameTo(destFile);
701 if (!isRenamed && srcFile.exists())
702 {
703 logger.debug("Trying hard copy, assuming partition crossing ...");
704 isRenamed = renameFileHard(srcFile, destFile);
705 }
706 logger.debug("File renamed: " + isRenamed);
707 }
708 else
709 {
710 logger.debug(srcFile.getAbsolutePath() + " is not a valid file");
711 }
712 }
713 catch (Exception e)
714 {
715 logger.debug("Error moving file from " + srcFile.getAbsolutePath() + " to " + destFile.getAbsolutePath(), e);
716 }
717 }
718 else
719 {
720 logger.debug("Error renaming file " + srcFile.getAbsolutePath() + ". Destination file " + destFile.getAbsolutePath() + " already exists.");
721 }
722 }
723 else
724 {
725 logger.debug("Error renaming file. Source or destination file is null.");
726 }
727
728 return isRenamed;
729 }
730 }