KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > nightlabs > util > Utils


1 /* ************************************************************************** *
2  * Copyright (C) 2004 NightLabs GmbH, Marco Schulze *
3  * All rights reserved. *
4  * http://www.NightLabs.de *
5  * *
6  * This program and the accompanying materials are free software; you can re- *
7  * distribute it and/or modify it under the terms of the GNU General Public *
8  * License as published by the Free Software Foundation; either ver 2 of the *
9  * License, or any later version. *
10  * *
11  * This module is distributed in the hope that it will be useful, but WITHOUT *
12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FIT- *
13  * NESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more *
14  * details. *
15  * *
16  * You should have received a copy of the GNU General Public License along *
17  * with this module; if not, write to the Free Software Foundation, Inc.: *
18  * 59 Temple Place, Suite 330 *
19  * Boston MA 02111-1307 *
20  * USA *
21  * *
22  * Or get it online: *
23  * http://www.opensource.org/licenses/gpl-license.php *
24  * *
25  * In case, you want to use this module or parts of it in a proprietary pro- *
26  * ject, you can purchase it under the NightLabs Commercial License. Please *
27  * contact NightLabs GmbH under info AT nightlabs DOT com for more infos or *
28  * visit http://www.NightLabs.com *
29  * ************************************************************************** */

30
31 package com.nightlabs.util;
32
33 import java.io.DataInputStream JavaDoc;
34 import java.io.File JavaDoc;
35 import java.io.FileInputStream JavaDoc;
36 import java.io.FileOutputStream JavaDoc;
37 import java.io.IOException JavaDoc;
38 import java.io.InputStream JavaDoc;
39 import java.lang.reflect.Array JavaDoc;
40 import java.security.MessageDigest JavaDoc;
41 import java.security.NoSuchAlgorithmException JavaDoc;
42 import java.util.ArrayList JavaDoc;
43 import java.util.Collection JavaDoc;
44 import java.util.HashSet JavaDoc;
45 import java.util.Iterator JavaDoc;
46 import java.util.LinkedList JavaDoc;
47 import java.util.List JavaDoc;
48 import java.util.StringTokenizer JavaDoc;
49
50 /**
51  * This is a collection of utility functions. All methods
52  * of this class are static.
53  * @author Alex Bieber, Marc Klinger, Marco Schulze, Niklas Schiffler
54  * @version 1.0
55  */

