Source Code Cross Referenced for FileSystemUtils.java in  » Library » apache-common-IO » org » apache » commons » io » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Library » apache common IO » org.apache.commons.io 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         * Licensed to the Apache Software Foundation (ASF) under one or more
003:         * contributor license agreements.  See the NOTICE file distributed with
004:         * this work for additional information regarding copyright ownership.
005:         * The ASF licenses this file to You under the Apache License, Version 2.0
006:         * (the "License"); you may not use this file except in compliance with
007:         * the License.  You may obtain a copy of the License at
008:         * 
009:         *      http://www.apache.org/licenses/LICENSE-2.0
010:         * 
011:         * Unless required by applicable law or agreed to in writing, software
012:         * distributed under the License is distributed on an "AS IS" BASIS,
013:         * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014:         * See the License for the specific language governing permissions and
015:         * limitations under the License.
016:         */
017:        package org.apache.commons.io;
018:
019:        import java.io.BufferedReader;
020:        import java.io.IOException;
021:        import java.io.InputStream;
022:        import java.io.InputStreamReader;
023:        import java.io.OutputStream;
024:        import java.util.ArrayList;
025:        import java.util.Arrays;
026:        import java.util.List;
027:        import java.util.StringTokenizer;
028:
029:        /**
030:         * General File System utilities.
031:         * <p>
032:         * This class provides static utility methods for general file system
033:         * functions not provided via the JDK {@link java.io.File File} class.
034:         * <p>
035:         * The current functions provided are:
036:         * <ul>
037:         * <li>Get the free space on a drive
038:         * </ul>
039:         *
040:         * @author Frank W. Zammetti
041:         * @author Stephen Colebourne
042:         * @author Thomas Ledoux
043:         * @author James Urie
044:         * @author Magnus Grimsell
045:         * @author Thomas Ledoux
046:         * @version $Id: FileSystemUtils.java 453889 2006-10-07 11:56:25Z scolebourne $
047:         * @since Commons IO 1.1
048:         */
049:        public class FileSystemUtils {
050:
051:            /** Singleton instance, used mainly for testing. */
052:            private static final FileSystemUtils INSTANCE = new FileSystemUtils();
053:
054:            /** Operating system state flag for error. */
055:            private static final int INIT_PROBLEM = -1;
056:            /** Operating system state flag for neither Unix nor Windows. */
057:            private static final int OTHER = 0;
058:            /** Operating system state flag for Windows. */
059:            private static final int WINDOWS = 1;
060:            /** Operating system state flag for Unix. */
061:            private static final int UNIX = 2;
062:            /** Operating system state flag for Posix flavour Unix. */
063:            private static final int POSIX_UNIX = 3;
064:
065:            /** The operating system flag. */
066:            private static final int OS;
067:            static {
068:                int os = OTHER;
069:                try {
070:                    String osName = System.getProperty("os.name");
071:                    if (osName == null) {
072:                        throw new IOException("os.name not found");
073:                    }
074:                    osName = osName.toLowerCase();
075:                    // match
076:                    if (osName.indexOf("windows") != -1) {
077:                        os = WINDOWS;
078:                    } else if (osName.indexOf("linux") != -1
079:                            || osName.indexOf("sun os") != -1
080:                            || osName.indexOf("sunos") != -1
081:                            || osName.indexOf("solaris") != -1
082:                            || osName.indexOf("mpe/ix") != -1
083:                            || osName.indexOf("freebsd") != -1
084:                            || osName.indexOf("irix") != -1
085:                            || osName.indexOf("digital unix") != -1
086:                            || osName.indexOf("unix") != -1
087:                            || osName.indexOf("mac os x") != -1) {
088:                        os = UNIX;
089:                    } else if (osName.indexOf("hp-ux") != -1
090:                            || osName.indexOf("aix") != -1) {
091:                        os = POSIX_UNIX;
092:                    } else {
093:                        os = OTHER;
094:                    }
095:
096:                } catch (Exception ex) {
097:                    os = INIT_PROBLEM;
098:                }
099:                OS = os;
100:            }
101:
102:            /**
103:             * Instances should NOT be constructed in standard programming.
104:             */
105:            public FileSystemUtils() {
106:                super ();
107:            }
108:
109:            //-----------------------------------------------------------------------
110:            /**
111:             * Returns the free space on a drive or volume by invoking
112:             * the command line.
113:             * This method does not normalize the result, and typically returns
114:             * bytes on Windows, 512 byte units on OS X and kilobytes on Unix.
115:             * As this is not very useful, this method is deprecated in favour
116:             * of {@link #freeSpaceKb(String)} which returns a result in kilobytes.
117:             * <p>
118:             * Note that some OS's are NOT currently supported, including OS/390,
119:             * OpenVMS and and SunOS 5. (SunOS is supported by <code>freeSpaceKb</code>.)
120:             * <pre>
121:             * FileSystemUtils.freeSpace("C:");       // Windows
122:             * FileSystemUtils.freeSpace("/volume");  // *nix
123:             * </pre>
124:             * The free space is calculated via the command line.
125:             * It uses 'dir /-c' on Windows and 'df' on *nix.
126:             *
127:             * @param path  the path to get free space for, not null, not empty on Unix
128:             * @return the amount of free drive space on the drive or volume
129:             * @throws IllegalArgumentException if the path is invalid
130:             * @throws IllegalStateException if an error occurred in initialisation
131:             * @throws IOException if an error occurs when finding the free space
132:             * @since Commons IO 1.1, enhanced OS support in 1.2 and 1.3
133:             * @deprecated Use freeSpaceKb(String)
134:             *  Deprecated from 1.3, may be removed in 2.0
135:             */
136:            public static long freeSpace(String path) throws IOException {
137:                return INSTANCE.freeSpaceOS(path, OS, false);
138:            }
139:
140:            //-----------------------------------------------------------------------
141:            /**
142:             * Returns the free space on a drive or volume in kilobytes by invoking
143:             * the command line.
144:             * <pre>
145:             * FileSystemUtils.freeSpaceKb("C:");       // Windows
146:             * FileSystemUtils.freeSpaceKb("/volume");  // *nix
147:             * </pre>
148:             * The free space is calculated via the command line.
149:             * It uses 'dir /-c' on Windows, 'df -kP' on AIX/HP-UX and 'df -k' on other Unix.
150:             * <p>
151:             * In order to work, you must be running Windows, or have a implementation of
152:             * Unix df that supports GNU format when passed -k (or -kP). If you are going
153:             * to rely on this code, please check that it works on your OS by running
154:             * some simple tests to compare the command line with the output from this class.
155:             * If your operating system isn't supported, please raise a JIRA call detailing
156:             * the exact result from df -k and as much other detail as possible, thanks.
157:             *
158:             * @param path  the path to get free space for, not null, not empty on Unix
159:             * @return the amount of free drive space on the drive or volume in kilobytes
160:             * @throws IllegalArgumentException if the path is invalid
161:             * @throws IllegalStateException if an error occurred in initialisation
162:             * @throws IOException if an error occurs when finding the free space
163:             * @since Commons IO 1.2, enhanced OS support in 1.3
164:             */
165:            public static long freeSpaceKb(String path) throws IOException {
166:                return INSTANCE.freeSpaceOS(path, OS, true);
167:            }
168:
169:            //-----------------------------------------------------------------------
170:            /**
171:             * Returns the free space on a drive or volume in a cross-platform manner.
172:             * Note that some OS's are NOT currently supported, including OS/390.
173:             * <pre>
174:             * FileSystemUtils.freeSpace("C:");  // Windows
175:             * FileSystemUtils.freeSpace("/volume");  // *nix
176:             * </pre>
177:             * The free space is calculated via the command line.
178:             * It uses 'dir /-c' on Windows and 'df' on *nix.
179:             *
180:             * @param path  the path to get free space for, not null, not empty on Unix
181:             * @param os  the operating system code
182:             * @param kb  whether to normalize to kilobytes
183:             * @return the amount of free drive space on the drive or volume
184:             * @throws IllegalArgumentException if the path is invalid
185:             * @throws IllegalStateException if an error occurred in initialisation
186:             * @throws IOException if an error occurs when finding the free space
187:             */
188:            long freeSpaceOS(String path, int os, boolean kb)
189:                    throws IOException {
190:                if (path == null) {
191:                    throw new IllegalArgumentException("Path must not be empty");
192:                }
193:                switch (os) {
194:                case WINDOWS:
195:                    return (kb ? freeSpaceWindows(path) / 1024
196:                            : freeSpaceWindows(path));
197:                case UNIX:
198:                    return freeSpaceUnix(path, kb, false);
199:                case POSIX_UNIX:
200:                    return freeSpaceUnix(path, kb, true);
201:                case OTHER:
202:                    throw new IllegalStateException(
203:                            "Unsupported operating system");
204:                default:
205:                    throw new IllegalStateException(
206:                            "Exception caught when determining operating system");
207:                }
208:            }
209:
210:            //-----------------------------------------------------------------------
211:            /**
212:             * Find free space on the Windows platform using the 'dir' command.
213:             *
214:             * @param path  the path to get free space for, including the colon
215:             * @return the amount of free drive space on the drive
216:             * @throws IOException if an error occurs
217:             */
218:            long freeSpaceWindows(String path) throws IOException {
219:                path = FilenameUtils.normalize(path);
220:                if (path.length() > 2 && path.charAt(1) == ':') {
221:                    path = path.substring(0, 2); // seems to make it work
222:                }
223:
224:                // build and run the 'dir' command
225:                String[] cmdAttribs = new String[] { "cmd.exe", "/C",
226:                        "dir /-c " + path };
227:
228:                // read in the output of the command to an ArrayList
229:                List lines = performCommand(cmdAttribs, Integer.MAX_VALUE);
230:
231:                // now iterate over the lines we just read and find the LAST
232:                // non-empty line (the free space bytes should be in the last element
233:                // of the ArrayList anyway, but this will ensure it works even if it's
234:                // not, still assuming it is on the last non-blank line)
235:                for (int i = lines.size() - 1; i >= 0; i--) {
236:                    String line = (String) lines.get(i);
237:                    if (line.length() > 0) {
238:                        return parseDir(line, path);
239:                    }
240:                }
241:                // all lines are blank
242:                throw new IOException(
243:                        "Command line 'dir /-c' did not return any info "
244:                                + "for path '" + path + "'");
245:            }
246:
247:            /**
248:             * Parses the Windows dir response last line
249:             *
250:             * @param line  the line to parse
251:             * @param path  the path that was sent
252:             * @return the number of bytes
253:             * @throws IOException if an error occurs
254:             */
255:            long parseDir(String line, String path) throws IOException {
256:                // read from the end of the line to find the last numeric
257:                // character on the line, then continue until we find the first
258:                // non-numeric character, and everything between that and the last
259:                // numeric character inclusive is our free space bytes count
260:                int bytesStart = 0;
261:                int bytesEnd = 0;
262:                int j = line.length() - 1;
263:                innerLoop1: while (j >= 0) {
264:                    char c = line.charAt(j);
265:                    if (Character.isDigit(c)) {
266:                        // found the last numeric character, this is the end of
267:                        // the free space bytes count
268:                        bytesEnd = j + 1;
269:                        break innerLoop1;
270:                    }
271:                    j--;
272:                }
273:                innerLoop2: while (j >= 0) {
274:                    char c = line.charAt(j);
275:                    if (!Character.isDigit(c) && c != ',' && c != '.') {
276:                        // found the next non-numeric character, this is the
277:                        // beginning of the free space bytes count
278:                        bytesStart = j + 1;
279:                        break innerLoop2;
280:                    }
281:                    j--;
282:                }
283:                if (j < 0) {
284:                    throw new IOException(
285:                            "Command line 'dir /-c' did not return valid info "
286:                                    + "for path '" + path + "'");
287:                }
288:
289:                // remove commas and dots in the bytes count
290:                StringBuffer buf = new StringBuffer(line.substring(bytesStart,
291:                        bytesEnd));
292:                for (int k = 0; k < buf.length(); k++) {
293:                    if (buf.charAt(k) == ',' || buf.charAt(k) == '.') {
294:                        buf.deleteCharAt(k--);
295:                    }
296:                }
297:                return parseBytes(buf.toString(), path);
298:            }
299:
300:            //-----------------------------------------------------------------------
301:            /**
302:             * Find free space on the *nix platform using the 'df' command.
303:             *
304:             * @param path  the path to get free space for
305:             * @param kb  whether to normalize to kilobytes
306:             * @param posix  whether to use the posix standard format flag
307:             * @return the amount of free drive space on the volume
308:             * @throws IOException if an error occurs
309:             */
310:            long freeSpaceUnix(String path, boolean kb, boolean posix)
311:                    throws IOException {
312:                if (path.length() == 0) {
313:                    throw new IllegalArgumentException("Path must not be empty");
314:                }
315:                path = FilenameUtils.normalize(path);
316:
317:                // build and run the 'dir' command
318:                String flags = "-";
319:                if (kb) {
320:                    flags += "k";
321:                }
322:                if (posix) {
323:                    flags += "P";
324:                }
325:                String[] cmdAttribs = (flags.length() > 1 ? new String[] {
326:                        "df", flags, path } : new String[] { "df", path });
327:
328:                // perform the command, asking for up to 3 lines (header, interesting, overflow)
329:                List lines = performCommand(cmdAttribs, 3);
330:                if (lines.size() < 2) {
331:                    // unknown problem, throw exception
332:                    throw new IOException(
333:                            "Command line 'df' did not return info as expected "
334:                                    + "for path '" + path + "'- response was "
335:                                    + lines);
336:                }
337:                String line2 = (String) lines.get(1); // the line we're interested in
338:
339:                // Now, we tokenize the string. The fourth element is what we want.
340:                StringTokenizer tok = new StringTokenizer(line2, " ");
341:                if (tok.countTokens() < 4) {
342:                    // could be long Filesystem, thus data on third line
343:                    if (tok.countTokens() == 1 && lines.size() >= 3) {
344:                        String line3 = (String) lines.get(2); // the line may be interested in
345:                        tok = new StringTokenizer(line3, " ");
346:                    } else {
347:                        throw new IOException(
348:                                "Command line 'df' did not return data as expected "
349:                                        + "for path '" + path
350:                                        + "'- check path is valid");
351:                    }
352:                } else {
353:                    tok.nextToken(); // Ignore Filesystem
354:                }
355:                tok.nextToken(); // Ignore 1K-blocks
356:                tok.nextToken(); // Ignore Used
357:                String freeSpace = tok.nextToken();
358:                return parseBytes(freeSpace, path);
359:            }
360:
361:            //-----------------------------------------------------------------------
362:            /**
363:             * Parses the bytes from a string.
364:             * 
365:             * @param freeSpace  the free space string
366:             * @param path  the path
367:             * @return the number of bytes
368:             * @throws IOException if an error occurs
369:             */
370:            long parseBytes(String freeSpace, String path) throws IOException {
371:                try {
372:                    long bytes = Long.parseLong(freeSpace);
373:                    if (bytes < 0) {
374:                        throw new IOException(
375:                                "Command line 'df' did not find free space in response "
376:                                        + "for path '" + path
377:                                        + "'- check path is valid");
378:                    }
379:                    return bytes;
380:
381:                } catch (NumberFormatException ex) {
382:                    throw new IOException(
383:                            "Command line 'df' did not return numeric data as expected "
384:                                    + "for path '" + path
385:                                    + "'- check path is valid");
386:                }
387:            }
388:
389:            //-----------------------------------------------------------------------
390:            /**
391:             * Performs the os command.
392:             *
393:             * @param cmdAttribs  the command line parameters
394:             * @param max The maximum limit for the lines returned
395:             * @return the parsed data
396:             * @throws IOException if an error occurs
397:             */
398:            List performCommand(String[] cmdAttribs, int max)
399:                    throws IOException {
400:                // this method does what it can to avoid the 'Too many open files' error
401:                // based on trial and error and these links:
402:                // http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4784692
403:                // http://bugs.sun.com/bugdatabase/view_bug.do?bug_id=4801027
404:                // http://forum.java.sun.com/thread.jspa?threadID=533029&messageID=2572018
405:                // however, its still not perfect as the JDK support is so poor
406:                // (see commond-exec or ant for a better multi-threaded multi-os solution)
407:
408:                List lines = new ArrayList(20);
409:                Process proc = null;
410:                InputStream in = null;
411:                OutputStream out = null;
412:                InputStream err = null;
413:                BufferedReader inr = null;
414:                try {
415:                    proc = openProcess(cmdAttribs);
416:                    in = proc.getInputStream();
417:                    out = proc.getOutputStream();
418:                    err = proc.getErrorStream();
419:                    inr = new BufferedReader(new InputStreamReader(in));
420:                    String line = inr.readLine();
421:                    while (line != null && lines.size() < max) {
422:                        line = line.toLowerCase().trim();
423:                        lines.add(line);
424:                        line = inr.readLine();
425:                    }
426:
427:                    proc.waitFor();
428:                    if (proc.exitValue() != 0) {
429:                        // os command problem, throw exception
430:                        throw new IOException(
431:                                "Command line returned OS error code '"
432:                                        + proc.exitValue() + "' for command "
433:                                        + Arrays.asList(cmdAttribs));
434:                    }
435:                    if (lines.size() == 0) {
436:                        // unknown problem, throw exception
437:                        throw new IOException(
438:                                "Command line did not return any info "
439:                                        + "for command "
440:                                        + Arrays.asList(cmdAttribs));
441:                    }
442:                    return lines;
443:
444:                } catch (InterruptedException ex) {
445:                    throw new IOException(
446:                            "Command line threw an InterruptedException '"
447:                                    + ex.getMessage() + "' for command "
448:                                    + Arrays.asList(cmdAttribs));
449:                } finally {
450:                    IOUtils.closeQuietly(in);
451:                    IOUtils.closeQuietly(out);
452:                    IOUtils.closeQuietly(err);
453:                    IOUtils.closeQuietly(inr);
454:                    if (proc != null) {
455:                        proc.destroy();
456:                    }
457:                }
458:            }
459:
460:            /**
461:             * Opens the process to the operating system.
462:             *
463:             * @param cmdAttribs  the command line parameters
464:             * @return the process
465:             * @throws IOException if an error occurs
466:             */
467:            Process openProcess(String[] cmdAttribs) throws IOException {
468:                return Runtime.getRuntime().exec(cmdAttribs);
469:            }
470:
471:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.