|
From: <cr...@us...> - 2008-05-18 04:37:53
|
Revision: 4106
http://jnode.svn.sourceforge.net/jnode/?rev=4106&view=rev
Author: crawley
Date: 2008-05-17 21:37:38 -0700 (Sat, 17 May 2008)
Log Message:
-----------
Rewrote CpCommand. It now supports multiple arguments, and uses the
new syntax mechanism.
Modified Paths:
--------------
trunk/fs/descriptors/org.jnode.fs.command.xml
trunk/fs/src/fs/org/jnode/fs/command/CpCommand.java
Modified: trunk/fs/descriptors/org.jnode.fs.command.xml
===================================================================
--- trunk/fs/descriptors/org.jnode.fs.command.xml 2008-05-18 04:36:21 UTC (rev 4105)
+++ trunk/fs/descriptors/org.jnode.fs.command.xml 2008-05-18 04:37:38 UTC (rev 4106)
@@ -48,6 +48,19 @@
<argument argLabel="file"/>
</repeat>
</syntax>
+ <syntax alias="cp">
+ <sequence description="copy files or directories">
+ <optionSet>
+ <option argLabel="force" shortName="f" longName="force"/>
+ <option argLabel="update" shortName="u" longName="update"/>
+ <option argLabel="interactive" shortName="i" longName="interactive"/>
+ <option argLabel="recursive" shortName="r" longName="recursive"/>
+ <option argLabel="verbose" shortName="v" longName="verbose"/>
+ </optionSet>
+ <repeat minCount="1"><argument argLabel="source"/></repeat>
+ <argument argLabel="target"/>
+ </sequence>
+ </syntax>
<syntax alias="del">
<sequence description="delete a file or directory">
<optional>
Modified: trunk/fs/src/fs/org/jnode/fs/command/CpCommand.java
===================================================================
--- trunk/fs/src/fs/org/jnode/fs/command/CpCommand.java 2008-05-18 04:36:21 UTC (rev 4105)
+++ trunk/fs/src/fs/org/jnode/fs/command/CpCommand.java 2008-05-18 04:37:38 UTC (rev 4106)
@@ -21,6 +21,7 @@
package org.jnode.fs.command;
+import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
@@ -29,554 +30,365 @@
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
+import java.io.PrintStream;
import java.net.MalformedURLException;
import java.net.URL;
-import org.jnode.shell.help.Help;
-import org.jnode.shell.help.Parameter;
-import org.jnode.shell.help.Syntax;
-import org.jnode.shell.help.argument.FileArgument;
-import org.jnode.shell.help.argument.OptionArgument;
+import org.jnode.shell.AbstractCommand;
+import org.jnode.shell.CommandLine;
+import org.jnode.shell.syntax.*;
/**
+ * File copy utility. This utility copies one file to another file, or multiple files or directories
+ * into a directory. Recursive directory copy is supported.
*
- * Copy a File to a File or Directory
- *
- * Syntaxe : cp [-u | -f | -i] [-v] [-r] file/url-src file-dst Exemples cp -ur
- * -v d:/adir d:/temp
- *
- *
- * TODO : support of patern file source (cp *.j*g /dir/) support file name with
- * strange char like * \ /
- *
- * @author Yves Galante (yve...@jm...)
- * @version 0.1
- *
+ * @author cr...@jn...
*/
-public class CpCommand {
+public class CpCommand extends AbstractCommand {
- static final byte MODE_BASE = 0;
-
- static final byte MODE_ITERATIVE = 1;
-
+ static final byte MODE_NORMAL = 0;
+ static final byte MODE_INTERACTIVE = 1;
static final byte MODE_FORCE = 2;
-
static final byte MODE_UPDATE = 3;
- static final char MODE_FORCE_C = 'f';
+ private final FileArgument ARG_SOURCE =
+ new FileArgument("source", Argument.MANDATORY + Argument.MULTIPLE, "source files or directories");
- static final char MODE_INTER_C = 'i';
+ private final FileArgument ARG_TARGET =
+ new FileArgument("target", Argument.MANDATORY, "target file or directory");
- static final char MODE_UPDATE_C = 'u';
+ private final FlagArgument FLAG_FORCE =
+ new FlagArgument("force", Argument.OPTIONAL, "if set, force overwrite of existing files");
+
+ private final FlagArgument FLAG_INTERACTIVE =
+ new FlagArgument("interactive", Argument.OPTIONAL, "if set, ask before overwriting existing files");
+
+ private final FlagArgument FLAG_UPDATE =
+ new FlagArgument("update", Argument.OPTIONAL, "if set, overwrite existing files older than their source");
+
+ private final FlagArgument FLAG_RECURSIVE =
+ new FlagArgument("recursive", Argument.OPTIONAL, "if set, recursively copy source directories");
+
+ private final FlagArgument FLAG_VERBOSE =
+ new FlagArgument("verbose", Argument.OPTIONAL, "if set, output a line for each file copied");
- static final char OPTION_VERBOSE_C = 'v';
+ private byte mode = MODE_NORMAL;
+ private boolean recursive = false;
+ private boolean verbose = false;
+ private int filesCopied = 0;
+ private int directoriesCreated = 0;
+ private BufferedReader in;
+ private PrintStream out;
+ private PrintStream err;
+ private byte[] buffer = new byte[1024 * 8];
- static final char OPTION_RECURCIVE_C = 'r';
-
- static final FileArgument ARG_FSRC = new FileArgument("file or url",
- "file or url source");
-
- static final FileArgument ARG_FDST = new FileArgument("file", "file dest");
-
- static final OptionArgument ARG_OPT1 = new OptionArgument(
- "option",
- "a option",
- new OptionArgument.Option[] {
- new OptionArgument.Option("-" + MODE_FORCE_C + "",
- "if an existing destination file overwrite"),
- new OptionArgument.Option("-" + MODE_INTER_C + "",
- "if an existing destination file ask"),
- new OptionArgument.Option("-" + MODE_UPDATE_C + "",
- "if an existing destination file overwrite only if\ndate is older")});
-
- static final OptionArgument ARG_OPT2 = new OptionArgument("option",
- "a option",
- new OptionArgument.Option[] { new OptionArgument.Option("-"
- + OPTION_VERBOSE_C + "", "verbose")});
-
- static final OptionArgument ARG_OPT3 = new OptionArgument("option",
- "a option",
- new OptionArgument.Option[] { new OptionArgument.Option("-"
- + OPTION_RECURCIVE_C + "", "recursie")});
-
- public static Help.Info HELP_INFO = new Help.Info("cp",
- new Syntax[] { new Syntax("copy a file or url to a file",
- new Parameter[] {
- new Parameter(ARG_OPT1, Parameter.OPTIONAL),
- new Parameter(ARG_OPT2, Parameter.OPTIONAL),
- new Parameter(ARG_OPT3, Parameter.OPTIONAL),
- new Parameter(ARG_FSRC, Parameter.MANDATORY),
- new Parameter(ARG_FDST, Parameter.MANDATORY)})});
-
- /**
- * ****************************** non static filed
- * ************************************
- */
-
- private URL _urlSrc;
-
- private File _fileSrc;
-
- private File _fileDst;
-
- private byte _mode = MODE_BASE;
-
- private boolean _recursive = false;
-
- private boolean _verbose = false;
-
- private boolean _srcIsDir = false;
-
- private boolean _argsOk = true;
-
- final byte[] buf = new byte[128*1024];
-
- /**
- * Construct this class with args[] [-u | -f | -i] [-v] [-r] file/url-src
- * file-dst
- *
- * @param args
- * commande argument
- */
- public CpCommand(String[] args) {
- _argsOk = parseOption(args);
+ public CpCommand() {
+ super("Copy files or directories");
+ registerArguments(ARG_SOURCE, ARG_TARGET, FLAG_FORCE, FLAG_INTERACTIVE, FLAG_RECURSIVE,
+ FLAG_UPDATE, FLAG_VERBOSE);
}
-
- /**
- * Constructor with file
- *
- * @param fileSrc
- * @param fileDst
- * @param mode
- * @param recursive
- * @param verbose
- */
- public CpCommand(File fileSrc, File fileDst, byte mode, boolean recursive,
- boolean verbose) {
- _fileSrc = fileSrc;
- _fileDst = fileDst;
- _mode = mode;
- _recursive = recursive;
- _verbose = verbose;
+
+ public static void main(String[] args) throws Exception {
+ new CpCommand().execute(args);
}
- /**
- * Constructor with URL
- *
- * @param urlSrc
- * @param fileDst
- * @param mode
- * @param verbose
- */
- public CpCommand(URL urlSrc, File fileDst, byte mode, boolean verbose) {
- _urlSrc = urlSrc;
- _fileDst = fileDst;
- _mode = mode;
- _verbose = verbose;
+ public void execute(CommandLine commandLine, InputStream in,
+ PrintStream out, PrintStream err) throws Exception {
+ this.out = out;
+ this.err = err;
+ processFlags();
+ if (mode == MODE_INTERACTIVE) {
+ this.in = new BufferedReader(new InputStreamReader(in));
+ }
+ File[] sources = ARG_SOURCE.getValues();
+ File target = ARG_TARGET.getValue();
+ if (sources.length == 0) {
+ error("No source files or directories supplied");
+ }
+ if (target.isDirectory()) {
+ if (!target.canWrite()) {
+ error("Target directory is not writable");
+ }
+ for (File source : sources) {
+ if (checkSafe(source, target)) {
+ copyIntoDirectory(source, target);
+ }
+ }
+ }
+ else if (sources.length > 1) {
+ error("Multi-file copy requires the target to be a directory");
+ }
+ else {
+ File source = sources[0];
+ if (source.isDirectory()) {
+ error("Cannot copy a directory to a file");
+ }
+ else if (target.exists() && !target.isFile()) {
+ error("Cannot copy to a device");
+ }
+ else {
+ if (checkSafe(source, target)) {
+ copyToFile(source, target);
+ }
+ }
+ }
+ if (verbose) {
+ out.println("Files copied: " + filesCopied + ", directories created: " + directoriesCreated);
+ }
}
- /**
- * Copy
- *
- * @return Return the number of file copied
- */
- public int copy() throws Exception {
- if (!_argsOk) {
- HELP_INFO.parse(new String[ 0]);
- return 0;
+ private void processFlags() {
+ recursive = FLAG_RECURSIVE.isSet();
+ verbose = FLAG_VERBOSE.isSet();
+ // The mode flags are mutually exclusive ...
+ if (FLAG_FORCE.isSet()) {
+ mode = MODE_FORCE;
}
- if (_fileSrc != null) {
- if (!check()) { return 0; }
- if (_srcIsDir) {
- return copyDir();
- } else {
- return copyFile();
+ if (FLAG_INTERACTIVE.isSet()) {
+ if (mode != MODE_NORMAL) {
+ error("The 'force', 'interactive' and 'update' flags are mutually exclusive");
}
- } else {
- if (!checkURL()) { return 0; }
- return copyURL();
+ mode = MODE_INTERACTIVE;
}
-
+ if (FLAG_UPDATE.isSet()) {
+ if (mode != MODE_NORMAL) {
+ error("The 'force', 'interactive' and 'update' flags are mutually exclusive");
+ }
+ mode = MODE_UPDATE;
+ }
}
-
+
/**
- * Syntaxe [-u | -f | -i] [-v] [-r] filesrc filedst Exemple cp -uv file1
- * file2 cp -f -r file1 file2
+ * Copy a file or directory into a supplied target directory.
*
- * @param args
- *
- * @since 30 mars 04
+ * @param source the name of the object to be copied
+ * @param targetDir the destination directory
+ * @throws IOException
*/
- private boolean parseOption(String[] args) {
-
- String options;
- StringBuilder sb = new StringBuilder(5);
-
- if (args.length < 2 || args.length > 10) { return false; }
-
- // concat all options
- for (int i = 0; i < args.length - 2; i++) {
- if (args[ i].charAt(0) != '-') return false;
- sb.append(args[ i].substring(1));
+ private void copyIntoDirectory(File source, File targetDir) throws IOException {
+ if (!targetDir.canWrite()) {
+ skip("directory '" + targetDir + "' is not writable");
}
- options = sb.toString();
- sb = null;
- // parse options
- for (int i = 0; i < options.length(); i++) {
- char option = options.charAt(i);
- switch (option) {
- case MODE_FORCE_C:
- if (_mode == MODE_BASE) {
- _mode = MODE_FORCE;
- } else {
- return false;
+ else if (source.isDirectory()) {
+ if (recursive) {
+ File newDir = new File(targetDir, source.getName());
+ if (!newDir.exists()) {
+ if (verbose) {
+ out.println("Creating directory '" + newDir + "'");
+ }
+ newDir.mkdir();
+ directoriesCreated++;
}
- break;
- case MODE_UPDATE_C:
- if (_mode == MODE_BASE) {
- _mode = MODE_UPDATE;
- } else {
- return false;
+ else if (!newDir.isDirectory()) {
+ if (mode == MODE_FORCE) {
+ if (verbose) {
+ out.println("Replacing file '" + newDir + "' with a directory");
+ }
+ newDir.delete();
+ newDir.mkdir();
+ directoriesCreated++;
+ }
+ else {
+ skip("not overwriting '" + newDir + "' with a directory");
+ return;
+ }
}
- break;
- case MODE_INTER_C:
- if (_mode == MODE_BASE) {
- _mode = MODE_ITERATIVE;
- } else {
- return false;
+ String[] contents = source.list();
+ for (String name : contents) {
+ if (name.equals(".") || name.equals("..")) {
+ continue;
+ }
+ copyIntoDirectory(new File(source, name), newDir);
}
- break;
- case OPTION_VERBOSE_C:
- if (!_verbose) {
- _verbose = true;
- } else {
- return false;
- }
- break;
- case OPTION_RECURCIVE_C:
- if (!_recursive) {
- _recursive = true;
- } else {
- return false;
- }
- break;
- default:
- return false;
}
-
- }
-
- if (args[ args.length - 2].indexOf("://") >= 0) {
- try {
- _urlSrc = new URL(args[ args.length - 2]);
- } catch (MalformedURLException urlEx) {
- _urlSrc = null;
- System.err.println(args[ args.length - 2] + " is malformed");
- return false;
+ else {
+ skip("'" + source + "' is a directory");
}
}
- if (_urlSrc == null) {
- _fileSrc = new File(args[ args.length - 2]);
+ else {
+ File newFile = new File(targetDir, source.getName());
+ copyToFile(source, newFile);
}
- _fileDst = new File(args[ args.length - 1]);
- return true;
}
-
+
/**
- * Make some check on src url and on dst file
+ * Copy a file to (as) a file
*
- * @return
+ * @param sourceFile
+ * @param targetFile
+ * @throws IOException
*/
- private boolean checkURL() {
-
- if (_urlSrc == null || _fileDst == null) { return false; }
- // now file is converted to ftp
- //if(_urlSrc.getProtocol().equalsIgnoreCase("file")){
- // _urlSrc=null;
- // System.err.println(_urlSrc.toExternalForm()+" file protocol not
- // supported!");
- // return false;
- //}
- if (_fileDst.isDirectory()) { // directory not supported
- System.err.println(_fileDst.getAbsolutePath() + " is a directory!");
- return false;
+ private void copyToFile(File sourceFile, File targetFile) throws IOException {
+ if (!checkSafe(sourceFile, targetFile) ||
+ !checkSource(sourceFile) ||
+ !checkTarget(targetFile, sourceFile)) {
+ return;
}
-
- return checkDstOverwrite();
-
- }
-
- /**
- * Make some check on src file and on dst file
- *
- */
- private boolean check() {
-
- if (_fileSrc == null || _fileDst == null) { return false; }
-
- // same file check
- if (_fileSrc.toString().equalsIgnoreCase(_fileDst.toString())) {
- System.err.println("Same file !!!");
- return false;
+ if (verbose) {
+ out.println("Copying file '" + sourceFile + "' as '" + targetFile + "'");
}
-
- // file src check
- if (!_fileSrc.exists()) {
- System.err.println(_fileSrc.getAbsolutePath() + " not found");
- return false;
+
+ InputStream sin = null;
+ OutputStream tout = null;
+ try {
+ sin = new FileInputStream(sourceFile);
+ tout = new FileOutputStream(targetFile);
+ while (true) {
+ int nosBytesRead = sin.read(buffer);
+ if (nosBytesRead <= 0) {
+ break;
+ }
+ tout.write(buffer, 0, nosBytesRead);
+ }
}
- if (!_fileSrc.canRead()) {
- System.err.println("You havn't right too read "
- + _fileSrc.getAbsolutePath());
- return false;
- }
-
- // Source file is a directory ?
- if (_fileSrc.isDirectory()) {
- if (!_recursive) {
- System.err.println("For recursive copy, please use option -r");
- return false;
+ finally {
+ if (sin != null) {
+ try {
+ sin.close();
+ }
+ catch (IOException ex) {
+ // ignore
+ }
}
- if (_fileDst.isFile()) {
- System.err.println(_fileDst.getAbsolutePath()
- + " is not a directory ");
- return false;
+ if (tout != null) {
+ try {
+ tout.close();
+ }
+ catch (IOException ex) {
+ // ignore
+ }
}
- _srcIsDir = true;
- return true; // OK !
}
- // src not a dir, need more check
- _srcIsDir = false;
- // dst file is a directory ?
- if (_fileDst.isDirectory()) {
- _fileDst = new File(_fileDst.getAbsolutePath() + File.separator
- + _fileSrc.getName());
- }
-
- return checkDstOverwrite();
+ filesCopied++;
}
/**
- * We can overwrite the dst file ?
+ * Check that a source object exists, is readable and is either
+ * a file or a directory.
*
+ * @param source
* @return
*/
- private boolean checkDstOverwrite() {
- if (_fileDst.isFile()) {
- switch (_mode) {
- case MODE_BASE:
- System.err.println(_fileDst.getAbsolutePath()
- + " already exist");
- return false;
- case MODE_UPDATE:
- if (_fileSrc == null
- || _fileSrc.lastModified() <= _fileDst.lastModified()) { return false; }
- break;
- case MODE_ITERATIVE:
- if (!overWriteQuerry(_fileDst.getAbsolutePath())) { return false; }
- break;
- case MODE_FORCE:
- break;
- default:
- return false;
- }
- if (!_fileDst.canWrite()) {
- System.err.println(_fileDst.getAbsolutePath()
- + " cannot overwrite");
- return false;
- }
+ private boolean checkSource(File source) {
+ if (!source.exists()) {
+ return skip("'" + source + "' does not exist");
}
- return true;
- }
-
- /**
- * Copy the file src to the dst file
- *
- * @return number of copied file
- */
- private int copyFile() {
- InputStream is;
- FileOutputStream os;
- try {
- is = new FileInputStream(_fileSrc);
- } catch (FileNotFoundException fEx) {
- System.err.println(_fileSrc.getAbsolutePath() + " not found");
- return 0;
+ else if (!source.canRead()) {
+ return skip("'" + source + "' cannot be read");
}
- os = initDstFile();
- if (os == null) return 0;
-
- if (!copyData(is, os)) { return 0; }
- if (_verbose) {
- System.out.println("Copie : " + _fileSrc.getAbsolutePath() + " to "
- + _fileDst.getAbsolutePath());
+ else if (!(source.isFile() || source.isDirectory())) {
+ return vskip("'" + source + "' is a device");
}
- return 1;
- }
-
- private int copyDir() throws Exception {
- final File dstDir = new File(_fileDst.getAbsoluteFile()
- + File.separator);//+_fileSrc.getName()+File.separator);
- final File[] subFile = _fileSrc.listFiles();
- int numberFileCopied = 0;
-
- if (!dstDir.exists()) {
- if (!dstDir.mkdir()) {
- System.err.println(_fileDst.getParentFile().getAbsolutePath()
- + " cannot create ");
- return 0;
- }
+ else {
+ return true;
}
- for (int i = 0; i < subFile.length; i++) {
- final String name = subFile[ i].getName();
- if (name.equals(".") || name.equals("..")) continue;
- File subDstDir = new File(dstDir.getAbsoluteFile() + File.separator
- + name);
- CpCommand cp = new CpCommand(subFile[ i], subDstDir, _mode,
- _recursive, _verbose);
- numberFileCopied += cp.copy();
- }
- return numberFileCopied;
}
/**
- * Copy the url src to the dst file
+ * Check that a copy is going to be safe. Unsafe things are copying a
+ * file to itself and copying a directory into itself or a subdirectory.
*
- * @return number of copied file
- */
- private int copyURL() {
- InputStream is;
- FileOutputStream os;
-
- os = initDstFile();
- if (os == null) return 0;
- try {
- is = _urlSrc.openStream();
- } catch (IOException fEx) {
- System.err.println("File not found " + _urlSrc.toExternalForm());
- return 0;
- }
-
- if (!copyData(is, os)) { return 0; }
- if (_verbose) {
- System.out.println("Copie : " + _urlSrc.toExternalForm() + " to "
- + _fileDst.getAbsolutePath());
- }
- return 1;
- }
-
- /**
- * Copy an inputstream to a outputstream
- *
- * @param is
- * @param os
+ * @param source
+ * @param target
* @return
+ * @throws IOException
*/
- private boolean copyData(InputStream is, OutputStream os) {
- try {
- int len = 0;
- //final byte[] buf = new byte[128*1024];
- while ((len = is.read(buf)) > 0) {
- os.write(buf, 0, len);
+ private boolean checkSafe(File source, File target) throws IOException {
+ // These checks must be done with canonical paths. But fortunately they
+ // don't need to be repeated for every file/directory in a recursive copy.
+ String sourcePath = source.getCanonicalPath();
+ String targetPath = target.getCanonicalPath();
+ if (target.isDirectory()) {
+ if (recursive && source.isDirectory()) {
+ if (sourcePath.equals(targetPath)) {
+ return skip("Cannot copy directory '" + source + "' into itself");
+ }
+ if (!sourcePath.endsWith(File.separator)) {
+ sourcePath = sourcePath + File.separatorChar;
+ }
+ if (targetPath.startsWith(sourcePath)) {
+ return skip("Cannot copy directory '" + source +
+ "' into a subdirectory ('" + target + "')");
+ }
}
- os.close();
- is.close();
- } catch (IOException io) {
- System.err.println("An error is occure : copy aborted");
- io.printStackTrace();
- try {
- _fileDst.delete(); // clean
- } catch (Exception ex) {
+ }
+ else {
+ if (sourcePath.equals(targetPath)) {
+ return skip("Cannot copy file '" + source + "' to itself");
}
- return false;
}
return true;
}
/**
- * Open the dst file Make parent is need Delete if exist
+ * Check that the target can be written / overwritten. In interactive mode,
+ * the user is asked about clobbering existing files. In update mode, they
+ * are overwritten if the source is newer than the target. In force mode, they
+ * are clobbered without asking. In normal mode, existing target files are
+ * skipped.
*
- * @return the file outputstream
+ * @param target
+ * @param source
+ * @return
*/
- private FileOutputStream initDstFile() {
- final File dstParent = _fileDst.getParentFile();
- if (dstParent != null && !dstParent.exists()) { // make parent dir
- if (!dstParent.mkdirs()) {
- System.err.println("Directory can't create "
- + _fileDst.getParentFile().getAbsolutePath());
- return null;
- }
+ private boolean checkTarget(File target, File source) {
+ if (!target.exists()) {
+ return true;
}
- if (_fileDst.exists() && !_fileDst.delete()) {
- System.err.println("File can't overwrite "
- + _fileDst.getAbsolutePath());
- return null;
+ if (target.isDirectory() && !source.isDirectory()) {
+ return skip("Cannot copy '" + source + "' onto directory '" + target + "'");
}
-
- try {
- if (!_fileDst.createNewFile()) {
- System.err.println("File can't create "
- + _fileDst.getAbsolutePath());
- return null;
- }
- return new FileOutputStream(_fileDst);
- } catch (IOException io) {
- System.err.println("File can't create "
- + _fileDst.getAbsolutePath());
- } catch (SecurityException sec) {
- System.err.println("You havn't right too create "
- + _fileDst.getAbsolutePath());
+ if (!target.isFile()) {
+ return vskip("Cannot copy '" + source + "' to device '" + target + "'");
}
- return null;
-
- }
-
- // STATIC METHODES
-
- public static void main(String[] args) throws Exception {
- CpCommand cpCommand = new CpCommand(args);
- int nbCopiedFile = cpCommand.copy();
- System.out.println(nbCopiedFile + " file(s) copied");
- }
-
- /**
- * Ask user for owerwrite a file
- *
- * @param fileName
- * @return
- */
- private static boolean overWriteQuerry(String fileName) {
-
- final StringBuilder sbRead = new StringBuilder(256);
- final InputStreamReader reader = new InputStreamReader(System.in);
-
- String reponse = null;
-
- System.out.print("Overwrite " + fileName + " [N] ? ");
- try {
- int readInt;
- while ((readInt = reader.read()) > 0) {
- char ch = (char) readInt;
- if (ch == '\r') {
- continue;
+ switch (mode) {
+ case MODE_NORMAL:
+ return vskip("'" + target + "' already exists");
+ case MODE_FORCE:
+ return true;
+ case MODE_UPDATE:
+ return (source.lastModified() > target.lastModified() ||
+ vskip("'" + target + "' is newer than '" + source + "'"));
+ case MODE_INTERACTIVE:
+ out.print("Overwrite '" + target + "' with '" + source + "'? [y/n]");
+ while (true) {
+ try {
+ String line = in.readLine();
+ if (line == null) {
+ error("EOF - abandoning copying");
+ }
+ if (line.length() > 0) {
+ if (line.charAt(0) == 'y' || line.charAt(0) == 'Y') {
+ return true;
+ }
+ else if (line.charAt(0) == 'n' || line.charAt(0) == 'N') {
+ return vskip("'" + target + "'");
+ }
+ }
+ out.print("Answer 'y' or 'n'");
}
- if (ch == '\n') {
- break;
+ catch (IOException ex) {
+ error("IO Error - abandoning copying");
}
- sbRead.append(ch);
- System.out.print(ch); // Console echo
}
- System.out.println();
- reponse = sbRead.toString().trim();
- if (reponse.equalsIgnoreCase("Y")
- || reponse.equalsIgnoreCase("YES")) {
- return true;
- } else {
- return false;
- }
- } catch (IOException io) {
}
return false;
}
+ private void error(String msg) {
+ err.println(msg);
+ exit(1);
+ }
+
+ private boolean skip(String msg) {
+ err.println(msg + ": skipping");
+ return false;
+ }
+
+ private boolean vskip(String msg) {
+ if (verbose) {
+ err.println(msg + ": skipping");
+ }
+ return false;
+ }
}
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|