Skip to main content
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichael Valenta2002-04-23 15:30:29 +0000
committerMichael Valenta2002-04-23 15:30:29 +0000
commitacadf96a4ce3fa8044a2459c7b8de7a989541edb (patch)
tree05ac57b4be2bef4a7561dbd140d2878e2ffad2df
parent28df34b0a427aff6ffb90ee7fe456db20b65c289 (diff)
downloadeclipse.platform.team-acadf96a4ce3fa8044a2459c7b8de7a989541edb.tar.gz
eclipse.platform.team-acadf96a4ce3fa8044a2459c7b8de7a989541edb.tar.xz
eclipse.platform.team-acadf96a4ce3fa8044a2459c7b8de7a989541edb.zip
232: VCM UI + CVS: multiple round trips caused by API client (1GIZ4I8)
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Command.java50
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Session.java107
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IStatusListener.java22
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IUpdateMessageListener.java49
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/StatusListener.java19
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/UpdateListener.java31
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/messages.properties2
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSEntryLineTag.java7
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFile.java180
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolder.java342
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTree.java6
-rw-r--r--bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteResource.java9
-rw-r--r--bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/CVSCompareEditorInput.java37
-rw-r--r--bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/merge/MergeEditorInput.java44
14 files changed, 578 insertions, 327 deletions
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Command.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Command.java
index ee4bd2219..654bb3e5c 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Command.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Command.java
@@ -1,10 +1,15 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2002 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ *
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
package org.eclipse.team.internal.ccvs.core.client;
-/*
- * (c) Copyright IBM Corp. 2000, 2002.
- * All Rights Reserved.
- */
-
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Hashtable;
@@ -675,4 +680,39 @@ public abstract class Command extends Request {
protected LocalOption[] filterLocalOptions(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions) {
return localOptions;
}
+
+ /**
+ * Execute a CVS command inside an ICVSRunnable passed to Session.run()
+ * <p>
+ * Dispatches the commands, retrieves the results, and determines whether or
+ * not an error occurred. A listener may be supplied to capture message text
+ * that would normally be written to the standard error and standard output
+ * streams of a command line CVS client.
+ * </p>
+ * @param globalOptions the array of global options, or NO_GLOBAL_OPTIONS
+ * @param localOptions the array of local options, or NO_LOCAL_OPTIONS
+ * @param arguments the array of arguments (usually filenames relative to localRoot), or NO_ARGUMENTS
+ * @param listener the command output listener, or null to discard all messages
+ * @param monitor the progress monitor
+ * @return a status code indicating success or failure of the operation
+ * @throws CVSException if a fatal error occurs (e.g. connection timeout)
+ */
+ public final IStatus execute(GlobalOption[] globalOptions, LocalOption[] localOptions, ICVSResource[] arguments,
+ ICommandOutputListener listener, IProgressMonitor pm) throws CVSException {
+
+ // We assume that all the passed resources have the same root
+ Session openSession = Session.getOpenSession(arguments[0]);
+ if (openSession == null) {
+ throw new CVSException(Policy.bind("Command.noOpenSession")); //$NON-NLS-1$
+ } else {
+ // Convert arguments
+ List stringArguments = new ArrayList(arguments.length);
+ for (int i = 0; i < arguments.length; i++) {
+ stringArguments.add(arguments[i].getRelativePath(openSession.getLocalRoot()));
+ }
+ return execute(openSession, globalOptions, localOptions, (String[]) stringArguments.toArray(new String[stringArguments.size()]), listener, pm);
+ }
+
+
+ }
} \ No newline at end of file
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Session.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Session.java
index 080cf8214..a46b1846f 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Session.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Session.java
@@ -41,6 +41,7 @@ import org.eclipse.team.internal.ccvs.core.ICVSFolder;
import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation;
import org.eclipse.team.internal.ccvs.core.ICVSResource;
import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor;
+import org.eclipse.team.internal.ccvs.core.ICVSRunnable;
import org.eclipse.team.internal.ccvs.core.Policy;
import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation;
import org.eclipse.team.internal.ccvs.core.connection.Connection;
@@ -86,6 +87,9 @@ public class Session {
private static final boolean IS_CRLF_PLATFORM = Arrays.equals(
System.getProperty("line.separator").getBytes(), new byte[] { '\r', '\n' }); //$NON-NLS-1$
+ private static Map currentOpenSessions = null;
+ private static final int MAX_SESSIONS_OPEN = 10;
+
private CVSRepositoryLocation location;
private ICVSFolder localRoot;
private boolean outputToConsole;
@@ -127,6 +131,109 @@ public class Session {
this.outputToConsole = outputToConsole;
}
+ /**
+ * Execute the given runnable in a context that has access to an open session
+ *
+ * A session will be opened for the provided root. If the root is null, no session is opened.
+ * However, sessions will be open for nested calls to run and these sessions will not be closed
+ * until the outer most run finishes.
+ */
+ public static void run(ICVSRepositoryLocation location, ICVSFolder root, boolean outputToConsole,
+ ICVSRunnable runnable, IProgressMonitor monitor) throws CVSException {
+
+ // Determine if we are nested or not
+ boolean isOuterRun = false;
+ if (currentOpenSessions == null) {
+ // Initialize the variable to be a map
+ currentOpenSessions = new HashMap();
+ isOuterRun = true;
+ }
+
+ try {
+ monitor = Policy.monitorFor(monitor);
+ monitor.beginTask(null, 100);
+ if (root == null) {
+ // We don't have a root, so just run the runnable
+ // (assuming that nested runs will create sessions)
+ runnable.run(Policy.subMonitorFor(monitor, 90));
+ } else {
+ // Open a session on the root as far up the chain as possible
+ ICVSFolder actualRoot = root;
+ while (actualRoot.isManaged()) {
+ actualRoot = actualRoot.getParent();
+ }
+ // Look for the root in the current open sessions
+ Session session = (Session)currentOpenSessions.get(actualRoot);
+ if (session == null) {
+ // Make sure we don't exceed our maximum
+ if (currentOpenSessions.size() == MAX_SESSIONS_OPEN) {
+ // Pick one at random and close it
+ Object key = currentOpenSessions.keySet().iterator().next();
+ try {
+ ((Session)currentOpenSessions.get(key)).close();
+ } catch (CVSException e) {
+ CVSProviderPlugin.log(e.getStatus());
+ } finally {
+ currentOpenSessions.remove(key);
+ }
+ }
+ // If it's not there, open a session for the given root and remember it
+ session = new Session(location, actualRoot, outputToConsole);
+ session.open(Policy.subMonitorFor(monitor, 10));
+ currentOpenSessions.put(actualRoot, session);
+ }
+
+ try {
+ root.run(runnable, Policy.subMonitorFor(monitor, 100));
+ } catch (CVSException e) {
+ // The run didn't succeed so close the session and forget it ever existed
+ try {
+ // The session may have been close by a nested run
+ if (currentOpenSessions.get(actualRoot) != null) session.close();
+ } finally {
+ currentOpenSessions.remove(actualRoot);
+ throw e;
+ }
+ }
+ }
+ } finally {
+ monitor.done();
+ if (isOuterRun) {
+ // Close all open sessions
+ try {
+ Iterator iter = currentOpenSessions.keySet().iterator();
+ while (iter.hasNext()) {
+ Session session = (Session)currentOpenSessions.get(iter.next());
+ try {
+ session.close();
+ } catch (CVSException e) {
+ CVSProviderPlugin.log(e.getStatus());
+ }
+ }
+ } finally {
+ currentOpenSessions = null;
+ }
+ }
+ }
+ }
+
+ /**
+ * Answer the currently open session
+ */
+ protected static Session getOpenSession(ICVSResource resource) {
+ ICVSFolder root;
+ if (resource.isFolder()) {
+ root = (ICVSFolder)resource;
+ } else {
+ root = resource.getParent();
+ }
+ while (root.isManaged()) {
+ root = root.getParent();
+ }
+ // Look for the root in the current open sessions
+ return (Session)currentOpenSessions.get(root);
+ }
+
/**
* Register a case collision with the session.
*
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IStatusListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IStatusListener.java
index 50c1e1dd8..f36162143 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IStatusListener.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IStatusListener.java
@@ -1,11 +1,17 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2002 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ *
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
package org.eclipse.team.internal.ccvs.core.client.listeners;
-
-/*
- * (c) Copyright IBM Corp. 2000, 2002.
- * All Rights Reserved.
- */
import org.eclipse.core.runtime.IPath;
+import org.eclipse.team.internal.ccvs.core.ICVSFolder;
public interface IStatusListener {
@@ -14,7 +20,9 @@ public interface IStatusListener {
/**
* Provides access to the revision of a file through the use of the Status command.
*
- * The provided path is the absoulte remote path of the resource including the repository root directory
+ * @param commandRoot the root directory of the command
+ * @param path the absolute remote path of the resource including the repository root directory
+ * @param remoteRevision the remote revision of the file
*/
- public void fileStatus(IPath path, String remoteRevision);
+ public void fileStatus(ICVSFolder commandRoot, IPath path, String remoteRevision);
}
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IUpdateMessageListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IUpdateMessageListener.java
index fe6f62f6b..c3583baa0 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IUpdateMessageListener.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IUpdateMessageListener.java
@@ -1,11 +1,17 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2002 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ *
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
package org.eclipse.team.internal.ccvs.core.client.listeners;
-
-/*
- * (c) Copyright IBM Corp. 2000, 2002.
- * All Rights Reserved.
- */
import org.eclipse.core.runtime.IPath;
+import org.eclipse.team.internal.ccvs.core.ICVSFolder;
/**
* This listener is used by RemoteFolder to listener for E and M messages
@@ -13,17 +19,34 @@ import org.eclipse.core.runtime.IPath;
*/
public interface IUpdateMessageListener {
/**
- * information that a directory which has been reported using directoryInformation() does not exist
+ * Notification that a directory (which may or may not have been reported by
+ * directoryInformation()) does not exist.
+ *
+ * @param commandRoot the root directory of the command
+ * @param path the path of the directory relative to the commandRoot
+ */
+ public void directoryDoesNotExist(ICVSFolder commandRoot, IPath path);
+ /**
+ * Notification of information about a directory.
+ *
+ * @param commandRoot the root directory of the command
+ * @param path the path of the directory relative to the commandRoot
+ * @param newDirectory true if the directory does not exist locally (i.e. in the commandRoot hierarchy)
*/
- public void directoryDoesNotExist(IPath path);
+ public void directoryInformation(ICVSFolder commandRoot, IPath path, boolean newDirectory);
/**
- * directory information
+ * Notification of information about a file
+ *
+ * @param type the type of update for the file (see Update for type constants)
+ * @param commandRoot the root directory of the command
+ * @param filename the path of the file relative to the commandRoot
*/
- public void directoryInformation(IPath path, boolean newDirectory);
+ public void fileInformation(int type, ICVSFolder parent, String filename);
/**
- * file information
+ * Notification that a file does not exists remotely
+ *
+ * @param commandRoot the root directory of the command
+ * @param filename the path of the file relative to the commandRoot
*/
- public void fileInformation(int type, String filename);
-
- public void fileDoesNotExist(String filename);
+ public void fileDoesNotExist(ICVSFolder parent, String filename);
}
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/StatusListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/StatusListener.java
index 8fccd7116..cdf501883 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/StatusListener.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/StatusListener.java
@@ -1,10 +1,15 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2002 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ *
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
package org.eclipse.team.internal.ccvs.core.client.listeners;
-/*
- * (c) Copyright IBM Corp. 2000, 2002.
- * All Rights Reserved.
- */
-
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
@@ -47,7 +52,7 @@ public class StatusListener implements ICommandOutputListener {
}
// Inform the listener about the file revision
- statusListener.fileStatus(fullPath, remoteRevision);
+ statusListener.fileStatus(commandRoot, fullPath, remoteRevision);
}
}
return OK;
@@ -69,7 +74,7 @@ public class StatusListener implements ICommandOutputListener {
// (i.e. the resource is a folder)
if (statusListener != null)
// XXX We should be using that path relative to the root of the command (mRoot)!!!
- statusListener.fileStatus(new Path(folderPath).removeFirstSegments(1), IStatusListener.FOLDER_REVISION);
+ statusListener.fileStatus(commandRoot, new Path(folderPath).removeFirstSegments(1), IStatusListener.FOLDER_REVISION);
isFolder = false;
return OK;
}
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/UpdateListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/UpdateListener.java
index 847bb11f1..e70a71d8a 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/UpdateListener.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/UpdateListener.java
@@ -1,10 +1,15 @@
+/*******************************************************************************
+ * Copyright (c) 2000, 2002 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Common Public License v0.5
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/cpl-v05.html
+ *
+ * Contributors:
+ * IBM - Initial API and implementation
+ ******************************************************************************/
package org.eclipse.team.internal.ccvs.core.client.listeners;
-/*
- * (c) Copyright IBM Corp. 2000, 2002.
- * All Rights Reserved.
- */
-
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
@@ -56,7 +61,7 @@ public class UpdateListener implements ICommandOutputListener {
type = Update.STATE_MERGEABLE_CONFLICT;
merging = false;
}
- updateMessageListener.fileInformation(type, path);
+ updateMessageListener.fileInformation(type, commandRoot, path);
}
return OK;
}
@@ -99,23 +104,23 @@ public class UpdateListener implements ICommandOutputListener {
String message = line.substring(SERVER_PREFIX.length());
if (message.startsWith("Updating")) { //$NON-NLS-1$
if (updateMessageListener != null) {
- IPath path = new Path(message.substring(8));
- updateMessageListener.directoryInformation(path, false);
+ IPath path = new Path(message.substring(9));
+ updateMessageListener.directoryInformation(commandRoot, path, false);
}
} else if (message.startsWith("skipping directory")) { //$NON-NLS-1$
if (updateMessageListener != null) {
IPath path = new Path(message.substring(18).trim());
- updateMessageListener.directoryDoesNotExist(path);
+ updateMessageListener.directoryDoesNotExist(commandRoot, path);
}
} else if (message.startsWith("New directory")) { //$NON-NLS-1$
if (updateMessageListener != null) {
IPath path = new Path(message.substring(15, message.indexOf('\'', 15)));
- updateMessageListener.directoryInformation(path, true);
+ updateMessageListener.directoryInformation(commandRoot, path, true);
}
} else if (message.endsWith("is no longer in the repository")) { //$NON-NLS-1$
if (updateMessageListener != null) {
String filename = message.substring(0, message.length() - 31);
- updateMessageListener.fileDoesNotExist(filename);
+ updateMessageListener.fileDoesNotExist(commandRoot, filename);
}
} else if (message.startsWith("conflict:")) { //$NON-NLS-1$
/*
@@ -130,7 +135,7 @@ public class UpdateListener implements ICommandOutputListener {
if (message.endsWith("is modified but no longer in the repository")) { //$NON-NLS-1$
// The "C foler/file.ext" will come after this so if whould be ignored!
String filename = message.substring(10, message.length() - 44);
- updateMessageListener.fileDoesNotExist(filename);
+ updateMessageListener.fileDoesNotExist(commandRoot, filename);
}
}
return new CVSStatus(CVSStatus.WARNING, CVSStatus.CONFLICT, line);
@@ -143,7 +148,7 @@ public class UpdateListener implements ICommandOutputListener {
if (updateMessageListener != null) {
if (message.endsWith("is not (any longer) pertinent")) { //$NON-NLS-1$
String filename = message.substring(9, message.length() - 30);
- updateMessageListener.fileDoesNotExist(filename);
+ updateMessageListener.fileDoesNotExist(commandRoot, filename);
}
}
return new CVSStatus(CVSStatus.WARNING, CVSStatus.CONFLICT, line);
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/messages.properties b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/messages.properties
index 2e55e5a87..83ec04217 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/messages.properties
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/messages.properties
@@ -106,6 +106,7 @@ RemoteResource.invalidOperation=Invalid operation performed on remote resource
RemoteFolder.errorFetchingRevisions=Error fetching file revision numbers
RemoteFolder.invalidChild=Resource {0} is not a child of folder {1}
RemoteFolder.errorFetchingRevisions=Error fetching file revisions
+RemoteFolder.errorFetchingMembers=One or more error occured fetching the members of a remote folder
RemoteFolder.doesNotExist=Folder {0} does not exist remotely
RemoteFile.noContentsReceived=No contents received from server for {0}
@@ -141,6 +142,7 @@ Command.valid-requests=valid-requests
Command.unsupportedResponse=Unknown response received from cvs server: {0} {1}
Command.argumentNotManaged=Argument {0} is not managed
Command.invalidTag=HEAD is not a valid tag
+Command.noOpenSession=The CVS command cannot be issued because there is no connection available
Tag.notVersionOrBranchError=Error applying tag: the tag provided is not a version or branch tag.
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSEntryLineTag.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSEntryLineTag.java
index a8c37a767..ac60cf365 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSEntryLineTag.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSEntryLineTag.java
@@ -48,13 +48,6 @@ public class CVSEntryLineTag extends CVSTag {
return "";//$NON-NLS-1$
}
- public boolean equals(Object obj) {
- // We assume, that the name and type can not be null
- if (obj == this) return true;
- if (!(obj instanceof CVSEntryLineTag)) return false;
- return (type == ((CVSEntryLineTag)obj).type) && name.equals(((CVSEntryLineTag)obj).name);
- }
-
/*
* For debugging purposes.
*/
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFile.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFile.java
index 03b791bb7..fe3286756 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFile.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFile.java
@@ -34,7 +34,9 @@ import org.eclipse.team.internal.ccvs.core.ICVSFolder;
import org.eclipse.team.internal.ccvs.core.ICVSRemoteFile;
import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource;
import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation;
+import org.eclipse.team.internal.ccvs.core.ICVSResource;
import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor;
+import org.eclipse.team.internal.ccvs.core.ICVSRunnable;
import org.eclipse.team.internal.ccvs.core.ILogEntry;
import org.eclipse.team.internal.ccvs.core.Policy;
import org.eclipse.team.internal.ccvs.core.client.Command;
@@ -190,133 +192,111 @@ public class RemoteFile extends RemoteResource implements ICVSRemoteFile {
// We will end up here if we couldn't read or delete the cache file
throw new CVSException(new CVSStatus(IStatus.ERROR, 0, Policy.bind("RemoteFile.errorRetrievingFromCache", e.getMessage()), e));//$NON-NLS-1$
}
- monitor = Policy.monitorFor(monitor);
- monitor.beginTask(Policy.bind("RemoteFile.getContents"), 100); //$NON-NLS-1$
- try {
- List entries = new ArrayList();
- IStatus status;
- Session s = new Session(getRepository(), parent, false);
- s.open(Policy.subMonitorFor(monitor, 10));
- try {
- status = Command.UPDATE.execute(s,
+
+ Session.run(getRepository(), parent, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ monitor.beginTask(null, 100);
+ IStatus status = Command.UPDATE.execute(
Command.NO_GLOBAL_OPTIONS,
new LocalOption[] {
Update.makeTagOption(new CVSTag(info.getRevision(), CVSTag.VERSION)),
Update.IGNORE_LOCAL_CHANGES },
- new String[] { getName() },
+ new ICVSResource[] { RemoteFile.this },
null,
- Policy.subMonitorFor(monitor, 80));
- if (status.getCode() != CVSStatus.SERVER_ERROR && entry == null) {
- getLogEntry(s, Policy.subMonitorFor(monitor, 10));
- // Ignore the status of the log entry fetch.
- // If it fails, the entry will still be null
+ Policy.subMonitorFor(monitor, 90));
+ if (status.getCode() != CVSStatus.SERVER_ERROR) {
+ try {
+ getLogEntry(Policy.subMonitorFor(monitor, 10));
+ } catch (CVSException e) {
+ // Ignore the status of the log entry fetch.
+ // If it fails, the entry will still be null
+ }
+ }
+ monitor.done();
+ if (status.getCode() == CVSStatus.SERVER_ERROR) {
+ throw new CVSServerException(status);
}
- } finally {
- s.close();
- }
- if (status.getCode() == CVSStatus.SERVER_ERROR) {
- throw new CVSServerException(status);
}
- // If the update succeeded but no contents were retreived from the server
- // than we can assume that the remote file has no contents.
- if (contents == null) {
- // The above is true unless there is a cache file
- try {
- File ioFile = CVSProviderPlugin.getPlugin().getCacheFileFor(getCacheRelativePath());
- if (ioFile.exists()) {
- return new BufferedInputStream(new FileInputStream(ioFile));
- } else {
- contents = new byte[0];
- }
- } catch (IOException e) {
- // Something is wrong with the cached file so signal an error.
- throw new CVSException(new CVSStatus(IStatus.ERROR, 0, Policy.bind("RemoteFile.errorRetrievingFromCache", e.getMessage()), e));//$NON-NLS-1$
+ }, monitor);
+
+ // If the update succeeded but no contents were retreived from the server
+ // than we can assume that the remote file has no contents.
+ if (contents == null) {
+ // The above is true unless there is a cache file
+ try {
+ File ioFile = CVSProviderPlugin.getPlugin().getCacheFileFor(getCacheRelativePath());
+ if (ioFile.exists()) {
+ return new BufferedInputStream(new FileInputStream(ioFile));
+ } else {
+ contents = new byte[0];
}
+ } catch (IOException e) {
+ // Something is wrong with the cached file so signal an error.
+ throw new CVSException(new CVSStatus(IStatus.ERROR, 0, Policy.bind("RemoteFile.errorRetrievingFromCache", e.getMessage()), e));//$NON-NLS-1$
}
- } finally {
- monitor.done();
}
}
return new ByteArrayInputStream(contents);
}
/*
- * @see ICVSRemoteFile#getLogEntry()
+ * @see ICVSRemoteFile#getLogEntry(IProgressMonitor)
*/
public ILogEntry getLogEntry(IProgressMonitor monitor) throws CVSException {
if (entry == null) {
- monitor = Policy.monitorFor(monitor);
- monitor.beginTask(Policy.bind("RemoteFile.getLogEntries"), 100); //$NON-NLS-1$
- try {
- Session s = new Session(getRepository(), parent, false);
- s.open(Policy.subMonitorFor(monitor, 10));
- try {
- IStatus status = getLogEntry(s, Policy.subMonitorFor(monitor, 90));
- if (status.getCode() == CVSStatus.SERVER_ERROR) {
- throw new CVSServerException(status);
+ Session.run(getRepository(), parent, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ monitor = Policy.monitorFor(monitor);
+ monitor.beginTask(Policy.bind("RemoteFile.getLogEntries"), 100); //$NON-NLS-1$
+ try {
+ final List entries = new ArrayList();
+ IStatus status = Command.LOG.execute(
+ Command.NO_GLOBAL_OPTIONS,
+ new LocalOption[] {
+ Command.LOG.makeRevisionOption(info.getRevision())},
+ new ICVSResource[] { RemoteFile.this },
+ new LogListener(RemoteFile.this, entries),
+ Policy.subMonitorFor(monitor, 100));
+ if (entries.size() == 1) {
+ entry = (ILogEntry)entries.get(0);
+ }
+ if (status.getCode() == CVSStatus.SERVER_ERROR) {
+ throw new CVSServerException(status);
+ }
+ } finally {
+ monitor.done();
}
- } finally {
- s.close();
}
- } finally {
- monitor.done();
- }
+ }, monitor);
}
return entry;
}
- /*
- * Fetch the log entry corresponding to the receivers revision and set the entry
- * instance variable to the result. If the fecth failed, entry will be null and
- * the resulting IStatus will contain any errors.
- */
- private IStatus getLogEntry(Session session, IProgressMonitor monitor) throws CVSException {
- List entries = new ArrayList();
- IStatus status = Command.LOG.execute(session,
- Command.NO_GLOBAL_OPTIONS,
- new LocalOption[] {
- Command.LOG.makeRevisionOption(info.getRevision())},
- new String[] { getName() },
- new LogListener(this, entries),
- Policy.subMonitorFor(monitor, 10));
- if (entries.size() == 1) {
- entry = (ILogEntry)entries.get(0);
- } else {
- // No log entry was fetch for the remote file.
- entry = null;
- }
- return status;
- }
-
/**
* @see ICVSRemoteFile#getLogEntries()
*/
public ILogEntry[] getLogEntries(IProgressMonitor monitor) throws CVSException {
- monitor = Policy.monitorFor(monitor);
- monitor.beginTask(Policy.bind("RemoteFile.getLogEntries"), 100); //$NON-NLS-1$
- try {
- // Perform a "cvs log..." with a custom message handler
- final List entries = new ArrayList();
- IStatus status;
- Session s = new Session(getRepository(), parent, false);
- s.open(Policy.subMonitorFor(monitor, 10));
- QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness();
- try {
- CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE);
- status = Command.LOG.execute(s, Command.NO_GLOBAL_OPTIONS, Command.NO_LOCAL_OPTIONS,
- new String[] { getName() }, new LogListener(this, entries),
- Policy.subMonitorFor(monitor, 90));
- } finally {
- CVSProviderPlugin.getPlugin().setQuietness(quietness);
- s.close();
- }
- if (status.getCode() == CVSStatus.SERVER_ERROR) {
- throw new CVSServerException(status);
+ final List entries = new ArrayList();
+ Session.run(getRepository(), parent, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ monitor = Policy.monitorFor(monitor);
+ monitor.beginTask(Policy.bind("RemoteFile.getLogEntries"), 100); //$NON-NLS-1$
+ QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness();
+ try {
+ CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE);
+ IStatus status = Command.LOG.execute(Command.NO_GLOBAL_OPTIONS, Command.NO_LOCAL_OPTIONS,
+ new ICVSResource[] { RemoteFile.this }, new LogListener(RemoteFile.this, entries),
+ Policy.subMonitorFor(monitor, 100));
+ if (status.getCode() == CVSStatus.SERVER_ERROR) {
+ throw new CVSServerException(status);
+ }
+ } finally {
+ CVSProviderPlugin.getPlugin().setQuietness(quietness);
+ monitor.done();
+ }
}
- return (ILogEntry[])entries.toArray(new ILogEntry[entries.size()]);
- } finally {
- monitor.done();
- }
+ }, monitor);
+ return (ILogEntry[])entries.toArray(new ILogEntry[entries.size()]);
}
/**
@@ -352,10 +332,6 @@ public class RemoteFile extends RemoteResource implements ICVSRemoteFile {
public ResourceSyncInfo getSyncInfo() {
return info;
}
-
- public ICVSFolder getParent() {
- return parent;
- }
/**
* @see ICVSResource#getRelativePath(ICVSFolder)
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolder.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolder.java
index 0db7fcdab..3ddce36cc 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolder.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolder.java
@@ -12,6 +12,7 @@ import java.util.List;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.IProgressMonitor;
import org.eclipse.core.runtime.IStatus;
+import org.eclipse.core.runtime.MultiStatus;
import org.eclipse.core.runtime.OperationCanceledException;
import org.eclipse.core.runtime.Path;
import org.eclipse.team.core.TeamException;
@@ -84,13 +85,13 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
}
// Get the file revisions for the given filenames
- protected void updateFileRevisions(Session session, String[] fileNames, IProgressMonitor monitor) throws CVSException {
+ protected void updateFileRevisions(final ICVSFile[] files, IProgressMonitor monitor) throws CVSException {
final int[] count = new int[] {0};
// Create a listener for receiving the revision info
- IStatusListener listener = new IStatusListener() {
- public void fileStatus(IPath path, String remoteRevision) {
+ final IStatusListener listener = new IStatusListener() {
+ public void fileStatus(ICVSFolder parent, IPath path, String remoteRevision) {
if (remoteRevision == IStatusListener.FOLDER_REVISION)
// Ignore any folders
return;
@@ -98,7 +99,7 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
((RemoteFile)getChild(path.lastSegment())).setRevision(remoteRevision);
count[0]++;
} catch (CVSException e) {
- // The count wil be off to indicate an error
+ // The count will be off to indicate an error
}
}
};
@@ -107,20 +108,24 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness();
try {
CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE);
- IStatus status = Command.STATUS.execute(session,
- Command.NO_GLOBAL_OPTIONS,
- Command.NO_LOCAL_OPTIONS,
- fileNames,
- new StatusListener(listener),
- Policy.subMonitorFor(monitor, 100));
- if (status.getCode() == CVSStatus.SERVER_ERROR) {
- throw new CVSServerException(status);
- }
+ Session.run(getRepository(), this, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ IStatus status = Command.STATUS.execute(
+ Command.NO_GLOBAL_OPTIONS,
+ Command.NO_LOCAL_OPTIONS,
+ files,
+ new StatusListener(listener),
+ monitor);
+ if (status.getCode() == CVSStatus.SERVER_ERROR) {
+ throw new CVSServerException(status);
+ }
+ }
+ }, monitor);
} finally {
CVSProviderPlugin.getPlugin().setQuietness(quietness);
}
- if (count[0] != fileNames.length)
+ if (count[0] != files.length)
throw new CVSException(Policy.bind("RemoteFolder.errorFetchingRevisions")); //$NON-NLS-1$
}
@@ -159,62 +164,63 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
* CVS will signal an error if a folder only contains subfolders when a tag is used. If we get this
* error and we're looking for a folder, we need to reissue the command without a tag.
*/
- protected boolean exists(ICVSRemoteResource child, CVSTag tag, IProgressMonitor monitor) throws CVSException {
+ protected boolean exists(final ICVSRemoteResource child, CVSTag tag, IProgressMonitor monitor) throws CVSException {
final IProgressMonitor progress = Policy.monitorFor(monitor);
progress.beginTask(Policy.bind("RemoteFolder.exists"), 100); //$NON-NLS-1$
try {
// Create the listener for remote files and folders
final boolean[] exists = new boolean[] {true};
- IUpdateMessageListener listener = new IUpdateMessageListener() {
- public void directoryInformation(IPath path, boolean newDirectory) {
+ final IUpdateMessageListener listener = new IUpdateMessageListener() {
+ public void directoryInformation(ICVSFolder parent, IPath path, boolean newDirectory) {
exists[0] = true;
}
- public void directoryDoesNotExist(IPath path) {
+ public void directoryDoesNotExist(ICVSFolder parent, IPath path) {
exists[0] = false;
}
- public void fileInformation(int type, String filename) {
+ public void fileInformation(int type, ICVSFolder parent, String filename) {
// We can't set exists true here as we may get a conflict on a deleted file.
// i.e. remote files are always communicated to the server as modified.
}
- public void fileDoesNotExist(String filename) {
+ public void fileDoesNotExist(ICVSFolder parent, String filename) {
exists[0] = false;
}
};
// Build the local options
- List localOptions = new ArrayList();
+ final List localOptions = new ArrayList();
localOptions.add(Update.RETRIEVE_ABSENT_DIRECTORIES);
if (tag != null && tag.getType() != CVSTag.HEAD)
localOptions.add(Update.makeTagOption(tag));
// Retrieve the children and any file revision numbers in a single connection
- // Perform a "cvs -n update -d -r tagName folderName" with custom message and error handlers
- IStatus status;
- Session s = new Session(getRepository(), this, false);
- s.open(Policy.subMonitorFor(progress, 10));
- try {
- status = Command.UPDATE.execute(s,
- new GlobalOption[] { Command.DO_NOT_CHANGE },
- (LocalOption[]) localOptions.toArray(new LocalOption[localOptions.size()]),
- new String[] { child.getName() }, new UpdateListener(listener),
- Policy.subMonitorFor(progress, 90));
- } finally {
- s.close();
- }
- if (status.getCode() == CVSStatus.SERVER_ERROR) {
- CVSServerException e = new CVSServerException(status);
- if ( ! e.isNoTagException() || ! child.isContainer()) {
- if (e.containsErrors()) {
- throw e;
+ // Perform a "cvs -n update -d -r tagName folderName" with custom message and error handlers
+ final boolean[] retry = new boolean[] {false};
+ Session.run(getRepository(), this, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ IStatus status = Command.UPDATE.execute(
+ new GlobalOption[] { Command.DO_NOT_CHANGE },
+ (LocalOption[]) localOptions.toArray(new LocalOption[localOptions.size()]),
+ new ICVSResource[] { child }, new UpdateListener(listener),
+ monitor);
+ if (status.getCode() == CVSStatus.SERVER_ERROR) {
+ CVSServerException e = new CVSServerException(status);
+ if (e.isNoTagException() && child.isContainer()) {
+ retry[0] = true;
+ } else {
+ if (e.containsErrors()) {
+ throw e;
+ }
+ }
}
}
- // we now know that this is an exception caused by a cvs bug.
- // if the folder has no files in it (just subfolders) cvs does not respond with the subfolders...
- // workaround: retry the request with no tag to get the directory names (if any)
+ }, Policy.subMonitorFor(progress, 80));
+
+ // We now know that this is an exception caused by a cvs bug.
+ // If the folder has no files in it (just subfolders) CVS does not respond with the subfolders...
+ // Workaround: Retry the request with no tag to get the directory names (if any)
+ if (retry[0]) {
Policy.checkCanceled(progress);
- if (e.isNoTagException()) {
- return exists(child, null, progress);
- }
+ return exists(child, null, Policy.subMonitorFor(progress, 20));
}
return exists[0];
} finally {
@@ -248,75 +254,106 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
final List newRemoteDirectories = new ArrayList();
final List newRemoteFiles = new ArrayList();
final boolean[] exists = new boolean[] {true};
- IUpdateMessageListener listener = new IUpdateMessageListener() {
- public void directoryInformation(IPath path, boolean newDirectory) {
- if (newDirectory && path.segmentCount() == 1) {
- newRemoteDirectories.add(path.lastSegment());
- progress.subTask(path.lastSegment().toString());
- progress.worked(1);
+ final List exceptions = new ArrayList();
+ final IUpdateMessageListener listener = new IUpdateMessageListener() {
+ public void directoryInformation(ICVSFolder parent, IPath path, boolean newDirectory) {
+ try {
+ path = getRelativePathRootRelativePath(parent, path);
+ if (newDirectory && path.segmentCount() == 1) {
+ newRemoteDirectories.add(path.lastSegment());
+ progress.subTask(path.lastSegment().toString());
+ progress.worked(1);
+ }
+ } catch (CVSException e) {
+ exceptions.add(e);
}
}
- public void directoryDoesNotExist(IPath path) {
- if (path.isEmpty()) {
- // the remote folder doesn't exist
- exists[0] = false;
+ public void directoryDoesNotExist(ICVSFolder parent, IPath path) {
+ try {
+ path = getRelativePathRootRelativePath(parent, path);
+ if (path.isEmpty()) {
+ // the remote folder doesn't exist
+ exists[0] = false;
+ }
+ } catch (CVSException e) {
+ exceptions.add(e);
}
}
- public void fileInformation(int type, String filename) {
- IPath filePath = new Path(filename);
- if( filePath.segmentCount() == 1 ) {
- String properFilename = filePath.lastSegment();
- newRemoteFiles.add(properFilename);
- progress.subTask(properFilename);
- progress.worked(1);
+ public void fileInformation(int type, ICVSFolder parent, String filename) {
+ try {
+ IPath filePath = new Path(filename);
+ filePath = getRelativePathRootRelativePath(parent, filePath);
+ if( filePath.segmentCount() == 1 ) {
+ String properFilename = filePath.lastSegment();
+ newRemoteFiles.add(properFilename);
+ progress.subTask(properFilename);
+ progress.worked(1);
+ }
+ } catch (CVSException e) {
+ exceptions.add(e);
}
}
- public void fileDoesNotExist(String filename) {
+ public void fileDoesNotExist(ICVSFolder parent, String filename) {
}
};
// Build the local options
- List localOptions = new ArrayList();
+ final List localOptions = new ArrayList();
localOptions.add(Update.RETRIEVE_ABSENT_DIRECTORIES);
if (tag != null) localOptions.add(Update.makeTagOption(tag));
// Retrieve the children and any file revision numbers in a single connection
- Session s = new Session(getRepository(), this, false);
- s.open(Policy.subMonitorFor(progress, 10));
try {
- // Perform a "cvs -n update -d -r tagName folderName"
- IStatus status = Command.UPDATE.execute(s,
- new GlobalOption[] { Command.DO_NOT_CHANGE },
- (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]),
- new String[] { Session.CURRENT_LOCAL_FOLDER },
- new UpdateListener(listener),
- Policy.subMonitorFor(progress, 60));
- if (status.getCode() == CVSStatus.SERVER_ERROR) {
- throw new CVSServerException(status);
- }
- if (progress.isCanceled()) {
- throw new OperationCanceledException();
- }
- if (! exists[0]) {
- throw new CVSException(new CVSStatus(CVSStatus.ERROR, CVSStatus.DOES_NOT_EXIST, Policy.bind("RemoteFolder.doesNotExist", getRepositoryRelativePath()))); //$NON-NLS-1$
- }
-
- // Convert the file and folder names to IManagedResources
- List result = new ArrayList();
- for (int i=0;i<newRemoteFiles.size();i++) {
- result.add(new RemoteFile(this, Update.STATE_NONE, (String)newRemoteFiles.get(i), tag));
- }
- for (int i=0;i<newRemoteDirectories.size();i++)
- result.add(new RemoteFolder(this, getRepository(), new Path(getRepositoryRelativePath()).append((String)newRemoteDirectories.get(i)), tag));
- children = (ICVSRemoteResource[])result.toArray(new ICVSRemoteResource[0]);
-
- // Get the revision numbers for the files
- if (newRemoteFiles.size() > 0) {
- updateFileRevisions(s, (String[])newRemoteFiles.toArray(new String[newRemoteFiles.size()]),
- Policy.subMonitorFor(progress, 30));
- } else {
- progress.worked(30);
- }
+ Session.run(getRepository(), this, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ // Perform a "cvs -n update -d -r tagName folderName"
+ monitor.beginTask(null, 100); //$NON-NLS-1$
+ IStatus status = Command.UPDATE.execute(
+ new GlobalOption[] { Command.DO_NOT_CHANGE },
+ (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]),
+ new ICVSResource[] { RemoteFolder.this },
+ new UpdateListener(listener),
+ Policy.subMonitorFor(monitor, 60));
+ if (status.getCode() == CVSStatus.SERVER_ERROR) {
+ throw new CVSServerException(status);
+ }
+ if (! exists[0]) {
+ throw new CVSException(new CVSStatus(CVSStatus.ERROR, CVSStatus.DOES_NOT_EXIST, Policy.bind("RemoteFolder.doesNotExist", getRepositoryRelativePath()))); //$NON-NLS-1$
+ }
+ // Report any exceptions that occured fetching the members
+ if ( ! exceptions.isEmpty()) {
+ if (exceptions.size() == 1) {
+ throw (CVSException)exceptions.get(0);
+ } else {
+ MultiStatus multi = new MultiStatus(CVSProviderPlugin.ID, 0, Policy.bind("RemoteFolder.errorFetchingMembers"), null); //$NON-NLS-1$
+ for (int i = 0; i < exceptions.size(); i++) {
+ multi.merge(((CVSException)exceptions.get(i)).getStatus());
+ }
+ throw new CVSException(multi);
+ }
+ }
+ // Convert the file names to remote resources
+ Policy.checkCanceled(monitor);
+ List result = new ArrayList();
+ List remoteFiles = new ArrayList();
+ for (int i=0;i<newRemoteFiles.size();i++) {
+ RemoteFile newFile = new RemoteFile(RemoteFolder.this, Update.STATE_NONE, (String)newRemoteFiles.get(i), tag);
+ result.add(newFile);
+ remoteFiles.add(newFile);
+ }
+ // Convert the folder names to remote resources
+ for (int i=0;i<newRemoteDirectories.size();i++)
+ result.add(new RemoteFolder(RemoteFolder.this, getRepository(), new Path(getRepositoryRelativePath()).append((String)newRemoteDirectories.get(i)), tag));
+ children = (ICVSRemoteResource[])result.toArray(new ICVSRemoteResource[0]);
+ // Get the revision numbers for the files
+ if (remoteFiles.size() > 0) {
+ updateFileRevisions((ICVSFile[])remoteFiles.toArray(new ICVSFile[remoteFiles.size()]),
+ Policy.subMonitorFor(monitor, 40));
+ } else {
+ monitor.worked(40);
+ }
+ }
+ }, Policy.subMonitorFor(progress, 80));
} catch (CVSServerException e) {
if ( ! e.isNoTagException() && e.containsErrors())
throw e;
@@ -326,7 +363,7 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
// if the folder has no files in it (just subfolders) cvs does not respond with the subfolders...
// workaround: retry the request with no tag to get the directory names (if any)
Policy.checkCanceled(progress);
- children = getMembers(null, progress);
+ children = getMembers(null, Policy.subMonitorFor(progress, 20));
// the returned children must be given the original tag
for (int i = 0; i < children.length; i++) {
ICVSRemoteResource remoteResource = children[i];
@@ -334,10 +371,8 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
((RemoteFolder)remoteResource).setTag(tag);
}
}
- } finally {
- s.close();
}
-
+
// We need to remember the children that were fetched in order to support file
// operations that depend on the parent knowing about the child (i.e. RemoteFile#getContents)
return children;
@@ -403,10 +438,6 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
return Command.NO_LOCAL_OPTIONS;
}
- protected String getLocalPath() {
- throw new UnsupportedOperationException();
- }
-
public String getRepositoryRelativePath() {
// The REPOSITORY property of the folder info is the repository relative path
return getFolderSyncInfo().getRepository();
@@ -416,18 +447,19 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
* @see ICVSResource#getRelativePath(ICVSFolder)
*/
public String getRelativePath(ICVSFolder ancestor) throws CVSException {
-
- if (ancestor == this)
- return Session.CURRENT_LOCAL_FOLDER;
-
- RemoteResource rootFolder;
- try {
- rootFolder = (RemoteResource)ancestor;
- } catch (ClassCastException e) {
- throw new CVSException(Policy.bind("RemoteResource.invalidResourceClass"),e); //$NON-NLS-1$
+ // Check to see if the receiver is the ancestor
+ if (ancestor == this) return Session.CURRENT_LOCAL_FOLDER;
+ // Otherwise, we need a parent to continue
+ if (parent == null) {
+ throw new CVSException(Policy.bind("RemoteFolder.invalidChild", getName(), ancestor.getName())); //$NON-NLS-1$
+ }
+ // Append the receivers name to the parents path relative to the ancestor
+ String parentPath = parent.getRelativePath(ancestor);
+ if (parentPath.equals(Session.CURRENT_LOCAL_FOLDER) || parentPath.length() == 0) {
+ return getName();
+ } else {
+ return Util.appendPath(parentPath, getName());
}
-
- return Util.getRelativePath(rootFolder.getLocalPath(), getLocalPath());
}
public ICVSRepositoryLocation getRepository() {
@@ -473,7 +505,7 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
* does not exist, an exception is thrown.
*/
public ICVSResource getChild(String path) throws CVSException {
- if (path.equals(Session.CURRENT_LOCAL_FOLDER))
+ if (path.equals(Session.CURRENT_LOCAL_FOLDER) || path.length() == 0)
return this;
ICVSRemoteResource[] children = getChildren();
if (children == null)
@@ -596,59 +628,57 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
* Update the file revision for the given child such that the revision is the one in the given branch.
* Return true if the file exists and false otherwise
*/
- protected boolean updateRevision(ICVSRemoteFile child, CVSTag tag, IProgressMonitor monitor) throws CVSException {
-
+ protected boolean updateRevision(final ICVSRemoteFile child, CVSTag tag, IProgressMonitor monitor) throws CVSException {
+ final IProgressMonitor progress = Policy.monitorFor(monitor);
+ progress.beginTask(null, 100); //$NON-NLS-1$
ICVSRemoteResource[] oldChildren = children;
try {
children = new ICVSRemoteResource[] {child};
// Create the listener for remote files and folders
final boolean[] exists = new boolean[] {true};
- IUpdateMessageListener listener = new IUpdateMessageListener() {
- public void directoryInformation(IPath path, boolean newDirectory) {
+ final IUpdateMessageListener listener = new IUpdateMessageListener() {
+ public void directoryInformation(ICVSFolder parent, IPath path, boolean newDirectory) {
}
- public void directoryDoesNotExist(IPath path) {
+ public void directoryDoesNotExist(ICVSFolder parent, IPath path) {
// If we get this, we can assume that the parent directory no longer exists
exists[0] = false;
}
- public void fileInformation(int type, String filename) {
+ public void fileInformation(int type, ICVSFolder parent, String filename) {
// The file was found and has a different revision
try {
- ((RemoteFile)getChild(filename)).setWorkspaceSyncState(type);
+ ((RemoteFile)parent.getChild(filename)).setWorkspaceSyncState(type);
} catch(CVSException e) {
exists[0] = false;
}
exists[0] = true;
}
- public void fileDoesNotExist(String filename) {
+ public void fileDoesNotExist(ICVSFolder parent, String filename) {
exists[0] = false;
}
};
// Build the local options
- List localOptions = new ArrayList();
+ final List localOptions = new ArrayList();
if (tag != null && tag.getType() != CVSTag.HEAD)
localOptions.add(Update.makeTagOption(tag));
// Retrieve the children and any file revision numbers in a single connection
- Session s = new Session(getRepository(), this, false);
- s.open(monitor);
- try {
- // Perform a "cvs -n update -d -r tagName fileName" with custom message and error handlers
- Command.UPDATE.execute(s,
- new GlobalOption[] { Command.DO_NOT_CHANGE },
- (LocalOption[]) localOptions.toArray(new LocalOption[localOptions.size()]),
- new String[] { child.getName() },
- new UpdateListener(listener),
- monitor);
-
- if (!exists[0]) return false;
- updateFileRevisions(s, new String[] {child.getName()}, monitor);
- return true;
-
- } finally {
- s.close();
- }
+ Session.run(getRepository(), this, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ // Perform a "cvs -n update -d -r tagName fileName" with custom message and error handlers
+ Command.UPDATE.execute(
+ new GlobalOption[] { Command.DO_NOT_CHANGE },
+ (LocalOption[]) localOptions.toArray(new LocalOption[localOptions.size()]),
+ new ICVSResource[] { child },
+ new UpdateListener(listener),
+ monitor);
+ }
+ }, Policy.subMonitorFor(progress, 70));
+
+ if (!exists[0]) return false;
+ updateFileRevisions(new ICVSFile[] {child}, Policy.subMonitorFor(progress, 30));
+ return true;
} finally {
children = oldChildren;
}
@@ -693,4 +723,24 @@ public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, IC
throw new CVSException(e.getStatus());
}
}
+
+ public boolean equals(Object target) {
+ if ( ! super.equals(target)) return false;
+ RemoteFolder folder = (RemoteFolder)target;
+ CVSTag tag1 = getTag();
+ CVSTag tag2 = folder.getTag();
+ if (tag1 == null) tag1 = CVSTag.DEFAULT;
+ if (tag2 == null) tag2 = CVSTag.DEFAULT;
+ return tag1.equals(tag2);
+ }
+
+ protected IPath getRelativePathRootRelativePath(ICVSFolder root, IPath path) throws CVSException {
+ if (root == this) {
+ return path;
+ }
+ if (path.isEmpty()) {
+ throw new CVSException(Policy.bind("RemoteFolder.invalidPath"));
+ }
+ return getRelativePathRootRelativePath((ICVSFolder)root.getChild(path.segment(0)), path.removeFirstSegments(1));
+ }
} \ No newline at end of file
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTree.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTree.java
index a4219f30a..e784c3e3e 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTree.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTree.java
@@ -57,11 +57,5 @@ public class RemoteFolderTree extends RemoteFolder {
((ICVSResource)children[i]).accept(visitor);
}
}
-
- protected String getLocalPath() {
- if (parent == null)
- return ""; //$NON-NLS-1$
- return Util.appendPath(parent.getLocalPath(), getName());
- }
}
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteResource.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteResource.java
index 90e81acd0..430e3b10b 100644
--- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteResource.java
+++ b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteResource.java
@@ -41,9 +41,6 @@ public abstract class RemoteResource extends PlatformObject implements ICVSRemot
return info.getName();
}
- protected String getLocalPath() {
- return Util.appendPath(parent.getLocalPath(), getName());
- }
/*
* @see ICVSRemoteResource#getParent()
*/
@@ -93,8 +90,8 @@ public abstract class RemoteResource extends PlatformObject implements ICVSRemot
* @see ICVSResource#getParent()
*/
public ICVSFolder getParent() {
- throw new UnsupportedOperationException(Policy.bind("RemoteResource.invalidOperation")); //$NON-NLS-1$
- }
+ return parent;
+ }
/*
* @see ICVSResource#isIgnored()
@@ -107,7 +104,7 @@ public abstract class RemoteResource extends PlatformObject implements ICVSRemot
* @see ICVSResource#isManaged()
*/
public boolean isManaged() {
- return true;
+ return parent != null;
}
/*
diff --git a/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/CVSCompareEditorInput.java b/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/CVSCompareEditorInput.java
index ed7b11c69..3bd5a6c85 100644
--- a/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/CVSCompareEditorInput.java
+++ b/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/CVSCompareEditorInput.java
@@ -35,12 +35,13 @@ import org.eclipse.swt.widgets.Composite;
import org.eclipse.team.core.TeamException;
import org.eclipse.team.internal.ccvs.core.CVSException;
import org.eclipse.team.internal.ccvs.core.CVSTag;
-import org.eclipse.team.internal.ccvs.core.CVSTeamProvider;
import org.eclipse.team.internal.ccvs.core.ICVSFile;
import org.eclipse.team.internal.ccvs.core.ICVSRemoteFile;
import org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder;
import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource;
import org.eclipse.team.internal.ccvs.core.ICVSResource;
+import org.eclipse.team.internal.ccvs.core.ICVSRunnable;
+import org.eclipse.team.internal.ccvs.core.client.Session;
import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot;
import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo;
@@ -305,7 +306,7 @@ public class CVSCompareEditorInput extends CompareEditorInput {
* Method declared on CompareEditorInput
*/
protected Object prepareInput(IProgressMonitor monitor) throws InvocationTargetException, InterruptedException {
- boolean threeWay = ancestor != null;
+ final boolean threeWay = ancestor != null;
if (right == null || left == null) {
setMessage(Policy.bind("CVSCompareEditorInput.different")); //$NON-NLS-1$
return null;
@@ -313,7 +314,7 @@ public class CVSCompareEditorInput extends CompareEditorInput {
initLabels();
- Differencer d = new Differencer() {
+ final Differencer d = new Differencer() {
protected boolean contentsEqual(Object input1, Object input2) {
int compare = teamEqual(input1, input2);
if (compare == NODE_EQUAL) {
@@ -349,22 +350,30 @@ public class CVSCompareEditorInput extends CompareEditorInput {
}
};
- try {
- monitor.beginTask(Policy.bind("CVSCompareEditorInput.comparing"), 30); //$NON-NLS-1$
-
+ try {
// do the diff
- IProgressMonitor sub = new SubProgressMonitor(monitor, 30);
- try {
- sub.beginTask(Policy.bind("CVSCompareEditorInput.comparing"), 100); //$NON-NLS-1$
- return d.findDifferences(threeWay, sub, null, ancestor, left, right);
- } finally {
- sub.done();
- }
+ final Object[] result = new Object[] { null };
+ Session.run(null, null, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ monitor.beginTask(Policy.bind("CVSCompareEditorInput.comparing"), 30); //$NON-NLS-1$
+ IProgressMonitor sub = new SubProgressMonitor(monitor, 30);
+ sub.beginTask(Policy.bind("CVSCompareEditorInput.comparing"), 100); //$NON-NLS-1$
+ try {
+ result[0] = d.findDifferences(threeWay, sub, null, ancestor, left, right);
+ } finally {
+ sub.done();
+ }
+ }
+ }, monitor);
+ return result[0];
} catch (OperationCanceledException e) {
throw new InterruptedException(e.getMessage());
} catch (RuntimeException e) {
handle(e);
- return null;
+ return null;
+ } catch (CVSException e) {
+ handle(e);
+ return null;
} finally {
monitor.done();
}
diff --git a/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/merge/MergeEditorInput.java b/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/merge/MergeEditorInput.java
index b44bea365..5481d6870 100644
--- a/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/merge/MergeEditorInput.java
+++ b/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/merge/MergeEditorInput.java
@@ -5,16 +5,24 @@ package org.eclipse.team.internal.ccvs.ui.merge;
* All Rights Reserved.
*/
+import java.lang.reflect.InvocationTargetException;
+
import org.eclipse.compare.structuremergeviewer.ICompareInput;
+import org.eclipse.compare.structuremergeviewer.IDiffContainer;
+import org.eclipse.compare.structuremergeviewer.IDiffElement;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.runtime.IProgressMonitor;
-import org.eclipse.core.runtime.SubProgressMonitor;
import org.eclipse.jface.viewers.Viewer;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.team.core.TeamException;
import org.eclipse.team.core.sync.IRemoteResource;
import org.eclipse.team.core.sync.IRemoteSyncElement;
+import org.eclipse.team.internal.ccvs.core.CVSException;
import org.eclipse.team.internal.ccvs.core.CVSTag;
+import org.eclipse.team.internal.ccvs.core.ICVSFolder;
+import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource;
+import org.eclipse.team.internal.ccvs.core.ICVSRunnable;
+import org.eclipse.team.internal.ccvs.core.client.Session;
import org.eclipse.team.internal.ccvs.core.resources.CVSRemoteSyncElement;
import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot;
import org.eclipse.team.internal.ccvs.ui.Policy;
@@ -75,4 +83,38 @@ public class MergeEditorInput extends CVSSyncCompareInput {
// for merge purposes as equal.
return IRemoteSyncElement.GRANULARITY_CONTENTS;
}
+
+ /**
+ * Wrap the input preparation in a CVS session run so open sessions will be reused
+ */
+ public Object prepareInput(IProgressMonitor pm) throws InterruptedException, InvocationTargetException {
+ final Object[] result = new Object[] { null };
+ final Exception[] exception = new Exception[] {null};
+ try {
+ Session.run(null, null, false, new ICVSRunnable() {
+ public void run(IProgressMonitor monitor) throws CVSException {
+ try {
+ result[0] = MergeEditorInput.super.prepareInput(monitor);
+ } catch (InterruptedException e) {
+ exception[0] = e;
+ } catch (InvocationTargetException e) {
+ exception[0] = e;
+ }
+ }
+ }, pm);
+ } catch (CVSException e) {
+ throw new InvocationTargetException(e);
+ }
+
+ if (exception[0] != null) {
+ if (exception[0] instanceof InvocationTargetException) {
+ throw (InvocationTargetException)exception[0];
+ } else {
+ throw (InterruptedException)exception[0];
+ }
+ }
+
+ return result[0];
+ }
+
} \ No newline at end of file

Back to the top