public void doCopy(File srcPath, SVNRevision srcRevision, File dstPath, boolean force, boolean isMove) throws SVNException {
srcPath = new File(SVNPathUtil.validateFilePath(srcPath.getAbsolutePath())).getAbsoluteFile();
dstPath = new File(SVNPathUtil.validateFilePath(dstPath.getAbsolutePath())).getAbsoluteFile();
if (srcRevision.isValid() && srcRevision != SVNRevision.WORKING && !isMove) {
// url->wc copy
SVNWCAccess wcAccess = createWCAccess();
SVNURL srcURL = null;
try {
wcAccess.probeOpen(srcPath, false, 0);
SVNEntry srcEntry = wcAccess.getEntry(srcPath, false);
if (srcEntry == null) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.ENTRY_NOT_FOUND, "''{0}'' is not under version control", srcPath);
SVNErrorManager.error(err);
}
if (srcEntry.getURL() == null) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.ENTRY_MISSING_URL, "''{0}'' has no URL", srcPath);
SVNErrorManager.error(err);
}
srcURL = srcEntry.getSVNURL();
} finally {
wcAccess.close();
}
doCopy(srcURL, srcRevision, dstPath);
return;
}
// 1. can't copy src to its own child
if (SVNPathUtil.isChildOf(srcPath, dstPath) || srcPath.equals(dstPath)) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.UNSUPPORTED_FEATURE, "Cannot copy ''{0}'' into its own child ''{1}''",
new Object[] {srcPath, dstPath});
SVNErrorManager.error(err);
}
// 2. can't move path into itself
if (isMove && srcPath.equals(dstPath)) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.UNSUPPORTED_FEATURE, "Cannot move ''{0}'' into itself", srcPath);
SVNErrorManager.error(err);
}
// 3. src should exist
SVNFileType srcType = SVNFileType.getType(srcPath);
if (srcType == SVNFileType.NONE) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.NODE_UNKNOWN_KIND, "Path ''{0}'' does not exist", srcPath);
SVNErrorManager.error(err);
}
// 4. if dst exists - use its child
SVNFileType dstType = SVNFileType.getType(dstPath);
if (dstType == SVNFileType.DIRECTORY) {
dstPath = new File(dstPath, srcPath.getName());
dstType = SVNFileType.getType(dstPath);
if (dstType != SVNFileType.NONE) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.WC_OBSTRUCTED_UPDATE, "''{0}'' already exists and is in the way", dstPath);
SVNErrorManager.error(err);
}
} else if (dstType != SVNFileType.NONE) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.ENTRY_EXISTS, "File ''{0}'' already exists", dstPath);
SVNErrorManager.error(err);
}
SVNWCAccess wcAccess = createWCAccess();
SVNAdminArea adminArea = null;
File srcParent = srcPath.getParentFile();
File dstParent = dstPath.getParentFile();
try {
SVNAdminArea srcParentArea = null;
if (isMove) {
srcParentArea = wcAccess.open(srcParent, true, srcType == SVNFileType.DIRECTORY ? SVNWCAccess.INFINITE_DEPTH : 0);
if (srcParent.equals(dstParent)) {
adminArea = srcParentArea;
} else {
if (srcType == SVNFileType.DIRECTORY && SVNPathUtil.isChildOf(srcParent, dstParent)) {
adminArea = wcAccess.retrieve(dstParent);
} else {
adminArea = wcAccess.open(dstParent, true, 0);
}
}
if (!force) {
try {
SVNWCManager.canDelete(srcPath, getOptions(), this);
} catch (SVNException svne) {
SVNErrorMessage err = svne.getErrorMessage().wrap("Move will not be attempted unless forced");
SVNErrorManager.error(err, svne);
}
}
} else {
adminArea = wcAccess.open(dstParent, true, 0);
}
SVNWCAccess copyAccess = createWCAccess();
try {
SVNAdminArea srcArea = copyAccess.probeOpen(srcPath, false, SVNWCAccess.INFINITE_DEPTH);
SVNEntry dstEntry = adminArea.getEntry(adminArea.getThisDirName(), false);
if (dstEntry == null) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.ENTRY_NOT_FOUND, "''{0}'' is not under version control", adminArea.getRoot());
SVNErrorManager.error(err);
}
SVNEntry srcEntry = copyAccess.getEntry(srcPath, false);
if (srcEntry == null) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.ENTRY_NOT_FOUND, "''{0}'' is not under version control", srcPath);
SVNErrorManager.error(err);
}
if (srcEntry.getRepositoryRoot() != null && dstEntry.getRepositoryRoot() != null &&
!srcEntry.getRepositoryRoot().equals(dstEntry.getRepositoryRoot())) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.WC_INVALID_SCHEDULE, "Cannot copy to ''{0}'', as it is not from repository ''{1}''; it is from ''{2}''", new Object[] {adminArea.getRoot(), srcEntry.getRepositoryRoot(), dstEntry.getRepositoryRoot()});
SVNErrorManager.error(err);
}
if (dstEntry.isScheduledForDeletion()) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.WC_INVALID_SCHEDULE, "Cannot copy to ''{0}'' as it is scheduled for deletion", adminArea.getRoot());
SVNErrorManager.error(err);
}
if (srcType == SVNFileType.FILE) {
copyFile(adminArea, srcArea, srcPath, dstPath.getName());
} else if (srcType == SVNFileType.DIRECTORY) {
copyDir(adminArea, srcArea, srcPath, dstPath.getName());
}
} finally {
copyAccess.close();
}
if (isMove) {
SVNWCManager.delete(srcParentArea.getWCAccess(), srcParentArea, srcPath, true, false);
}
} finally {