56 public abstract class Utils
57 {
58     public static String JavaDoc addFinalSlash(String JavaDoc directory)
59     {
60         if (directory.endsWith(File.separator))
61             return directory;
62         else
63             return directory + File.separator;
64
65     }
66
67     public static String JavaDoc int2StringMinDigits(int i, int minDigits)
68     {
69         String JavaDoc s = Integer.toString(i);
70         if (s.length() < minDigits) {
71             StringBuffer JavaDoc sBuf = new StringBuffer JavaDoc(s);
72             while (sBuf.length() < minDigits)
73                 sBuf.insert(0, '0');
74
75             s = sBuf.toString();
76         }
77
78         return s;
79     }
80
81     public static String JavaDoc getRelativePath(String JavaDoc baseDir, String JavaDoc file)
82     throws IOException JavaDoc
83     {
84         return getRelativePath(new File JavaDoc(baseDir), file);
85     }
86
87     public static String JavaDoc getRelativePath(File JavaDoc baseDir, File JavaDoc file)
88     throws IOException JavaDoc
89     {
90         return getRelativePath(baseDir, file.getPath());
91     }
92
93     /**
94      * This method removes double slashes, single-dot-directories and double-dot-directories
95      * from a path. This means, it does nearly the same as <tt>File.getCanonicalPath</tt>, but
96      * it does not resolve symlinks. This is essential for the method <tt>getRelativePath</tt>,
97      * because this method first tries it with a simplified path before using the canonical path
98      * (prevents problems with iteration through directories, where there are symlinks).
99      * <p>
100      * Please note that this method makes the given path absolute!
101      *
102      * @param path A path to simplify, e.g. "/../opt/java/jboss/../jboss/./bin/././../server/default/lib/."
103      * @return Returns the simplified string, e.g. "/opt/java/jboss/server/default/lib"
104      */

105     public static String JavaDoc simplifyPath(File JavaDoc path)
106     {
107         LinkedList JavaDoc dirs = new LinkedList JavaDoc();
108
109         String JavaDoc pathStr = path.getAbsolutePath();
110         boolean startWithSeparator = pathStr.startsWith(File.separator);
111
112         StringTokenizer JavaDoc tk = new StringTokenizer JavaDoc(pathStr, File.separator, false);
113         while (tk.hasMoreTokens()) {
114             String JavaDoc dir = tk.nextToken();
115             if (".".equals(dir))
116                 ;// nothing
117
else if ("..".equals(dir)) {
118                 if (!dirs.isEmpty())
119                     dirs.removeLast();
120             }
121             else
122                 dirs.addLast(dir);
123         }
124
125         StringBuffer JavaDoc sb = new StringBuffer JavaDoc();
126         for (Iterator JavaDoc it = dirs.iterator(); it.hasNext(); ) {
127             String JavaDoc dir = (String JavaDoc) it.next();
128             if (startWithSeparator || sb.length() > 0)
129                 sb.append(File.separator);
130             sb.append(dir);
131         }
132         
133         return sb.toString();
134     }
135     
136     public static String JavaDoc getRelativePath(File JavaDoc baseDir, String JavaDoc file)
137     throws IOException JavaDoc
138     {
139         if (!baseDir.isAbsolute())
140             throw new IllegalArgumentException JavaDoc("baseDir \""+baseDir.getPath()+"\" is not absolute!");
141
142         File JavaDoc absFile;
143         File JavaDoc tmpF = new File JavaDoc(file);
144         if (tmpF.isAbsolute())
145             absFile = tmpF;
146         else
147             absFile = new File JavaDoc(baseDir, file);
148
149         String JavaDoc absFileStr = null;
150         String JavaDoc baseDirStr = null;
151         for (int mode_base = 0; mode_base < 2; ++mode_base) {
152             switch (mode_base) {
153                 case 0:
154                     baseDirStr = simplifyPath(baseDir);
155                 break;
156                 case 1:
157                     baseDirStr = baseDir.getCanonicalPath();
158                 break;
159                 default:
160                     throw new IllegalStateException JavaDoc("this should never happen!");
161             }
162             
163             for (int mode_abs = 0; mode_abs < 2; ++mode_abs) {
164                 baseDirStr = addFinalSlash(baseDirStr);
165
166                 switch (mode_abs) {
167                     case 0:
168                         absFileStr = simplifyPath(absFile);
169                     break;
170                     case 1:
171                         absFileStr = absFile.getCanonicalPath();
172                     break;
173                     default:
174                         throw new IllegalStateException JavaDoc("this should never happen!");
175                 }
176
177                 if (!absFileStr.startsWith(baseDirStr)) {
178                     if (mode_base >= 1 && mode_abs >= 1)
179                         throw new IllegalArgumentException JavaDoc("file \""+file+"\" is not a child of baseDir \""+baseDir.getCanonicalPath()+"\"!");
180                 }
181                 else
182                     break;
183             } // for (int mode_abs = 0; mode_abs < 2; ++mode_abs) {
184
} // for (int mode = 0; mode < 2; ++mode) {
185

186         if (baseDirStr == null)
187             throw new NullPointerException JavaDoc("baseDirStr == null");
188         
189         if (absFileStr == null)
190             throw new NullPointerException JavaDoc("absFileStr == null");
191
192         return absFileStr.substring(baseDirStr.length(), absFileStr.length());
193     }
194
195     /**
196      * Convenience method for <code>transferStreamData(in, out, 0, -1)</code>
197      * @param in
198      * @param out
199      * @return The number of bytes transferred
200      * @throws IOException
201      */

202     public static long transferStreamData(java.io.InputStream JavaDoc in, java.io.OutputStream JavaDoc out)
203     throws java.io.IOException JavaDoc
204     {
205         return transferStreamData(in, out, 0, -1);
206     }
207
208 // /**
209
// * @param bandwidthCalculator if this is <code>null</code>, no trafficshaping will be done.
210
// * @param priority Must be a number from 1 to 10, where 10 means no traffic shaping and 1
211
// * means 10% of the available bandwidth.
212
// */
213
// public static long transferStreamData(java.io.InputStream in, java.io.OutputStream out,
214
// com.nightlabs.protocol.BandwidthCalculator bandwidthCalculator, byte priority, int remoteBandwidthReceive
215
// )
216
// throws java.io.IOException
217
// {
218
// int bytesRead;
219
// int transferred = 0;
220
// int txBlockSize = 4096;
221
// int recalcTXTimePeriod = 15000; // Mindest-Anzahl in Milli-Sekunden die zwischen den Berechnungen der txTime liegen muss.
222
// byte[] buf = new byte[txBlockSize];
223
//
224
// long lastTXTimeCalcDT = 0;
225
//
226
// int txTime = 0; // for traffic shaping
227
// long lastWriteDurationMSec = 0; // for traffic shaping
228
//
229
// while (true) {
230
// bytesRead = in.read(buf);
231
//
232
// if (bytesRead <= 0)
233
// break;
234
//
235
// if (bandwidthCalculator != null && System.currentTimeMillis() - lastTXTimeCalcDT > recalcTXTimePeriod) {
236
// int currentBandwidthSend = bandwidthCalculator.calculateCurrentBandwidthSend(priority, remoteBandwidthReceive);
237
//
238
// if (currentBandwidthSend == Integer.MAX_VALUE)
239
// txTime = 0;
240
// else
241
// txTime = 1000 * txBlockSize / currentBandwidthSend; // sleepTime is in millisec
242
//
243
// if (txTime > 10)
244
// Log.logDefault(Log.DEBUG, "txTime=\""+txTime+"\" Sleeping active!");
245
// else
246
// Log.logDefault(Log.DEBUG, "txTime=\""+txTime+"\" Sleeping NOT active!");
247
//
248
// lastTXTimeCalcDT = System.currentTimeMillis();
249
// }
250
//
251
// if (txTime > 10 && transferred != 0) {
252
// int sleepTime = txTime - (int)lastWriteDurationMSec;
253
// Log.logDefault(Log.DEBUG, "sleepTime="+sleepTime);
254
// if (sleepTime > 10)
255
// try { Thread.currentThread().sleep(sleepTime); } catch (InterruptedException x) { }
256
// }
257
//
258
// long beginWriteDT = System.currentTimeMillis();
259
// out.write(buf, 0, bytesRead);
260
// lastWriteDurationMSec = System.currentTimeMillis() - beginWriteDT;
261
// if (lastWriteDurationMSec > Integer.MAX_VALUE || lastWriteDurationMSec < 0)
262
// lastWriteDurationMSec = Integer.MAX_VALUE;
263
//
264
// transferred += bytesRead;
265
// }
266
// out.flush();
267
// return transferred;
268
// }
269

270     /**
271      * This method deletes the given directory recursively. If the given parameter
272      * specifies a file and no directory, it will be deleted anyway. If one or more
273      * files or subdirectories cannot be deleted, the method still continues and tries
274      * to delete as many files/subdirectories as possible.
275      *
276      * @param dir The directory or file to delete
277      * @return True, if the file or directory does not exist anymore. This means it either
278      * was not existing already before or it has been successfully deleted. False, if the
279      * directory could not be deleted.
280      */

281     public static boolean deleteDirectoryRecursively(String JavaDoc dir)
282     {
283         File JavaDoc dirF = new File JavaDoc(dir);
284         return deleteDirectoryRecursively(dirF);
285     }
286
287     /**
288      * This method deletes the given directory recursively. If the given parameter
289      * specifies a file and no directory, it will be deleted anyway. If one or more
290      * files or subdirectories cannot be deleted, the method still continues and tries
291      * to delete as many files/subdirectories as possible.
292      *
293      * @param dir The directory or file to delete
294      * @return True, if the file or directory does not exist anymore. This means it either
295      * was not existing already before or it has been successfully deleted. False, if the
296      * directory could not be deleted.
297      */

298     public static boolean deleteDirectoryRecursively(File JavaDoc dir)
299     {
300         if (!dir.exists())
301             return true;
302
303         if (dir.isDirectory()) {
304             File JavaDoc[] content = dir.listFiles();
305             for (int i = 0; i < content.length; ++i) {
306                 File JavaDoc f = content[i];
307                 if (f.isDirectory())
308                     deleteDirectoryRecursively(f);
309                 else
310                     f.delete();
311             }
312         }
313
314         return dir.delete();
315     }
316
317     /**
318      * Transfer data between streams
319      * @param in The input stream
320      * @param out The output stream
321      * @param inputOffset How many bytes to skip before transferring
322      * @param inputLen How many bytes to transfer. -1 = all
323      * @return The number of bytes transferred
324      * @throws IOException if an error occurs.
325      */

326     public static long transferStreamData(java.io.InputStream JavaDoc in, java.io.OutputStream JavaDoc out, long inputOffset, long inputLen)
327     throws java.io.IOException JavaDoc
328     {
329         int bytesRead;
330         int transferred = 0;
331         byte[] buf = new byte[4096];
332
333         //skip offset
334
if(inputOffset > 0)
335             if(in.skip(inputOffset) != inputOffset)
336                 throw new IOException JavaDoc("Input skip failed (offset "+inputOffset+")");
337
338         while (true) {
339             if(inputLen >= 0)
340                 bytesRead = in.read(buf, 0, (int)Math.min(buf.length, inputLen-transferred));
341             else
342                 bytesRead = in.read(buf);
343
344             if (bytesRead <= 0)
345                 break;
346
347             out.write(buf, 0, bytesRead);
348
349             transferred += bytesRead;
350
351             if(inputLen >= 0 && transferred >= inputLen)
352                 break;
353         }
354         out.flush();
355         return transferred;
356     }
357     
358     public static void copyResource(Class JavaDoc sourceResClass, String JavaDoc sourceResName, String JavaDoc dest_name)
359     throws IOException JavaDoc
360     {
361             InputStream JavaDoc source = null;
362             FileOutputStream JavaDoc destination = null;
363             try{
364                     source = sourceResClass.getResourceAsStream(sourceResName);
365                 File JavaDoc destination_file = new File JavaDoc(dest_name);
366                 
367                 if (destination_file.exists()) {
368                         if (destination_file.isFile()) {
369                                 DataInputStream JavaDoc in = new DataInputStream JavaDoc(System.in);
370                                 if (!destination_file.canWrite())
371                                         throw new IOException JavaDoc("FileCopy: destination " + "file is unwriteable: " + destination_file.getCanonicalPath());
372                         } else
373                                 throw new IOException JavaDoc("FileCopy: destination is not a file: " + destination_file.getCanonicalPath());
374                 } else {
375                         File JavaDoc parentdir = parent(destination_file);
376                         if (!parentdir.exists())
377                                 throw new IOException JavaDoc("FileCopy: destination "+ "directory doesn't exist: " + destination_file.getCanonicalPath());
378                         if (!parentdir.canWrite())
379                                 throw new IOException JavaDoc("FileCopy: destination "+ "directory is unwriteable: " + destination_file.getCanonicalPath());
380                 } // if (destination_file.exists())
381
destination = new FileOutputStream JavaDoc(destination_file);
382                 transferStreamData(source,destination);
383             } finally {
384                     if (source != null)
385                         try { source.close(); } catch (IOException JavaDoc e) { ; }
386                     if (destination != null)
387                         try { destination.close(); } catch (IOException JavaDoc e) { ; }
388              }
389                 
390     }
391
392     public static void copyFile(String JavaDoc source_name, String JavaDoc dest_name)
393     throws IOException JavaDoc
394     {
395             File JavaDoc source_file = new File JavaDoc(source_name);
396             File JavaDoc destination_file = new File JavaDoc(dest_name);
397             copyFile(source_file,destination_file);
398     }
399
400     public static void copyFile(File JavaDoc source_file, File JavaDoc destination_file)
401     throws IOException JavaDoc
402     {
403         FileInputStream JavaDoc source = null;
404         FileOutputStream JavaDoc destination = null;
405         byte[] buffer;
406         int bytes_read;
407
408         try {
409             // First make sure the specified source file
410
// exists, is a file, and is readable.
411
if (!source_file.exists() || !source_file.isFile())
412                 throw new IOException JavaDoc("FileCopy: no such source file: "+source_file.getCanonicalPath());
413             if (!source_file.canRead())
414              throw new IOException JavaDoc("FileCopy: source file is unreadable: "+source_file.getCanonicalPath());
415
416             // If the destination exists, make sure it is a writeable file
417
// and ask before overwriting it. If the destination doesn't
418
// exist, make sure the directory exists and is writeable.
419
if (destination_file.exists()) {
420                 if (destination_file.isFile()) {
421                     DataInputStream JavaDoc in = new DataInputStream JavaDoc(System.in);
422                     if (!destination_file.canWrite())
423                         throw new IOException JavaDoc("FileCopy: destination " +
424                                                                                                                      "file is unwriteable: " + destination_file.getCanonicalPath());
425                 } else
426                     throw new IOException JavaDoc("FileCopy: destination is not a file: " + destination_file.getCanonicalPath());
427             } else {
428                 File JavaDoc parentdir = parent(destination_file);
429                 if (!parentdir.exists())
430                     throw new IOException JavaDoc("FileCopy: destination "
431                                     + "directory doesn't exist: " +
432                                     destination_file.getCanonicalPath());
433                  if (!parentdir.canWrite())
434                      throw new IOException JavaDoc("FileCopy: destination "
435                                     + "directory is unwriteable: " +
436                                     destination_file.getCanonicalPath());
437             }
438             // If we've gotten this far, then everything is okay; we can
439
// copy the file.
440
source = new FileInputStream JavaDoc(source_file);
441             destination = new FileOutputStream JavaDoc(destination_file);
442             transferStreamData(source, destination);
443             // No matter what happens, always close any streams we've opened.
444
} finally {
445             if (source != null)
446                 try { source.close(); } catch (IOException JavaDoc e) { ; }
447             if (destination != null)
448                 try { destination.close(); } catch (IOException JavaDoc e) { ; }
449         }
450     }
451
452     // File.getParent() can return null when the file is specified without
453
// a directory or is in the root directory.
454
// This method handles those cases.
455
private static File JavaDoc parent(File JavaDoc f) {
456         String JavaDoc dirname = f.getParent();
457         if (dirname == null) {
458             return new File JavaDoc(File.separator);
459         }
460         return new File JavaDoc(dirname);
461     }
462
463     public static String JavaDoc decodeHexStr(byte buf[], int pos, int len) {
464          StringBuffer JavaDoc hex = new StringBuffer JavaDoc();
465          while (len-- > 0) {
466                 byte ch = buf[pos++];
467                 int d = (ch >> 4) & 0xf;
468                 hex.append((char)(d >= 10 ? 'a' - 10 + d : '0' + d));
469                 d = ch & 0xf;
470                 hex.append((char)(d >= 10 ? 'a' - 10 + d : '0' + d));
471          }
472          return hex.toString();
473     }
474
475     public static String JavaDoc getMD5HexString(String JavaDoc clear)
476     throws NoSuchAlgorithmException JavaDoc
477     {
478         byte[] enc = MessageDigest.getInstance("MD5").digest(clear.getBytes());
479         return decodeHexStr(enc, 0, enc.length);
480     }
481
482
483     public static String JavaDoc htmlEncode(String JavaDoc s)
484     {
485         if (s == null)
486             return "";
487
488         StringBuffer JavaDoc sb = new StringBuffer JavaDoc();
489         for (int i = 0; i < s.length(); i++) {
490             char ch = s.charAt(i);
491             if (ch == '\n')
492                 sb.append("<br>");
493             else if (ch == '<')
494                 sb.append("&lt;");
495             else if (ch == '>')
496                 sb.append("&gt;");
497             else if (ch == '\t')
498                 sb.append("&nbsp;&nbsp;&nbsp;&nbsp;");
499             else
500                 sb.append(ch);
501         } // for (int i = 0; i < bytesRead; i++) {
502
return sb.toString();
503     }
504
505     /**
506      * This method calls {@link #array2ArrayList(Object[], boolean)} with
507      * <tt>canReturnNull = false</tt>.
508      *
509      * @param objects An array of objects - can be <tt>null</tt>.
510      * @return Returns an <tt>ArrayList</tt> - never <tt>null</tt>.
511      * The <tt>ArrayList</tt> is empty if <tt>objects</tt> is <tt>null</tt>.
512      */

513     public static ArrayList JavaDoc array2ArrayList(Object JavaDoc[] objects)
514     {
515         return array2ArrayList(objects, false);
516     }
517
518     /**
519      * @param canReturnNull If <tt>false</tt>, the result will never be <tt>null</tt>,
520      * but an empty list if <tt>objects</tt> is null.
521      * @param objects An array of objects - can be <tt>null</tt>.
522      * @return Returns an <tt>ArrayList</tt> - never <tt>null</tt>.
523      * The <tt>ArrayList</tt> is empty if <tt>objects</tt> is <tt>null</tt> and
524      * <tt>canReturnNull</tt> is <tt>false</tt>. If <tt>canReturnNull == true</tt>
525      * and <tt>objects == null</tt>, the result will be <tt>null</tt>.
526      */

527     public static ArrayList JavaDoc array2ArrayList(Object JavaDoc[] objects, boolean canReturnNull)
528     {
529         if (canReturnNull && objects == null)
530             return null;
531
532         ArrayList JavaDoc l = new ArrayList JavaDoc(objects == null ? 0 : objects.length);
533         if (objects != null) {
534             for (int i = 0; i < objects.length; ++i)
535                 l.add(objects[i]);
536         }
537         return l;
538     }
539
540     /**
541      * This method calls {@link #array2HashSet(Object[], boolean)} with
542      * <tt>canReturnNull = false</tt>.
543      *
544      * @param objects An array of objects - can be <tt>null</tt>.
545      * @return Returns an <tt>ArrayList</tt> - never <tt>null</tt>.
546      * The <tt>ArrayList</tt> is empty if <tt>objects</tt> is <tt>null</tt>.
547      */

548     public static HashSet JavaDoc array2HashSet(Object JavaDoc[] objects)
549     {
550         return array2HashSet(objects, false);
551     }
552
553     /**
554      * @param canReturnNull If <tt>false</tt>, the result will never be <tt>null</tt>,
555      * but an empty list if <tt>objects</tt> is null.
556      * @param objects An array of objects - can be <tt>null</tt>.
557      * @return Returns an <tt>ArrayList</tt> - never <tt>null</tt>.
558      * The <tt>ArrayList</tt> is empty if <tt>objects</tt> is <tt>null</tt> and
559      * <tt>canReturnNull</tt> is <tt>false</tt>. If <tt>canReturnNull == true</tt>
560      * and <tt>objects == null</tt>, the result will be <tt>null</tt>.
561      */

562     public static HashSet JavaDoc array2HashSet(Object JavaDoc[] objects, boolean canReturnNull)
563     {
564         if (canReturnNull && objects == null)
565             return null;
566
567         HashSet JavaDoc s = new HashSet JavaDoc(objects == null ? 0 : objects.length);
568         if (objects != null) {
569             for (int i = 0; i < objects.length; ++i)
570                 s.add(objects[i]);
571         }
572         return s;
573     }
574
575     public static Object JavaDoc[] collection2TypedArray(Collection JavaDoc c, Class JavaDoc clazz)
576     {
577         Object JavaDoc array = Array.newInstance(clazz, c.size());
578         int i = 0;
579         for (Iterator JavaDoc it = c.iterator(); it.hasNext(); )
580             Array.set(array, i++, it.next());
581         return (Object JavaDoc[])array;
582     }
583
584     /**
585      * Moves the given element up in the given list.
586      *
587      * @param list The list
588      * @param element The element
589      */

590     public static void moveListElementUp(List JavaDoc list, Object JavaDoc element) {
591         int index = list.indexOf(element);
592         if (index <= 0 || index >= list.size())
593             return;
594         list.remove(index);
595         list.add(index-1, element);
596     }
597     
598     /**
599      * Moves the given element down in the given list.
600      * @param list The list
601      * @param element The element
602      */

603     public static void moveListElementDown(List JavaDoc list, Object JavaDoc element) {
604         int index = list.indexOf(element);
605         if (index < 0 || index >= list.size()-1)
606             return;
607         list.remove(index);
608         list.add(index+1, element);
609     }
610 }
Popular Tags