diff options
Diffstat (limited to 'bundles/org.eclipse.team.cvs.core/src')
159 files changed, 0 insertions, 29185 deletions
diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSAnnotateBlock.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSAnnotateBlock.java deleted file mode 100644 index 01477b68f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSAnnotateBlock.java +++ /dev/null @@ -1,125 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -/** - * Model for a CVS Annotate block. - */ -public class CVSAnnotateBlock { - - String revision = ""; - String user = ""; - int startLine = 0; - int endLine = 0; - int sourceOffset = 0; - boolean valid = false; - - /** - * @return - */ - public boolean isValid() { - return valid; - } - - /** - * @return index of line where source starts. - */ - public int getSourceOffset() { - return sourceOffset; - } - - /** - * @return int the last source line of the receiver - */ - public int getEndLine() { - return endLine; - } - - /** - * @param line - */ - public void setEndLine(int line) { - endLine = line; - } - - /** - * @return the revision the receiver occured in. - */ - public String getRevision() { - return revision; - } - - /** - * @return the first source line number of the receiver - */ - public int getStartLine() { - return startLine; - } - - - /** - * Parase a CVS Annotate output line and instantiate the receiver - * @param line a CVS Annotate output line - */ - public CVSAnnotateBlock(String line, int lineNumber) { - super(); - - startLine = lineNumber; - endLine = lineNumber; - - int index = line.indexOf(' '); - if (index == -1) { - return; - } - revision = line.substring(0, index); - - index = line.indexOf("(", index); - if (index == -1) { - return; - } - - int index2 = line.indexOf(' ', index); - if (index2 == -1) { - return; - } - - user = line.substring(index + 1, index2); - - index = line.indexOf(":", index2); - if (index == -1) { - return; - } - - sourceOffset = index + 2; - valid = true; - } - - /** - * Used by the default LabelProvider to display objects in a List View - */ - public String toString() { - int delta = endLine - startLine + 1; - String line = "lines"; - if (delta == 1) { - line = "line"; - } - return user + " " + revision + " (" + String.valueOf(delta) + " " + line + ")"; - } - - /** - * Answer true if the receiver contains the given line number, false otherwse. - * @param i a line number - * @return true if receiver contains a line number. - */ - public boolean contains(int i) { - return (i >= startLine && i <= endLine); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSException.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSException.java deleted file mode 100644 index 3aaf0a21f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSException.java +++ /dev/null @@ -1,100 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import java.io.IOException; -import java.lang.reflect.InvocationTargetException; - -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Status; -import org.eclipse.team.core.TeamException; - -/** - * A checked expection representing a failure in the CVS plugin. - * <p> - * CVS exceptions contain a status object describing the cause of - * the exception. - * </p> - * - * @see IStatus - */ -public class CVSException extends TeamException { - - public CVSException(CoreException e) { - super(e); - } - - public CVSException(int severity, int code, String message, Throwable e) { - super(new CVSStatus(severity, code, message, e)); - } - - public CVSException(int severity, int code, String message) { - this(severity, code, message, null); - } - - public CVSException(String message) { - super(new CVSStatus(IStatus.ERROR, UNABLE, message, null)); - } - - public CVSException(String message, Throwable e) { - this(IStatus.ERROR, UNABLE, message, e); - } - - public CVSException(IStatus status) { - super(status); - } - - /* - * Static helper methods for creating exceptions - */ - public static CVSException wrapException(IResource resource, String message, IOException e) { - // NOTE: we should record the resource somehow - // We should also inlcude the IO message - return new CVSException(new CVSStatus(IStatus.ERROR, IO_FAILED, message, e)); - } - - /* - * Static helper methods for creating exceptions - */ - public static CVSException wrapException(IResource resource, String message, CoreException e) { - return new CVSException(new CVSStatus(IStatus.ERROR, e.getStatus().getCode(), message, e)); - } - - /* - * Static helper methods for creating exceptions - */ - public static CVSException wrapException(Exception e) { - Throwable t = e; - if (e instanceof InvocationTargetException) { - Throwable target = ((InvocationTargetException) e).getTargetException(); - if (target instanceof CVSException) { - return (CVSException) target; - } - t = target; - } - return new CVSException(new CVSStatus(IStatus.ERROR, UNABLE, t.getMessage() != null ? t.getMessage() : "", t)); //$NON-NLS-1$ - } - - public static CVSException wrapException(CoreException e) { - if (e instanceof CVSException) { - return (CVSException)e; - } - return new CVSException(e); - } - - public CoreException toCoreException() { - IStatus status = getStatus(); - return new CoreException(new Status(status.getSeverity(), status.getPlugin(), 0, status.getMessage(), this)); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSMergeSubscriber.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSMergeSubscriber.java deleted file mode 100644 index 9e651c008..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSMergeSubscriber.java +++ /dev/null @@ -1,326 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Iterator; -import java.util.List; - -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceChangeEvent; -import org.eclipse.core.resources.IResourceChangeListener; -import org.eclipse.core.resources.IResourceDelta; -import org.eclipse.core.resources.IResourceDeltaVisitor; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.ContentComparisonCriteria; -import org.eclipse.team.core.subscribers.ITeamResourceChangeListener; -import org.eclipse.team.core.subscribers.SyncInfo; -import org.eclipse.team.core.subscribers.TeamDelta; -import org.eclipse.team.core.subscribers.TeamProvider; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.syncinfo.RemoteSynchronizer; -import org.eclipse.team.internal.ccvs.core.syncinfo.RemoteTagSynchronizer; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer; -import org.eclipse.team.internal.core.SaveContext; - -/** - * A CVSMergeSubscriber is responsible for maintaining the remote trees for a merge into - * the workspace. The remote trees represent the CVS revisions of the start and end - * points (version or branch) of the merge. - * - * This subscriber stores the remote handles in the resource tree sync info slot. When - * the merge is cancelled this sync info is cleared. - * - * A merge can persist between workbench sessions and thus can be used as an - * ongoing merge. - * - * TODO: Is the merge subscriber interested in workspace sync info changes? - * TODO: Do certain operations (e.g. replace with) invalidate a merge subscriber? - * TODO: How to ensure that sync info is flushed when merge roots are deleted? - */ -public class CVSMergeSubscriber extends CVSSyncTreeSubscriber implements IResourceChangeListener, ITeamResourceChangeListener { - - public static final String UNIQUE_ID_PREFIX = "merge-"; - - private CVSTag start, end; - private List roots; - private RemoteTagSynchronizer remoteSynchronizer; - private RemoteSynchronizer mergedSynchronizer; - private RemoteTagSynchronizer baseSynchronizer; - - private static final byte[] NO_REMOTE = new byte[0]; - - - protected IResource[] refreshRemote(IResource[] resources, int depth, IProgressMonitor monitor) throws TeamException { - IResource[] remoteChanges = super.refreshRemote(resources, depth, monitor); - adjustMergedResources(remoteChanges); - return remoteChanges; - } - - private void adjustMergedResources(IResource[] remoteChanges) throws CVSException { - for (int i = 0; i < remoteChanges.length; i++) { - IResource resource = remoteChanges[i]; - mergedSynchronizer.removeSyncBytes(resource, IResource.DEPTH_ZERO, false /* not silent */); - } - } - - private static QualifiedName getUniqueId() { - String uniqueId = Long.toString(System.currentTimeMillis()); - return new QualifiedName(CVSSubscriberFactory.ID, UNIQUE_ID_PREFIX + uniqueId); - } - - public CVSMergeSubscriber(IResource[] roots, CVSTag start, CVSTag end) { - this(getUniqueId(), roots, start, end); - } - - public CVSMergeSubscriber(QualifiedName id, IResource[] roots, CVSTag start, CVSTag end) { - super(id, "CVS Merge: " + start.getName() + " to " + end.getName(), "CVS Merge"); - this.start = start; - this.end = end; - this.roots = new ArrayList(Arrays.asList(roots)); - initialize(); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSWorkspaceSubscriber#initialize() - */ - private void initialize() { - QualifiedName id = getId(); - String syncKeyPrefix = id.getLocalName(); - remoteSynchronizer = new RemoteTagSynchronizer(syncKeyPrefix + end.getName(), end); - baseSynchronizer = new RemoteTagSynchronizer(syncKeyPrefix + start.getName(), start); - mergedSynchronizer = new RemoteSynchronizer(syncKeyPrefix + "0merged"); //$NON-NLS-1$ - - try { - setCurrentComparisonCriteria(ContentComparisonCriteria.ID_IGNORE_WS); - } catch (TeamException e) { - // use the default but log an exception because the content comparison should - // always be available. - CVSProviderPlugin.log(e); - } - - ResourcesPlugin.getWorkspace().addResourceChangeListener(this); - CVSProviderPlugin.getPlugin().getCVSWorkspaceSubscriber().addListener(this); - } - - protected SyncInfo getSyncInfo(IResource local, IRemoteResource base, IRemoteResource remote, IProgressMonitor monitor) throws TeamException { - return new CVSMergeSyncInfo(local, base, remote, this, monitor); - } - - public void merged(IResource[] resources) throws CVSException { - for (int i = 0; i < resources.length; i++) { - IResource resource = resources[i]; - byte[] remoteBytes = remoteSynchronizer.getSyncBytes(resource); - if (remoteBytes == null) { - // If there is no remote, use a place holder to indicate the resouce was merged - remoteBytes = NO_REMOTE; - } - mergedSynchronizer.setSyncBytes(resource, remoteBytes); - } - fireTeamResourceChange(TeamDelta.asSyncChangedDeltas(this, resources)); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#cancel() - */ - public void cancel() { - super.cancel(); - ResourcesPlugin.getWorkspace().removeResourceChangeListener(this); - TeamProvider.deregisterSubscriber(this); - remoteSynchronizer.dispose(); - baseSynchronizer.dispose(); - mergedSynchronizer.dispose(); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#isCancellable() - */ - public boolean isCancellable() { - return true; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#roots() - */ - public IResource[] roots() { - return (IResource[]) roots.toArray(new IResource[roots.size()]); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getRemoteSynchronizer() - */ - protected ResourceSynchronizer getRemoteSynchronizer() { - return remoteSynchronizer; - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getBaseSynchronizer() - */ - protected ResourceSynchronizer getBaseSynchronizer() { - return baseSynchronizer; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#isSupervised(org.eclipse.core.resources.IResource) - */ - public boolean isSupervised(IResource resource) throws TeamException { - return getBaseSynchronizer().getSyncBytes(resource) != null || getRemoteSynchronizer().getSyncBytes(resource) != null; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.subscribers.TeamSubscriber#saveState(org.eclipse.team.internal.core.SaveContext) - */ - public SaveContext saveState() { - // start and end tags - SaveContext state = new SaveContext(); - state.setName("merge"); - state.putString("startTag", start.getName()); - state.putInteger("startTagType", start.getType()); - state.putString("endTag", end.getName()); - state.putInteger("endTagType", end.getType()); - - // resources roots - SaveContext[] ctxRoots = new SaveContext[roots.size()]; - int i = 0; - for (Iterator it = roots.iterator(); it.hasNext(); i++) { - IResource element = (IResource) it.next(); - ctxRoots[i] = new SaveContext(); - ctxRoots[i].setName("resource"); - ctxRoots[i].putString("fullpath", element.getFullPath().toString()); - } - state.setChildren(ctxRoots); - return state; - } - - public static CVSMergeSubscriber restore(QualifiedName id, SaveContext saveContext) throws CVSException { - String name = saveContext.getName(); - if(! name.equals("merge")) { - throw new CVSException("error restoring merge subscriber: " + name + " is an invalid save context."); - } - - CVSTag start = new CVSTag(saveContext.getString("startTag"), saveContext.getInteger("startTagType")); - CVSTag end = new CVSTag(saveContext.getString("endTag"), saveContext.getInteger("endTagType")); - - SaveContext[] ctxRoots = saveContext.getChildren(); - if(ctxRoots == null || ctxRoots.length == 0) { - throw new CVSException("error restoring merge subscriber: there are no roots in the save context."); - } - - List resources = new ArrayList(); - for (int i = 0; i < ctxRoots.length; i++) { - SaveContext context = ctxRoots[i]; - IPath path = new Path(context.getString("fullpath")); - IResource resource = ResourcesPlugin.getWorkspace().getRoot().findMember(path, true /* include phantoms */); - if(resource != null) { - resources.add(resource); - } else { - // log that a resource previously in the merge set is no longer in the workspace - CVSProviderPlugin.log(CVSStatus.INFO, "ignoring root resource not found in current workspace", null); - } - } - if(resources.isEmpty()) { - throw new CVSException("error restoring merge subscriber: there are no existing roots in the save context."); - } - IResource[] roots = (IResource[]) resources.toArray(new IResource[resources.size()]); - return new CVSMergeSubscriber(id, roots, start, end); - } - - public CVSTag getStartTag() { - return start; - } - - public CVSTag getEndTag() { - return end; - } - - public boolean isReleaseSupported() { - // you can't release changes to a merge - return false; - } - - /* - * What to do when a root resource for this merge changes? - * Deleted, Move, Copied - * Changed in a CVS way (tag changed, revision changed...) - * Contents changed by user - * @see IResourceChangeListener#resourceChanged(org.eclipse.core.resources.IResourceChangeEvent) - */ - public void resourceChanged(IResourceChangeEvent event) { - try { - IResourceDelta delta = event.getDelta(); - if(delta != null) { - delta.accept(new IResourceDeltaVisitor() { - public boolean visit(IResourceDelta delta) throws CoreException { - IResource resource = delta.getResource(); - - if (resource.getType()==IResource.PROJECT) { - IProject project = (IProject)resource; - if (!project.isAccessible()) { - return false; - } - if ((delta.getFlags() & IResourceDelta.OPEN) != 0) { - return false; - } - if (RepositoryProvider.getProvider(project, CVSProviderPlugin.getTypeId()) == null) { - return false; - } - } - - if (roots.contains(resource)) { - if (delta.getKind() == IResourceDelta.REMOVED || delta.getKind() == IResourceDelta.MOVED_TO) { - cancel(); - } - // stop visiting children - return false; - } - // keep visiting children - return true; - } - }); - } - } catch (CoreException e) { - CVSProviderPlugin.log(e.getStatus()); - } - } - - public boolean isMerged(IResource resource) throws CVSException { - return mergedSynchronizer.getSyncBytes(resource) != null; - } - - /* - * Currently only the workspace subscriber knows when a project has been deconfigured. We will listen for these events - * and remove the root then forward to merge subscriber listeners. - * (non-Javadoc) - * @see org.eclipse.team.core.subscribers.ITeamResourceChangeListener#teamResourceChanged(org.eclipse.team.core.subscribers.TeamDelta[]) - */ - public void teamResourceChanged(TeamDelta[] deltas) { - for (int i = 0; i < deltas.length; i++) { - TeamDelta delta = deltas[i]; - switch(delta.getFlags()) { - case TeamDelta.PROVIDER_DECONFIGURED: - IResource resource = delta.getResource(); - if(roots.remove(resource)) { - fireTeamResourceChange(new TeamDelta[] {delta}); - } - break; - } - } - } -}
\ No newline at end of file diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSMergeSyncInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSMergeSyncInfo.java deleted file mode 100644 index d992055ed..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSMergeSyncInfo.java +++ /dev/null @@ -1,63 +0,0 @@ -/* - * Created on Jun 18, 2003 - * - * To change the template for this generated file go to - * Window>Preferences>Java>Code Generation>Code and Comments - */ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.SyncInfo; -import org.eclipse.team.core.subscribers.TeamSubscriber; -import org.eclipse.team.core.sync.IRemoteResource; - -/** - * @author JLemieux - * - * To change the template for this generated type comment go to - * Window>Preferences>Java>Code Generation>Code and Comments - */ -public class CVSMergeSyncInfo extends CVSSyncInfo { - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSSyncInfo#handleDeletionConflicts(int) - */ - protected int handleDeletionConflicts(int kind) { - // (see bug 40053). - if(kind == (SyncInfo.CONFLICTING | SyncInfo.DELETION | SyncInfo.PSEUDO_CONFLICT)) { - return SyncInfo.IN_SYNC; - } - return kind; - } - - protected int calculateKind(IProgressMonitor progress) throws TeamException { - // Report merged resources as in-sync - if (((CVSMergeSubscriber)getSubscriber()).isMerged(getLocal())) { - return IN_SYNC; - } - - int kind = super.calculateKind(progress); - - // Report outgoing resources as in-sync - if((kind & DIRECTION_MASK) == OUTGOING) { - return IN_SYNC; - } - - return kind; - } - - public CVSMergeSyncInfo(IResource local, IRemoteResource base, IRemoteResource remote, TeamSubscriber subscriber, IProgressMonitor monitor) throws TeamException { - super(local, base, remote, subscriber, monitor); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSSyncInfo#makeOutgoing(org.eclipse.core.runtime.IProgressMonitor) - */ - public void makeOutgoing(IProgressMonitor monitor) throws TeamException { - // Make the resource outgoing by marking it as merged with the subscriber - CVSMergeSubscriber subscriber = (CVSMergeSubscriber)getSubscriber(); - subscriber.merged(new IResource[] {getLocal() }); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSProviderPlugin.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSProviderPlugin.java deleted file mode 100644 index d6f3aceb7..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSProviderPlugin.java +++ /dev/null @@ -1,868 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.io.DataInputStream; -import java.io.DataOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileOutputStream; -import java.io.IOException; -import java.util.ArrayList; -import java.util.Collection; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Properties; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceChangeEvent; -import org.eclipse.core.resources.IResourceChangeListener; -import org.eclipse.core.resources.IWorkspace; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IPluginDescriptor; -import org.eclipse.core.runtime.ISafeRunnable; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Platform; -import org.eclipse.core.runtime.Plugin; -import org.eclipse.core.runtime.Preferences; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.core.runtime.Status; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.Team; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.TeamProvider; -import org.eclipse.team.core.sync.RemoteContentsCache; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Command.KSubstOption; -import org.eclipse.team.internal.ccvs.core.client.Command.QuietOption; -import org.eclipse.team.internal.ccvs.core.client.listeners.IConsoleListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.FileModificationManager; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.AddDeleteMoveListener; -import org.eclipse.team.internal.ccvs.core.util.ProjectDescriptionManager; -import org.eclipse.team.internal.ccvs.core.util.SyncFileChangeListener; -import org.eclipse.team.internal.ccvs.core.util.Util; - -public class CVSProviderPlugin extends Plugin { - - // preference names - public static final String READ_ONLY = "cvs.read.only"; //$NON-NLS-1$ - - // external command to run for ext connection method - public static final String DEFAULT_CVS_RSH = "ssh"; //$NON-NLS-1$ - // external command parameters - public static final String DEFAULT_CVS_RSH_PARAMETERS = "{host} -l {user}"; //$NON-NLS-1$ - // remote command to run for ext connection method - public static final String DEFAULT_CVS_SERVER = "cvs"; //$NON-NLS-1$ - // determines if empty directories received from the server should be pruned. - public static final boolean DEFAULT_PRUNE = true; - // determines if the user is prompted for confirmation before moving tags during a tag operation. - public static final boolean DEFAULT_CONFIRM_MOVE_TAG = true; - // determines if new directories should be discovered during update. - public static final boolean DEFAULT_FETCH = true; - // communication timeout with the server - public static final int DEFAULT_TIMEOUT = 60; - // file transfer compression level (0 - 9) - public static final int DEFAULT_COMPRESSION_LEVEL = 0; - // default text keyword substitution mode - public static final KSubstOption DEFAULT_TEXT_KSUBST_OPTION = Command.KSUBST_TEXT_EXPAND; - - // cvs plugin extension points and ids - public static final String ID = "org.eclipse.team.cvs.core"; //$NON-NLS-1$ - - public static final QualifiedName CVS_WORKSPACE_SUBSCRIBER_ID = new QualifiedName(CVSSubscriberFactory.ID, "workspace-subscriber"); - public static final String PT_AUTHENTICATOR = "authenticator"; //$NON-NLS-1$ - public static final String PT_CONNECTIONMETHODS = "connectionmethods"; //$NON-NLS-1$ - public static final String PT_FILE_MODIFICATION_VALIDATOR = "filemodificationvalidator"; //$NON-NLS-1$ - - private QuietOption quietness; - private int compressionLevel = DEFAULT_COMPRESSION_LEVEL; - private KSubstOption defaultTextKSubstOption = DEFAULT_TEXT_KSUBST_OPTION; - private int communicationsTimeout = DEFAULT_TIMEOUT; - private boolean pruneEmptyDirectories = DEFAULT_PRUNE; - private boolean fetchAbsentDirectories = DEFAULT_FETCH; - private boolean promptOnFileDelete = true; - private boolean promptOnFolderDelete = true; - private boolean replaceUnmanaged = true; - private boolean repositoriesAreBinary = false; - private String cvsRshCommand = DEFAULT_CVS_RSH; - private String cvsRshParameters = DEFAULT_CVS_RSH_PARAMETERS; - private String cvsServer = DEFAULT_CVS_SERVER; - private IConsoleListener consoleListener; - private boolean determineVersionEnabled = true; - private boolean confirmMoveTagEnabled = true; - - private static volatile CVSProviderPlugin instance; - - // CVS specific resource delta listeners - private IResourceChangeListener preAutoBuildListener; - private AddDeleteMoveListener addDeleteMoveListener; - private FileModificationManager fileModificationManager; - - private static final String REPOSITORIES_STATE_FILE = ".cvsProviderState"; //$NON-NLS-1$ - // version numbers for the state file (a positive number indicates version 1) - private static final int REPOSITORIES_STATE_FILE_VERSION_2 = -1; - private Map repositories = new HashMap(); - private List repositoryListeners = new ArrayList(); - private static List decoratorEnablementListeners = new ArrayList(); - - private CVSWorkspaceSubscriber cvsWorkspaceSubscriber; - - /** - * The identifier for the CVS nature - * (value <code>"org.eclipse.team.cvs.core.nature"</code>). - * The presence of this nature on a project indicates that it is - * CVS-capable. - * - * @see org.eclipse.core.resources.IProject#hasNature - */ - private static final String NATURE_ID = ID + ".cvsnature"; //$NON-NLS-1$ - - public CVSWorkspaceSubscriber getCVSWorkspaceSubscriber() { - return cvsWorkspaceSubscriber; - } - - /** - * @return - */ - public boolean isConfirmMoveTagEnabled() { - return confirmMoveTagEnabled; - } - - /** - * @param confirmMoveTag - */ - public void setConfirmMoveTagEnabled(boolean confirmMoveTag) { - this.confirmMoveTagEnabled = confirmMoveTag; - } - - /** - * Constructor for CVSProviderPlugin. - * @param descriptor - */ - public CVSProviderPlugin(IPluginDescriptor descriptor) { - super(descriptor); - instance = this; - } - - /** - * Convenience method for logging CoreExceptions to the plugin log - */ - public static void log(CoreException e) { - log(e.getStatus().getSeverity(), e.getMessage(), e); - } - - /** - * Log the given exception along with the provided message and severity indicator - */ - public static void log(int severity, String message, Throwable e) { - log(new Status(severity, ID, 0, message, e)); - } - - /** - * Log the given status. Do not use this method for the IStatus from a CoreException. - * Use<code>log(CoreException)</code> instead so the stack trace is not lost. - */ - public static void log(IStatus status) { - getPlugin().getLog().log(status); - } - - /** - * Returns the singleton plug-in instance. - * - * @return the plugin instance - */ - public static CVSProviderPlugin getPlugin() { - // If the instance has not been initialized, we will wait. - // This can occur if multiple threads try to load the plugin at the same - // time (see bug 33825: http://bugs.eclipse.org/bugs/show_bug.cgi?id=33825) - while (instance == null) { - try { - Thread.sleep(50); - } catch (InterruptedException e) { - // ignore and keep trying - } - } - return instance; - } - - /** - * Answers the repository provider type id for the cvs plugin - */ - public static String getTypeId() { - return NATURE_ID; - } - - /** - * Sets the file transfer compression level. (if supported) - * Valid levels are: 0 (disabled), 1 (worst/fastest) - 9 (best/slowest) - */ - public void setCompressionLevel(int level) { - compressionLevel = level; - } - - /** - * Gets the file transfer compression level. - */ - public int getCompressionLevel() { - return compressionLevel; - } - - /** - * Sets the default keyword substitution mode for text files. - */ - public void setDefaultTextKSubstOption(KSubstOption ksubst) { - defaultTextKSubstOption = ksubst; - } - - - /** - * Gets the default keyword substitution mode for text files. - */ - public KSubstOption getDefaultTextKSubstOption() { - return defaultTextKSubstOption; - } - - /** - * Should the CVS adapter prune empty directories - */ - public boolean getPruneEmptyDirectories() { - return pruneEmptyDirectories; - } - - /** - * Set whether the CVS adapter should prune empty directories - */ - public void setPruneEmptyDirectories(boolean prune) { - pruneEmptyDirectories = prune; - } - - /** - * Get the communications timeout value in seconds - */ - public int getTimeout() { - return communicationsTimeout; - } - - /** - * Set the timeout value for communications to a value in seconds. - * The value must be greater than or equal 0. If is it 0, there is no timeout. - */ - public void setTimeout(int timeout) { - this.communicationsTimeout = Math.max(0, timeout); - } - - /** - * Set the quietness option to use with cvs commands. - * Can be "", "-q" or "-Q" - */ - public void setQuietness(QuietOption option) { - this.quietness = option; - } - - /** - * Get the quietness option for commands - */ - public QuietOption getQuietness() { - return quietness; - } - - /** - * Set the console listener for commands. - * @param consoleListener the listener - */ - public void setConsoleListener(IConsoleListener consoleListener) { - this.consoleListener = consoleListener; - } - - /** - * Get the console listener for commands. - * @return the consoleListener, or null - */ - public IConsoleListener getConsoleListener() { - return consoleListener; - } - - /** - * @see Plugin#startup() - */ - public void startup() throws CoreException { - super.startup(); - Policy.localize("org.eclipse.team.internal.ccvs.core.messages"); //$NON-NLS-1$ - - // load the state which includes the known repositories - loadState(); - - // Initialize CVS change listeners. Note tha the report type is important. - IWorkspace workspace = ResourcesPlugin.getWorkspace(); - addDeleteMoveListener = new AddDeleteMoveListener(); - fileModificationManager = new FileModificationManager(); - // Group the two PRE_AUTO_BUILD listeners together for efficiency - final IResourceChangeListener projectDescriptionListener = new ProjectDescriptionManager(); - final IResourceChangeListener metaFileSyncListener = new SyncFileChangeListener(); - preAutoBuildListener = new IResourceChangeListener() { - public void resourceChanged(IResourceChangeEvent event) { - projectDescriptionListener.resourceChanged(event); - metaFileSyncListener.resourceChanged(event); - } - }; - workspace.addResourceChangeListener(preAutoBuildListener, IResourceChangeEvent.PRE_AUTO_BUILD); - workspace.addResourceChangeListener(addDeleteMoveListener, IResourceChangeEvent.POST_AUTO_BUILD); - workspace.addResourceChangeListener(fileModificationManager, IResourceChangeEvent.POST_CHANGE); - fileModificationManager.registerSaveParticipant(); - - RemoteContentsCache.enableCaching(ID); - - cvsWorkspaceSubscriber = new CVSWorkspaceSubscriber( - CVS_WORKSPACE_SUBSCRIBER_ID, - "CVS Workspace", - "Synchronizes the CVS managed resources in your workspace with their associated remote location"); - TeamProvider.registerSubscriber(cvsWorkspaceSubscriber); - } - - /** - * @see Plugin#shutdown() - */ - public void shutdown() throws CoreException { - super.shutdown(); - - // save the state which includes the known repositories - saveState(); - savePluginPreferences(); - - // remove listeners - IWorkspace workspace = ResourcesPlugin.getWorkspace(); - workspace.removeResourceChangeListener(preAutoBuildListener); - workspace.removeResourceChangeListener(fileModificationManager); - workspace.removeResourceChangeListener(addDeleteMoveListener); - - // remove all of this plugin's save participants. This is easier than having - // each class that added itself as a participant to have to listen to shutdown. - workspace.removeSaveParticipant(this); - - RemoteContentsCache.disableCache(ID); - } - - /** - * @see org.eclipse.core.runtime.Plugin#initializeDefaultPluginPreferences() - */ - protected void initializeDefaultPluginPreferences(){ - Preferences store = getPluginPreferences(); - store.setDefault(READ_ONLY, false); - } - - /** - * Gets the cvsRshCommand. - * @return Returns a String - */ - public String getCvsRshCommand() { - return cvsRshCommand; - } - - /** - * Sets the cvsRshCommand. - * @param cvsRshCommand The cvsRshCommand to set - */ - public void setCvsRshCommand(String cvsRshCommand) { - this.cvsRshCommand = cvsRshCommand; - } - - /** - * Returns the cvsRshParameters. - * @return String - */ - public String getCvsRshParameters() { - return cvsRshParameters; - } - - /** - * Sets the cvsRshParameters. - * @param cvsRshParameters The cvsRshParameters to set - */ - public void setCvsRshParameters(String cvsRshParameters) { - this.cvsRshParameters = cvsRshParameters; - } - - /** - * Gets the cvsServer. - * @return Returns a String - */ - public String getCvsServer() { - return cvsServer; - } - - /** - * Sets the cvsServer. - * @param cvsServer The cvsServer to set - */ - public void setCvsServer(String cvsServer) { - this.cvsServer = cvsServer; - } - - /** - * Gets the etchAbsentDirectories. - * @return Returns a boolean - */ - public boolean getFetchAbsentDirectories() { - return fetchAbsentDirectories; - } - - public boolean getRepositoriesAreBinary() { - return repositoriesAreBinary; - } - - /** - * Sets the fetchAbsentDirectories. - * @param etchAbsentDirectories The etchAbsentDirectories to set - */ - public void setFetchAbsentDirectories(boolean fetchAbsentDirectories) { - this.fetchAbsentDirectories = fetchAbsentDirectories; - } - - public boolean getPromptOnFileDelete() { - return promptOnFileDelete; - } - - public void setPromptOnFileDelete(boolean prompt) { - promptOnFileDelete = prompt; - } - - public void setRepositoriesAreBinary(boolean binary) { - repositoriesAreBinary = binary; - } - - public boolean getPromptOnFolderDelete() { - return promptOnFolderDelete; - } - - public void setPromptOnFolderDelete(boolean prompt) { - promptOnFolderDelete = prompt; - } - - private static List listeners = new ArrayList(); - - /* - * @see ITeamManager#addResourceStateChangeListener(IResourceStateChangeListener) - */ - public static void addResourceStateChangeListener(IResourceStateChangeListener listener) { - listeners.add(listener); - } - - /* - * @see ITeamManager#removeResourceStateChangeListener(IResourceStateChangeListener) - */ - public static void removeResourceStateChangeListener(IResourceStateChangeListener listener) { - listeners.remove(listener); - } - - public static void broadcastSyncInfoChanges(final IResource[] resources) { - for(Iterator it=listeners.iterator(); it.hasNext();) { - final IResourceStateChangeListener listener = (IResourceStateChangeListener)it.next(); - ISafeRunnable code = new ISafeRunnable() { - public void run() throws Exception { - listener.resourceSyncInfoChanged(resources); - } - public void handleException(Throwable e) { - // don't log the exception....it is already being logged in Platform#run - } - }; - Platform.run(code); - } - } - - public static void broadcastDecoratorEnablementChanged(final boolean enabled) { - for(Iterator it=decoratorEnablementListeners.iterator(); it.hasNext();) { - final ICVSDecoratorEnablementListener listener = (ICVSDecoratorEnablementListener)it.next(); - ISafeRunnable code = new ISafeRunnable() { - public void run() throws Exception { - listener.decoratorEnablementChanged(enabled); - } - public void handleException(Throwable e) { - // don't log the exception....it is already being logged in Platform#run - } - }; - Platform.run(code); - } - } - - public static void broadcastModificationStateChanges(final IResource[] resources) { - for(Iterator it=listeners.iterator(); it.hasNext();) { - final IResourceStateChangeListener listener = (IResourceStateChangeListener)it.next(); - ISafeRunnable code = new ISafeRunnable() { - public void run() throws Exception { - listener.resourceModified(resources); - } - public void handleException(Throwable e) { - // don't log the exception....it is already being logged in Platform#run - } - }; - Platform.run(code); - } - } - protected static void broadcastProjectConfigured(final IProject project) { - for(Iterator it=listeners.iterator(); it.hasNext();) { - final IResourceStateChangeListener listener = (IResourceStateChangeListener)it.next(); - ISafeRunnable code = new ISafeRunnable() { - public void run() throws Exception { - listener.projectConfigured(project); - } - public void handleException(Throwable e) { - // don't log the exception....it is already being logged in Platform#run - } - }; - Platform.run(code); - } - } - protected static void broadcastProjectDeconfigured(final IProject project) { - for(Iterator it=listeners.iterator(); it.hasNext();) { - final IResourceStateChangeListener listener = (IResourceStateChangeListener)it.next(); - ISafeRunnable code = new ISafeRunnable() { - public void run() throws Exception { - listener.projectDeconfigured(project); - } - public void handleException(Throwable e) { - // don't log the exception....it is already being logged in Platform#run - } - }; - Platform.run(code); - } - } - - /** - * Gets the replaceUnmanaged. - * @return Returns a boolean - */ - public boolean isReplaceUnmanaged() { - return replaceUnmanaged; - } - - /** - * Sets the replaceUnmanaged. - * @param replaceUnmanaged The replaceUnmanaged to set - */ - public void setReplaceUnmanaged(boolean replaceUnmanaged) { - this.replaceUnmanaged = replaceUnmanaged; - } - - /* - * Add the repository location to the cahced locations - */ - private void addToRepositoriesCache(ICVSRepositoryLocation repository) { - repositories.put(repository.getLocation(), repository); - Iterator it = repositoryListeners.iterator(); - while (it.hasNext()) { - ICVSListener listener = (ICVSListener)it.next(); - listener.repositoryAdded(repository); - } - } - - private void removeFromRepositoriesCache(ICVSRepositoryLocation repository) { - if (repositories.remove(repository.getLocation()) != null) { - Iterator it = repositoryListeners.iterator(); - while (it.hasNext()) { - ICVSListener listener = (ICVSListener)it.next(); - listener.repositoryRemoved(repository); - } - } - } - - /** - * Register to receive notification of repository creation and disposal - */ - public void addRepositoryListener(ICVSListener listener) { - repositoryListeners.add(listener); - } - - /** - * Register to receive notification of enablement of sync info decoration requirements. This - * can be useful for providing lazy initialization of caches that are only required for decorating - * resource with CVS information. - */ - public void addDecoratorEnablementListener(ICVSDecoratorEnablementListener listener) { - decoratorEnablementListeners.add(listener); - } - - /** - * De-register a listener - */ - public void removeRepositoryListener(ICVSListener listener) { - repositoryListeners.remove(listener); - } - - /** - * De-register the decorator enablement listener. - */ - public void removeDecoratorEnablementListener(ICVSDecoratorEnablementListener listener) { - decoratorEnablementListeners.remove(listener); - } - - /** - * Create a repository instance from the given properties. - * The supported properties are: - * - * connection The connection method to be used - * user The username for the connection - * password The password used for the connection (optional) - * host The host where the repository resides - * port The port to connect to (optional) - * root The server directory where the repository is located - * - * The created instance is not known by the provider and it's user information is not cached. - * The purpose of the created location is to allow connection validation before adding the - * location to the provider. - * - * This method will throw a CVSException if the location for the given configuration already - * exists. - */ - public ICVSRepositoryLocation createRepository(Properties configuration) throws CVSException { - // Create a new repository location - CVSRepositoryLocation location = CVSRepositoryLocation.fromProperties(configuration); - - // Check the cache for an equivalent instance and if there is one, throw an exception - CVSRepositoryLocation existingLocation = (CVSRepositoryLocation)repositories.get(location.getLocation()); - if (existingLocation != null) { - throw new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSProvider.alreadyExists"))); //$NON-NLS-1$ - } - - return location; - } - - /** - * Add the repository to the receiver's list of known repositories. Doing this will enable - * password caching accross platform invokations. - */ - public void addRepository(ICVSRepositoryLocation repository) throws CVSException { - // Check the cache for an equivalent instance and if there is one, just update the cache - CVSRepositoryLocation existingLocation = (CVSRepositoryLocation)repositories.get(repository.getLocation()); - if (existingLocation != null) { - ((CVSRepositoryLocation)repository).updateCache(); - } else { - // Cache the password and register the repository location - addToRepositoriesCache(repository); - ((CVSRepositoryLocation)repository).updateCache(); - } - saveState(); - } - - /** - * Dispose of the repository location - * - * Removes any cached information about the repository such as a remembered password. - */ - public void disposeRepository(ICVSRepositoryLocation repository) throws CVSException { - ((CVSRepositoryLocation)repository).dispose(); - removeFromRepositoriesCache(repository); - } - - /** - * Answer whether the provided repository location is known by the provider or not. - * The location string corresponds to the Strin returned by ICVSRepositoryLocation#getLocation() - */ - public boolean isKnownRepository(String location) { - return repositories.get(location) != null; - } - - /** - * Return a list of the know repository locations - */ - public ICVSRepositoryLocation[] getKnownRepositories() { - return (ICVSRepositoryLocation[])repositories.values().toArray(new ICVSRepositoryLocation[repositories.size()]); - } - - /** - * Get the repository instance which matches the given String. The format of the String is - * the same as that returned by ICVSRepositoryLocation#getLocation(). - * The format is: - * - * connection:user[:password]@host[#port]:root - * - * where [] indicates optional and the identier meanings are: - * - * connection The connection method to be used - * user The username for the connection - * password The password used for the connection (optional) - * host The host where the repository resides - * port The port to connect to (optional) - * root The server directory where the repository is located - * - * It is expected that the instance requested by using this method exists. - * If the repository location does not exist, it will be automatically created - * and cached with the provider. - * - * WARNING: Providing the password as part of the String will result in the password being part - * of the location permanently. This means that it cannot be modified by the authenticator. - */ - public ICVSRepositoryLocation getRepository(String location) throws CVSException { - ICVSRepositoryLocation repository = (ICVSRepositoryLocation)repositories.get(location); - if (repository == null) { - repository = CVSRepositoryLocation.fromString(location); - addToRepositoriesCache(repository); - } - return repository; - } - - private void loadState() { - try { - IPath pluginStateLocation = CVSProviderPlugin.getPlugin().getStateLocation().append(REPOSITORIES_STATE_FILE); - File file = pluginStateLocation.toFile(); - if (file.exists()) { - try { - DataInputStream dis = new DataInputStream(new FileInputStream(file)); - readState(dis); - dis.close(); - } catch (IOException e) { - throw new TeamException(new Status(Status.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSProvider.ioException"), e)); //$NON-NLS-1$ - } - } else { - // If the file did not exist, then prime the list of repositories with - // the providers with which the projects in the workspace are shared. - IProject[] projects = ResourcesPlugin.getWorkspace().getRoot().getProjects(); - for (int i = 0; i < projects.length; i++) { - RepositoryProvider provider = RepositoryProvider.getProvider(projects[i], CVSProviderPlugin.getTypeId()); - if (provider!=null) { - ICVSFolder folder = (ICVSFolder)CVSWorkspaceRoot.getCVSResourceFor(projects[i]); - FolderSyncInfo info = folder.getFolderSyncInfo(); - if (info != null) { - ICVSRepositoryLocation result = getRepository(info.getRoot()); - } - } - } - saveState(); - } - } catch (TeamException e) { - Util.logError(Policy.bind("CVSProvider.errorLoading"), e);//$NON-NLS-1$ - } - } - private void saveState() { - try { - IPath pluginStateLocation = CVSProviderPlugin.getPlugin().getStateLocation(); - File tempFile = pluginStateLocation.append(REPOSITORIES_STATE_FILE + ".tmp").toFile(); //$NON-NLS-1$ - File stateFile = pluginStateLocation.append(REPOSITORIES_STATE_FILE).toFile(); - try { - DataOutputStream dos = new DataOutputStream(new FileOutputStream(tempFile)); - writeState(dos); - dos.close(); - if (stateFile.exists()) { - stateFile.delete(); - } - boolean renamed = tempFile.renameTo(stateFile); - if (!renamed) { - throw new TeamException(new Status(Status.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSProvider.rename", tempFile.getAbsolutePath()), null)); //$NON-NLS-1$ - } - } catch (IOException e) { - throw new TeamException(new Status(Status.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSProvider.save",stateFile.getAbsolutePath()), e)); //$NON-NLS-1$ - } - } catch (TeamException e) { - Util.logError(Policy.bind("CVSProvider.errorSaving"), e);//$NON-NLS-1$ - } - } - - private void readState(DataInputStream dis) throws IOException, CVSException { - int count = dis.readInt(); - if (count >= 0) { - // this is the version 1 format of the state file - for (int i = 0; i < count; i++) { - getRepository(dis.readUTF()); - } - } else if (count == REPOSITORIES_STATE_FILE_VERSION_2) { - count = dis.readInt(); - for (int i = 0; i < count; i++) { - ICVSRepositoryLocation root = getRepository(dis.readUTF()); - String programName = dis.readUTF(); - if (!programName.equals(CVSRepositoryLocation.DEFAULT_REMOTE_CVS_PROGRAM_NAME)) { - ((CVSRepositoryLocation)root).setRemoteCVSProgramName(programName); - } - } - } else { - Util.logError(Policy.bind("CVSProviderPlugin.unknownStateFileVersion", new Integer(count).toString()), null); //$NON-NLS-1$ - } - } - - private void writeState(DataOutputStream dos) throws IOException { - // Write the repositories - dos.writeInt(REPOSITORIES_STATE_FILE_VERSION_2); - // Write out the repos - Collection repos = repositories.values(); - dos.writeInt(repos.size()); - Iterator it = repos.iterator(); - while (it.hasNext()) { - CVSRepositoryLocation root = (CVSRepositoryLocation)it.next(); - dos.writeUTF(root.getLocation()); - dos.writeUTF(root.getRemoteCVSProgramName()); - } - } - - public static boolean isText(IFile file) { - if (CVSProviderPlugin.getPlugin().getRepositoriesAreBinary()) return false; - return Team.getType(file) == Team.TEXT; - } - - /** - * Gets the determineVersionEnabled. - * @return boolean - */ - public boolean isDetermineVersionEnabled() { - return determineVersionEnabled; - } - - /** - * Sets the determineVersionEnabled. - * @param determineVersionEnabled The determineVersionEnabled to set - */ - public void setDetermineVersionEnabled(boolean determineVersionEnabled) { - this.determineVersionEnabled = determineVersionEnabled; - } - - /** - * Set the program name of the given repository location. - * The program name is the expected prefix on server text messages. - * Since we extract information out of these messages, we need to - * know what prefix to expect. The default is "cvs". - */ - public void setCVSProgramName(ICVSRepositoryLocation location, String programName) { - ((CVSRepositoryLocation)location).setRemoteCVSProgramName(programName); - saveState(); - } - - /** - * Method getResetTimestampOfFalseChange. - * @return boolean - */ - public boolean getResetTimestampOfFalseChange() { - return true; - } - /** - * Returns the fileModificationManager. - * @return FileModificationManager - */ - public FileModificationManager getFileModificationManager() { - return fileModificationManager; - } - - /** - * @return boolean - */ - public boolean isWatchEditEnabled() { - return getPluginPreferences().getBoolean(CVSProviderPlugin.READ_ONLY); - } - - public void setDebugProtocol(boolean value) { - Policy.DEBUG_CVS_PROTOCOL = value; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSRevisionNumberCompareCriteria.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSRevisionNumberCompareCriteria.java deleted file mode 100644 index 68bf3e2d4..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSRevisionNumberCompareCriteria.java +++ /dev/null @@ -1,99 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.subscribers.ComparisonCriteria; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * CVSRevisionNumberCompareCriteria - */ - public class CVSRevisionNumberCompareCriteria extends ComparisonCriteria { - - /* (non-Javadoc) - * @see ComparisonCriteria#getName() - */ - public String getName() { - return "Revision number comparison"; - } - - /* (non-Javadoc) - * @see ComparisonCriteria#getId() - */ - public String getId() { - return "org.eclipse.team.cvs.revisioncomparator"; - } - - /* (non-Javadoc) - * @see ComparisonCriteria#compare(Object, Object, IProgressMonitor) - */ - public boolean compare(Object e1, Object e2, IProgressMonitor monitor) { - if(e1 instanceof IResource && e2 instanceof IRemoteResource) { - return compare((IResource)e1, (IRemoteResource)e2); - } else if(e1 instanceof IRemoteResource && e2 instanceof IRemoteResource) { - return compare((IRemoteResource)e1, (IRemoteResource)e2); - } - return false; - } - - /** - * @see RemoteSyncElement#timestampEquals(IRemoteResource, IRemoteResource) - */ - protected boolean compare(IRemoteResource e1, IRemoteResource e2) { - if(e1.isContainer()) { - if(e2.isContainer()) { - return true; - } - return false; - } - return e1.equals(e2); - } - - /** - * @see RemoteSyncElement#timestampEquals(IResource, IRemoteResource) - */ - protected boolean compare(IResource e1, IRemoteResource e2) { - if(e1.getType() != IResource.FILE) { - if(e2.isContainer()) { - return true; - } - return false; - } - ICVSFile cvsFile = CVSWorkspaceRoot.getCVSFileFor((IFile)e1); - try { - byte[] syncBytes1 = cvsFile.getSyncBytes(); - byte[] syncBytes2 = ((ICVSRemoteFile)e2).getSyncBytes(); - - if(syncBytes1 != null) { - if(ResourceSyncInfo.isDeletion(syncBytes1) || ResourceSyncInfo.isMerge(syncBytes1) || cvsFile.isModified(null)) { - return false; - } - return ResourceSyncInfo.getRevision(syncBytes1).equals(ResourceSyncInfo.getRevision(syncBytes2)); - } - return false; - } catch(CVSException e) { - CVSProviderPlugin.log(e); - return false; - } - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.subscribers.ComparisonCriteria#usesFileContents() - */ - public boolean usesFileContents() { - return false; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSStatus.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSStatus.java deleted file mode 100644 index 4b5fa295d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSStatus.java +++ /dev/null @@ -1,67 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.core.runtime.Status; - -public class CVSStatus extends Status { - - /*** Status codes ***/ - public static final int SERVER_ERROR = -10; - public static final int NO_SUCH_TAG = -11; - public static final int CONFLICT = -12; - public static final int ERROR_LINE = -14; // generic uninterpreted E line from the server - public static final int TAG_ALREADY_EXISTS = -15; - public static final int COMMITTING_SYNC_INFO_FAILED = -16; - public static final int DOES_NOT_EXIST = -17; - public static final int FOLDER_NEEDED_FOR_FILE_DELETIONS = -18; - public static final int CASE_VARIANT_EXISTS = -19; - public static final int UNSUPPORTED_SERVER_VERSION = -20; - public static final int SERVER_IS_CVSNT = -21; - public static final int SERVER_IS_UNKNOWN = -22; - public static final int PROTOCOL_ERROR = -23; - public static final int ERROR_LINE_PARSE_FAILURE = -24; - - // Path for resource related status - private ICVSFolder commandRoot; - - public CVSStatus(int severity, int code, String message, Throwable t) { - super(severity, CVSProviderPlugin.ID, code, message, t); - } - - public CVSStatus(int severity, int code, String message) { - this(severity, code, message, null); - } - - public CVSStatus(int severity, int code, ICVSFolder commandRoot, String message) { - this(severity, code, message, null); - this.commandRoot = commandRoot; - } - - public CVSStatus(int severity, String message, Throwable t) { - this(severity, message); - } - - public CVSStatus(int severity, String message) { - this(severity, severity, message, null); - } - /** - * @see IStatus#getMessage() - */ - public String getMessage() { - String message = super.getMessage(); - if (commandRoot != null) { - message = Policy.bind("CVSStatus.messageWithRoot", commandRoot.getName(), message); //$NON-NLS-1$ - } - return message; - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSubscriberFactory.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSubscriberFactory.java deleted file mode 100644 index 5c71d065f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSubscriberFactory.java +++ /dev/null @@ -1,63 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.TeamSubscriber; -import org.eclipse.team.core.subscribers.TeamSubscriberFactory; -import org.eclipse.team.internal.core.SaveContext; - -/** - * CVSSubscriberFactory - */ -public class CVSSubscriberFactory extends TeamSubscriberFactory { - - final static public String ID = "org.eclipse.team.cvs.subscribers"; - - /* (non-Javadoc) - * @see org.eclipse.team.core.subscribers.ISyncTreeSubscriberFactory#getID() - */ - public String getID() { - return ID; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.subscribers.ISyncTreeSubscriberFactory#createSubscriber(org.eclipse.core.runtime.QualifiedName, org.eclipse.team.internal.core.SaveContext) - */ - public TeamSubscriber restoreSubscriber(QualifiedName id, SaveContext saveContext) throws TeamException { - if(isMergeSubscriber(id)) { - return CVSMergeSubscriber.restore(id, saveContext); - } - // CVS workspace subscribers are automatically recreated when the platform restarts. - return null; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.subscribers.ISyncTreeSubscriberFactory#saveSubscriber(org.eclipse.team.core.subscribers.TeamSubscriber) - */ - public SaveContext saveSubscriber(TeamSubscriber subscriber) throws TeamException { - if(isMergeSubscriber(subscriber.getId())) { - return ((CVSMergeSubscriber)subscriber).saveState(); - } else { - return null; - } - } - - private boolean isMergeSubscriber(QualifiedName id) { - String localName = id.getLocalName(); - if(localName.startsWith(CVSMergeSubscriber.UNIQUE_ID_PREFIX)) { - return true; - } else { - return false; - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSyncInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSyncInfo.java deleted file mode 100644 index fbbb503b3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSyncInfo.java +++ /dev/null @@ -1,327 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.SyncInfo; -import org.eclipse.team.core.subscribers.TeamSubscriber; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFolder; -import org.eclipse.team.internal.ccvs.core.resources.RemoteResource; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * CVSSyncInfo - */ -public class CVSSyncInfo extends SyncInfo { - - public CVSSyncInfo(IResource local, IRemoteResource base, IRemoteResource remote, TeamSubscriber subscriber, IProgressMonitor monitor) throws TeamException { - super(local, base, remote, subscriber, monitor); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.SyncInfo#computeSyncKind(org.eclipse.core.runtime.IProgressMonitor) - */ - protected int calculateKind(IProgressMonitor progress) throws TeamException { - // special handling for folders, the generic sync algorithm doesn't work well - // with CVS because folders are not in namespaces (e.g. they exist in all versions - // and branches). - IResource local = getLocal(); - if(local.getType() != IResource.FILE && getSubscriber().isThreeWay()) { - int folderKind = SyncInfo.IN_SYNC; - ICVSRemoteFolder remote = (ICVSRemoteFolder)getRemote(); - ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor((IContainer)local); - boolean isCVSFolder = false; - try { - isCVSFolder = cvsFolder.isCVSFolder(); - } catch (CVSException e) { - // Assume the folder is not a CVS folder - } - if(!local.exists()) { - if(remote != null) { - if (isCVSFolder) { - // TODO: This assumes all CVS folders are in-sync even if they have been pruned! - folderKind = SyncInfo.IN_SYNC; - } else { - folderKind = SyncInfo.INCOMING | SyncInfo.ADDITION; - } - } else { - // ignore conflicting deletion to keep phantom sync info - } - } else { - if(remote == null) { - if(isCVSFolder) { - // TODO: This is not really an incoming deletion - // The folder will be pruned once any children are commited - folderKind = SyncInfo.IN_SYNC; - //folderKind = SyncInfo.INCOMING | SyncInfo.DELETION; - } else { - folderKind = SyncInfo.OUTGOING | SyncInfo.ADDITION; - } - } else if(!isCVSFolder) { - folderKind = SyncInfo.CONFLICTING | SyncInfo.ADDITION; - } else { - // folder exists both locally and remotely and are considered in sync, however - // we aren't checking the folder mappings to ensure that they are the same. - } - } - return folderKind; - } - - // 1. Run the generic sync calculation algorithm, then handle CVS specific - // sync cases. - int kind = super.calculateKind(progress); - - // 2. Set the CVS specific sync type based on the workspace sync state provided - // by the CVS server. - IRemoteResource remote = getRemote(); - if(remote!=null && (kind & SyncInfo.PSEUDO_CONFLICT) == 0) { - RemoteResource cvsRemote = (RemoteResource)remote; - int type = cvsRemote.getWorkspaceSyncState(); - switch(type) { - // the server compared both text files and decided that it cannot merge - // them without line conflicts. - case Update.STATE_CONFLICT: - return kind | SyncInfo.MANUAL_CONFLICT; - - // the server compared both text files and decided that it can safely merge - // them without line conflicts. - case Update.STATE_MERGEABLE_CONFLICT: - return kind | SyncInfo.AUTOMERGE_CONFLICT; - } - } - - // 3. unmanage delete/delete conflicts and return that they are in sync - kind = handleDeletionConflicts(kind); - - return kind; - } - - /** - * Return true if the provided phantom folder conyains any outgoing file deletions. - * We only need to detect if there are any files since a phantom folder can only - * contain outgoing filre deletions and other folder. - * - * @param cvsFolder a phantom folder - * @return boolean - */ - private boolean containsOutgoingDeletions(ICVSFolder cvsFolder) { - final boolean result[] = new boolean[] { false }; - try { - cvsFolder.accept(new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - // Do nothing. Files are handled below - } - public void visitFolder(ICVSFolder folder) throws CVSException { - if (folder.members(ICVSFolder.FILE_MEMBERS).length > 0) { - result[0] = true; - } else { - folder.acceptChildren(this); - } - } - }); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - return result[0]; - } - - /* - * If the resource has a delete/delete conflict then ensure that the local is unmanaged so that the - * sync info can be properly flushed. - */ - protected int handleDeletionConflicts(int kind) { - if(kind == (SyncInfo.CONFLICTING | SyncInfo.DELETION | SyncInfo.PSEUDO_CONFLICT)) { - try { - IResource local = getLocal(); - ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(local); - if(!cvsResource.isFolder() && cvsResource.isManaged()) { - cvsResource.unmanage(null); - } - return SyncInfo.IN_SYNC; - } catch(CVSException e) { - CVSProviderPlugin.log(e); - return SyncInfo.CONFLICTING | SyncInfo.DELETION; - } - } - return kind; - } - - /* - * Update the sync info of the local resource in such a way that the local changes can be committed. - */ - public void makeOutgoing(IProgressMonitor monitor) throws TeamException { - - // TODO: What is the impact of using whatever the current granularity is? - // int syncKind = getSyncKind(GRANULARITY_TIMESTAMP , monitor); - int syncKind = getKind(); - boolean incoming = (syncKind & DIRECTION_MASK) == INCOMING; - boolean outgoing = (syncKind & DIRECTION_MASK) == OUTGOING; - - ICVSResource local = CVSWorkspaceRoot.getCVSResourceFor(getLocal()); - RemoteResource remote = (RemoteResource)getRemote(); - ResourceSyncInfo origInfo = local.getSyncInfo(); - MutableResourceSyncInfo info = null; - if(origInfo!=null) { - info = origInfo.cloneMutable(); - } - - if (outgoing) { - // The sync info is alright, it's already outgoing! - return; - } else if (incoming) { - // We have an incoming change, addition, or deletion that we want to ignore - if (local.exists()) { - // We could have an incoming change or deletion - if (remote == null) { - info.setAdded(); - } else { - // Otherwise change the revision to the remote revision and dirty the file - info.setRevision(remote.getSyncInfo().getRevision()); - info.setTimeStamp(null); - } - } else { - // We have an incoming add, turn it around as an outgoing delete - info = remote.getSyncInfo().cloneMutable(); - info.setDeleted(true); - } - } else if (local.exists()) { - // We have a conflict and a local resource! - if (getRemote() != null) { - if (getBase() != null) { - // We have a conflicting change, Update the local revision - info.setRevision(remote.getSyncInfo().getRevision()); - } else { - // We have conflictin additions. - // We need to fetch the contents of the remote to get all the relevant information (timestamp, permissions) - // TODO: Do we really need to fetch the contents here? - remote.getContents(Policy.monitorFor(monitor)); - info = remote.getSyncInfo().cloneMutable(); - } - } else if (getBase() != null) { - // We have a remote deletion. Make the local an addition - info.setAdded(); - } else { - // There's a local, no base and no remote. We can't possible have a conflict! - Assert.isTrue(false); - } - } else { - // We have a conflict and there is no local! - if (getRemote() != null) { - // We have a local deletion that conflicts with remote changes. - info.setRevision(remote.getSyncInfo().getRevision()); - info.setDeleted(true); - } else { - // We have conflicting deletions. Clear the sync info - info = null; - return; - } - } - if(info!=null) { - info.setTag(local.getParent().getFolderSyncInfo().getTag()); - } - ((ICVSFile)local).setSyncInfo(info, ICVSFile.UNKNOWN); - } - - /* - * Update the sync info of the local resource in such a way that the remote resource can be loaded - * ignore any local changes. - */ - public void makeIncoming(IProgressMonitor monitor) throws TeamException { - // To make outgoing deletions incoming, the local will not exist but - // it is still important to unmanage (e.g. delete all meta info) for the - // deletion. - CVSWorkspaceRoot.getCVSResourceFor(getLocal()).unmanage(null); - } - - /* - * Load the resource and folder sync info into the local from the remote - * - * This method can be used on incoming folder additions to set the folder sync info properly - * without hitting the server again. It also applies to conflicts that involves unmanaged - * local resources. - * - * If the local folder is already managed and is a cvs folder, this operation - * will throw an exception if the mapping does not match that of the remote. - */ - public void makeInSync() throws CVSException { - - // Only work on folders - if (getLocal().getType() == IResource.FILE) return; - - boolean outgoing = (getKind() & DIRECTION_MASK) == OUTGOING; - if (outgoing) return; - - ICVSFolder local = (ICVSFolder)CVSWorkspaceRoot.getCVSFolderFor((IContainer)getLocal()); - RemoteFolder remote = (RemoteFolder)getRemote(); - - // The parent must be managed - if (! local.getParent().isCVSFolder()) - return; - - // Ensure that the folder exists locally - if (! local.exists()) { - local.mkdir(); - } - - // If the folder already has CVS info, check that the remote and local match - if(local.isManaged() && local.isCVSFolder()) { - // Verify that the root and repository are the same - FolderSyncInfo remoteInfo = remote.getFolderSyncInfo(); - FolderSyncInfo localInfo = local.getFolderSyncInfo(); - if ( ! localInfo.getRoot().equals(remoteInfo.getRoot())) { - throw new CVSException(Policy.bind("CVSRemoteSyncElement.rootDiffers", new Object[] {local.getName(), remoteInfo.getRoot(), localInfo.getRoot()}));//$NON-NLS-1$ - } else if ( ! localInfo.getRepository().equals(remoteInfo.getRepository())) { - throw new CVSException(Policy.bind("CVSRemoteSyncElement.repositoryDiffers", new Object[] {local.getName(), remoteInfo.getRepository(), localInfo.getRepository()}));//$NON-NLS-1$ - } - // The folders are in sync so just return - return; - } - - // Since the parent is managed, this will also set the resource sync info. It is - // impossible for an incoming folder addition to map to another location in the - // repo, so we assume that using the parent's folder sync as a basis is safe. - // It is also impossible for an incomming folder to be static. - FolderSyncInfo remoteInfo = remote.getFolderSyncInfo(); - FolderSyncInfo localInfo = local.getParent().getFolderSyncInfo(); - local.setFolderSyncInfo(new FolderSyncInfo(remoteInfo.getRepository(), remoteInfo.getRoot(), localInfo.getTag(), false)); - } - - public String toString() { - IResource local = getLocal(); - IRemoteResource base = getBase(); - IRemoteResource remote = getRemote(); - StringBuffer result = new StringBuffer(); - result.append("Local: "); - result.append(getLocal().toString()); - result.append(" Base: "); - if (base == null) { - result.append("none"); - } else { - result.append(base.toString()); - } - result.append(" Remote: "); - if (remote == null) { - result.append("none"); - } else { - result.append(remote.toString()); - } - return result.toString(); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSyncTreeSubscriber.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSyncTreeSubscriber.java deleted file mode 100644 index 1ffee9ae5..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSSyncTreeSubscriber.java +++ /dev/null @@ -1,295 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.HashSet; -import java.util.List; -import java.util.Map; -import java.util.Set; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.ComparisonCriteria; -import org.eclipse.team.core.subscribers.ContentComparisonCriteria; -import org.eclipse.team.core.subscribers.SyncInfo; -import org.eclipse.team.core.subscribers.TeamSubscriber; -import org.eclipse.team.core.subscribers.TeamDelta; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer; - -/** - * This class provides common funtionality for three way sychronizing - * for CVS. - */ -public abstract class CVSSyncTreeSubscriber extends TeamSubscriber { - - private QualifiedName id; - private String name; - private String description; - - // options this subscriber supports for determining the sync state of resources - private Map comparisonCriterias = new HashMap(); - private String defaultCriteria; - - CVSSyncTreeSubscriber(QualifiedName id, String name, String description) { - this.id = id; - this.name = name; - this.description = description; - initializeComparisonCriteria(); - } - - /** - * Method invoked from the constructor to initialize the comparison criteria - * and the default criteria. - * This method can be overriden by subclasses. - */ - protected void initializeComparisonCriteria() { - // setup comparison criteria - ComparisonCriteria revisionNumberComparator = new CVSRevisionNumberCompareCriteria(); - ComparisonCriteria contentsComparator = new ContentComparisonCriteria(new ComparisonCriteria[] {revisionNumberComparator}, false /*consider whitespace */); - ComparisonCriteria contentsComparatorIgnoreWhitespace = new ContentComparisonCriteria(new ComparisonCriteria[] {revisionNumberComparator}, true /* ignore whitespace */); - - addComparisonCriteria(revisionNumberComparator); - addComparisonCriteria(contentsComparator); - addComparisonCriteria(contentsComparatorIgnoreWhitespace); - - // default - defaultCriteria = revisionNumberComparator.getId(); - } - - /** - * Add the comparison criteria to the subscriber - * - * @param comparator - */ - protected void addComparisonCriteria(ComparisonCriteria comparator) { - comparisonCriterias.put(comparator.getId(), comparator); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getId() - */ - public QualifiedName getId() { - return id; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getName() - */ - public String getName() { - return name; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getDescription() - */ - public String getDescription() { - return description; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#members(org.eclipse.core.resources.IResource) - */ - public IResource[] members(IResource resource) throws TeamException { - if(resource.getType() == IResource.FILE) { - return new IResource[0]; - } - try { - // Filter and return only phantoms associated with the remote synchronizer. - IResource[] members = ((IContainer)resource).members(true /* include phantoms */); - List filteredMembers = new ArrayList(members.length); - for (int i = 0; i < members.length; i++) { - IResource member = members[i]; - - // TODO: consider that there may be several sync states on this resource. There - // should instead be a method to check for the existance of a set of sync types on - // a resource. - if(member.isPhantom() && getRemoteSynchronizer().getSyncBytes(member) == null) { - continue; - } - - // TODO: Is this a valid use of isSupervised - if (isSupervised(resource)) { - filteredMembers.add(member); - } - } - return (IResource[]) filteredMembers.toArray(new IResource[filteredMembers.size()]); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#roots() - */ - public IResource[] roots() { - return null; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getRemoteResource(org.eclipse.core.resources.IResource) - */ - public IRemoteResource getRemoteResource(IResource resource) throws TeamException { - return getRemoteSynchronizer().getRemoteResource(resource); - } - - public IRemoteResource getBaseResource(IResource resource) throws TeamException { - return getBaseSynchronizer().getRemoteResource(resource); - } - - /** - * Return the synchronizer that provides the remote resources - */ - protected abstract ResourceSynchronizer getRemoteSynchronizer(); - /** - * Return the synchronizer that provides the base resources - */ - protected abstract ResourceSynchronizer getBaseSynchronizer(); - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getSyncInfo(org.eclipse.core.resources.IResource) - */ - public SyncInfo getSyncInfo(IResource resource, IProgressMonitor monitor) throws TeamException { - if (!isSupervised(resource)) return null; - IRemoteResource remoteResource = getRemoteResource(resource); - if(resource.getType() == IResource.FILE) { - IRemoteResource baseResource = getBaseResource(resource); - return getSyncInfo(resource, baseResource, remoteResource, monitor); - } else { - // In CVS, folders do not have a base. Hence, the remote is used as the base. - return getSyncInfo(resource, remoteResource, remoteResource, monitor); - } - } - - /** - * Method that creates an instance of SyncInfo for the provider local, base and remote. - * Can be overiden by subclasses. - * @param local - * @param base - * @param remote - * @param monitor - * @return - */ - protected SyncInfo getSyncInfo(IResource local, IRemoteResource base, IRemoteResource remote, IProgressMonitor monitor) throws TeamException { - try { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - CVSSyncInfo info = new CVSSyncInfo(local, base, remote, this, Policy.subMonitorFor(monitor, 100)); - - // if it's out of sync, then cache the contents - //if(info.getKind() != SyncInfo.IN_SYNC && remote != null) { - // remote.getContents(Policy.subMonitorFor(monitor, 30)); - //} - return info; - } finally { - monitor.done(); - } - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#refresh(org.eclipse.core.resources.IResource[], int, org.eclipse.core.runtime.IProgressMonitor) - */ - public void refresh(IResource[] resources, int depth, IProgressMonitor monitor) throws TeamException { - monitor = Policy.monitorFor(monitor); - try { - monitor.beginTask(null, 100); - IResource[] remoteChanges = refreshRemote(resources, depth, Policy.subMonitorFor(monitor, 60)); - IResource[] baseChanges = getBaseSynchronizer().refresh(resources, depth, getCacheFileContentsHint(), Policy.subMonitorFor(monitor, 40)); - - Set allChanges = new HashSet(); - allChanges.addAll(Arrays.asList(remoteChanges)); - allChanges.addAll(Arrays.asList(baseChanges)); - IResource[] changedResources = (IResource[]) allChanges.toArray(new IResource[allChanges.size()]); - fireTeamResourceChange(TeamDelta.asSyncChangedDeltas(this, changedResources)); - } finally { - monitor.done(); - } - } - - protected IResource[] refreshRemote(IResource[] resources, int depth, IProgressMonitor monitor) throws TeamException { - return getRemoteSynchronizer().refresh(resources, depth, getCacheFileContentsHint(), monitor); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getCurrentComparisonCriteria() - */ - public ComparisonCriteria getCurrentComparisonCriteria() { - return (ComparisonCriteria)comparisonCriterias.get(defaultCriteria); - } - - private boolean getCacheFileContentsHint() { - return getCurrentComparisonCriteria().usesFileContents(); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#setCurrentComparisonCriteria(java.lang.String) - */ - public void setCurrentComparisonCriteria(String id) throws TeamException { - if(! comparisonCriterias.containsKey(id)) { - throw new CVSException(id + " is not a valid comparison criteria"); - } - this.defaultCriteria = id; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#getComparisonCriterias() - */ - public ComparisonCriteria[] getComparisonCriterias() { - return (ComparisonCriteria[]) comparisonCriterias.values().toArray(new ComparisonCriteria[comparisonCriterias.size()]); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#isSupervised(org.eclipse.core.resources.IResource) - */ - public boolean isSupervised(IResource resource) throws TeamException { - RepositoryProvider provider = RepositoryProvider.getProvider(resource.getProject(), CVSProviderPlugin.getTypeId()); - if (provider == null) return false; - // TODO: what happens for resources that don't exist? - // TODO: is it proper to use ignored here? - ICVSResource cvsThing = CVSWorkspaceRoot.getCVSResourceFor(resource); - if (cvsThing.isIgnored()) { - // An ignored resource could have an incoming addition (conflict) - return getRemoteSynchronizer().getSyncBytes(resource) != null; - } - return true; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#isThreeWay() - */ - public boolean isThreeWay() { - return true; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#isCancellable() - */ - public boolean isCancellable() { - return false; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#cancel() - */ - public void cancel() { - // noop - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTag.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTag.java deleted file mode 100644 index 2b4b5fddd..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTag.java +++ /dev/null @@ -1,90 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.runtime.IStatus; - -/** - * A tag in CVS gives a label to a collection of revisions. The labels can represent a version, a branch, - * or a date. - */ -public class CVSTag { - - public final static int HEAD = 0; - public final static int BRANCH = 1; - public final static int VERSION = 2; - public final static int DATE = 3; - - public static final CVSTag DEFAULT = new CVSTag(); - public static final CVSTag BASE = new CVSTag("BASE", VERSION); //$NON-NLS-1$ - - protected String name; - protected int type; - - public CVSTag() { - this("HEAD", HEAD); //$NON-NLS-1$ - } - - public CVSTag(String name, int type) { - this.name = name; - this.type = type; - } - - public boolean equals(Object other) { - if(other == this) return true; - if (!(other instanceof CVSTag)) return false; - - CVSTag tag = ((CVSTag)other); - if (getType() != tag.getType()) return false; - if (!getName().equals(tag.getName())) return false; - return true; - } - - public String getName() { - return name; - } - - public int getType() { - // TODO: getType() will not return accurate types for Tags retrieved from the local CVS Entries file. See Bug: 36758 - return type; - } - - public int hashCode() { - return name.hashCode(); - } - - public int compareTo(CVSTag other) { - return getName().compareTo(other.getName()); - } - - public static boolean equalTags(CVSTag tag1, CVSTag tag2) { - if (tag1 == null) tag1 = CVSTag.DEFAULT; - if (tag2 == null) tag2 = CVSTag.DEFAULT; - return tag1.equals(tag2); - } - - public static IStatus validateTagName(String tagName) { - if (tagName == null) - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTag.nullName")); //$NON-NLS-1$ - if (tagName.equals("")) //$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTag.emptyName")); //$NON-NLS-1$ - if (!Character. isLetter(tagName.charAt(0))) - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTag.beginName")); //$NON-NLS-1$ - - for (int i = 0; i < tagName.length(); i++) { - char c = tagName.charAt(i); - if ( Character.isSpaceChar(c) || c == '$' || c == ',' || c == '.' || c == ':' || c == ';' || c == '@' || c == '|') - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTag.badCharName")); //$NON-NLS-1$ - } - return new CVSStatus(CVSStatus.OK, Policy.bind("ok")); //$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTeamProvider.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTeamProvider.java deleted file mode 100644 index ed4715ff3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTeamProvider.java +++ /dev/null @@ -1,1582 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.io.BufferedInputStream; -import java.io.BufferedReader; -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.io.PrintStream; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collection; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Set; -import java.util.SortedSet; -import java.util.TreeSet; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFileModificationValidator; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceVisitor; -import org.eclipse.core.resources.IWorkspaceRunnable; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.resources.team.IMoveDeleteHook; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IConfigurationElement; -import org.eclipse.core.runtime.IExtension; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.NullProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.core.runtime.Platform; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.core.runtime.Status; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteSyncElement; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Commit; -import org.eclipse.team.internal.ccvs.core.client.Diff; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.KSubstOption; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.client.listeners.AdminKSubstListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.DiffListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.EditorsListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; -import org.eclipse.team.internal.ccvs.core.resources.CVSRemoteSyncElement; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.EclipseSynchronizer; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.MoveDeleteHook; -import org.eclipse.team.internal.ccvs.core.util.PrepareForReplaceVisitor; -import org.eclipse.team.internal.ccvs.core.util.ReplaceWithBaseVisitor; -import org.eclipse.team.internal.ccvs.core.util.SyncFileWriter; -import org.eclipse.team.internal.core.streams.CRLFtoLFInputStream; -import org.eclipse.team.internal.core.streams.LFtoCRLFInputStream; - -/** - * This class acts as both the ITeamNature and the ITeamProvider instances - * required by the Team core. - * - * The current stat of this class and it's plugin is EXPERIMENTAL. - * As such, it is subject to change except in it's conformance to the - * TEAM API which it implements. - * - * Questions: - * - * How should a project/reource rename/move effect the provider? - * - * Currently we always update with -P. Is this OK? - * - A way to allow customizable options would be nice - * - * Is the -l option valid for commit and does it work properly for update and commit? - * - * Do we need an IUserInteractionProvider in the CVS core - * - prompt for user info (caching could be separate) - * - get release comments - * - prompt for overwrite of unmanaged files - * - * Need a mechanism for communicating meta-information (provided by Team?) - * - * Should pass null when there are no options for a cvs command - * - * We currently write the files to disk and do a refreshLocal to - * have them appear in Eclipse. This may be changed in the future. - */ -public class CVSTeamProvider extends RepositoryProvider { - - private static final boolean IS_CRLF_PLATFORM = Arrays.equals( - System.getProperty("line.separator").getBytes(), new byte[] { '\r', '\n' }); //$NON-NLS-1$ - - public static final IStatus OK = new Status(IStatus.OK, CVSProviderPlugin.ID, 0, Policy.bind("ok"), null); //$NON-NLS-1$ - - private static final int UNIFIED_FORMAT = 0; - private static final int CONTEXT_FORMAT = 1; - private static final int STANDARD_FORMAT = 2; - - private CVSWorkspaceRoot workspaceRoot; - private IProject project; - private String comment = ""; //$NON-NLS-1$ - - private static MoveDeleteHook moveDeleteHook= new MoveDeleteHook(); - private static IFileModificationValidator fileModificationValidator; - - // property used to indicate whether new directories should be discovered for the project - private final static QualifiedName FETCH_ABSENT_DIRECTORIES_PROP_KEY = - new QualifiedName("org.eclipse.team.cvs.core", "fetch_absent_directories"); //$NON-NLS-1$ //$NON-NLS-2$ - // property used to indicate whether the project is configured to use Watch/edit - private final static QualifiedName WATCH_EDIT_PROP_KEY = - new QualifiedName("org.eclipse.team.cvs.core", "watch_edit"); //$NON-NLS-1$ //$NON-NLS-2$ - - private static IFileModificationValidator getPluggedInValidator() { - IExtension[] extensions = Platform.getPluginRegistry().getExtensionPoint(CVSProviderPlugin.ID, CVSProviderPlugin.PT_FILE_MODIFICATION_VALIDATOR).getExtensions(); - if (extensions.length == 0) - return null; - IExtension extension = extensions[0]; - IConfigurationElement[] configs = extension.getConfigurationElements(); - if (configs.length == 0) { - CVSProviderPlugin.log(IStatus.ERROR, Policy.bind("CVSAdapter.noConfigurationElement", new Object[] {extension.getUniqueIdentifier()}), null);//$NON-NLS-1$ - return null; - } - try { - IConfigurationElement config = configs[0]; - return (IFileModificationValidator) config.createExecutableExtension("run");//$NON-NLS-1$ - } catch (CoreException ex) { - CVSProviderPlugin.log(IStatus.ERROR, Policy.bind("CVSAdapter.unableToInstantiate", new Object[] {extension.getUniqueIdentifier()}), ex);//$NON-NLS-1$ - return null; - } - } - - /** - * No-arg Constructor for IProjectNature conformance - */ - public CVSTeamProvider() { - } - - /** - * @see IProjectNature#deconfigure() - */ - public void deconfigure() throws CoreException { - // when a nature is removed from the project, notify the synchronizer that - // we no longer need the sync info cached. This does not affect the actual CVS - // meta directories on disk, and will remain unless a client calls unmanage(). - try { - EclipseSynchronizer.getInstance().deconfigure(getProject(), null); - } catch(CVSException e) { - throw new CoreException(e.getStatus()); - } - } - - public void deconfigured() { - CVSProviderPlugin.broadcastProjectDeconfigured(getProject()); - } - /** - * @see IProjectNature#getProject() - */ - public IProject getProject() { - return project; - } - - - - /** - * @see IProjectNature#setProject(IProject) - */ - public void setProject(IProject project) { - this.project = project; - try { - this.workspaceRoot = new CVSWorkspaceRoot(project); - // Ensure that the project has CVS info - if (workspaceRoot.getLocalRoot().getFolderSyncInfo() == null) { - CVSProviderPlugin.log(new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTeamProvider.noFolderInfo", project.getName())))); //$NON-NLS-1$ - } - } catch (CVSException e) { - // Ignore exceptions here. They will be surfaced elsewhere - } - } - - - - /** - * Add the given resources to the project. - * <p> - * The sematics follow that of CVS in the sense that any folders - * being added are created remotely as a result of this operation - * while files are created remotely on the next commit. - * </p> - * <p> - * This method uses the team file type registry to determine the type - * of added files. If the extension of the file is not in the registry, - * the file is assumed to be binary. - * </p> - * <p> - * NOTE: for now we do three operations: one each for folders, text files and binary files. - * We should optimize this when time permits to either use one operations or defer server - * contact until the next commit. - * </p> - * - * <p> - * There are special semantics for adding the project itself to the repo. In this case, the project - * must be included in the resources array. - * </p> - */ - public void add(IResource[] resources, int depth, IProgressMonitor progress) throws TeamException { - - // Visit the children of the resources using the depth in order to - // determine which folders, text files and binary files need to be added - // A TreeSet is needed for the folders so they are in the right order (i.e. parents created before children) - final SortedSet folders = new TreeSet(); - // Sets are required for the files to ensure that files will not appear twice if there parent was added as well - // and the depth isn't zero - final Map /* from KSubstOption to Set */ files = new HashMap(); - final TeamException[] eHolder = new TeamException[1]; - for (int i=0; i<resources.length; i++) { - - final IResource currentResource = resources[i]; - - // Throw an exception if the resource is not a child of the receiver - checkIsChild(currentResource); - - try { - // Auto-add parents if they are not already managed - IContainer parent = currentResource.getParent(); - ICVSResource cvsParentResource = CVSWorkspaceRoot.getCVSResourceFor(parent); - while (parent.getType() != IResource.ROOT && parent.getType() != IResource.PROJECT && ! isManaged(cvsParentResource)) { - folders.add(cvsParentResource); - parent = parent.getParent(); - cvsParentResource = cvsParentResource.getParent(); - } - - // Auto-add children - final TeamException[] exception = new TeamException[] { null }; - currentResource.accept(new IResourceVisitor() { - public boolean visit(IResource resource) { - try { - ICVSResource mResource = CVSWorkspaceRoot.getCVSResourceFor(resource); - // Add the resource is its not already managed and it was either - // added explicitly (is equal currentResource) or is not ignored - if (! isManaged(mResource) && (currentResource.equals(resource) || ! mResource.isIgnored())) { - if (resource.getType() == IResource.FILE) { - KSubstOption ksubst = KSubstOption.fromFile((IFile) resource); - Set set = (Set) files.get(ksubst); - if (set == null) { - set = new HashSet(); - files.put(ksubst, set); - } - set.add(mResource); - } else { - folders.add(mResource); - } - } - // Always return true and let the depth determine if children are visited - return true; - } catch (CVSException e) { - exception[0] = e; - return false; - } - } - }, depth, false); - if (exception[0] != null) { - throw exception[0]; - } - } catch (CoreException e) { - throw new CVSException(new Status(IStatus.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSTeamProvider.visitError", new Object[] {resources[i].getFullPath()}), e)); //$NON-NLS-1$ - } - } - // If an exception occured during the visit, throw it here - if (eHolder[0] != null) - throw eHolder[0]; - - // Add the folders, followed by files! - progress.beginTask(null, files.size() * 10 + (folders.isEmpty() ? 0 : 10)); - try { - if (!folders.isEmpty()) { - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(progress, 2)); - try { - IStatus status = Command.ADD.execute( - session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - (ICVSResource[])folders.toArray(new ICVSResource[folders.size()]), - null, - Policy.subMonitorFor(progress, 8)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - session.close(); - } - } - for (Iterator it = files.entrySet().iterator(); it.hasNext();) { - Map.Entry entry = (Map.Entry) it.next(); - final KSubstOption ksubst = (KSubstOption) entry.getKey(); - final Set set = (Set) entry.getValue(); - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(progress, 2)); - try { - IStatus status = Command.ADD.execute( - session, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] { ksubst }, - (ICVSResource[])set.toArray(new ICVSResource[set.size()]), - null, - Policy.subMonitorFor(progress, 8)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - session.close(); - } - } - } finally { - progress.done(); - } - } - - /* - * Consider a folder managed only if it's also a CVS folder - */ - private boolean isManaged(ICVSResource cvsResource) throws CVSException { - return cvsResource.isManaged() && (!cvsResource.isFolder() || ((ICVSFolder)cvsResource).isCVSFolder()); - } - - /** - * Checkin any local changes using "cvs commit ...". - * - * @see ITeamProvider#checkin(IResource[], int, IProgressMonitor) - */ - public void checkin(IResource[] resources, int depth, IProgressMonitor progress) throws TeamException { - - // Build the local options - List localOptions = new ArrayList(); - localOptions.add(Commit.makeArgumentOption(Command.MESSAGE_OPTION, comment)); - - // If the depth is not infinite, we want the -l option - if (depth != IResource.DEPTH_INFINITE) { - localOptions.add(Commit.DO_NOT_RECURSE); - } - LocalOption[] commandOptions = (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]); - - // Build the arguments list - String[] arguments = getValidArguments(resources, commandOptions); - - // Commit the resources - IStatus status; - Session s = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot()); - progress.beginTask(null, 100); - try { - // Opening the session takes 20% of the time - s.open(Policy.subMonitorFor(progress, 20)); - status = Command.COMMIT.execute(s, - Command.NO_GLOBAL_OPTIONS, - commandOptions, - arguments, null, - Policy.subMonitorFor(progress, 80)); - } finally { - s.close(); - progress.done(); - } - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } - - /** - * @see ITeamProvider#delete(IResource[], int, IProgressMonitor) - */ - public void delete(IResource[] resources, final IProgressMonitor progress) throws TeamException { - try { - progress.beginTask(null, 100); - - // Delete any files locally and record the names. - // Use a resource visitor to ensure the proper depth is obtained - final IProgressMonitor subProgress = Policy.infiniteSubMonitorFor(progress, 30); - subProgress.beginTask(null, 256); - final List files = new ArrayList(resources.length); - final TeamException[] eHolder = new TeamException[1]; - for (int i=0;i<resources.length;i++) { - IResource resource = resources[i]; - checkIsChild(resource); - try { - if (resource.exists()) { - resource.accept(new IResourceVisitor() { - public boolean visit(IResource resource) { - try { - ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(resource); - if (cvsResource.isManaged()) { - String name = resource.getProjectRelativePath().toString(); - if (resource.getType() == IResource.FILE) { - files.add(name); - ((IFile)resource).delete(false, true, subProgress); - } - } - } catch (TeamException e) { - eHolder[0] = e; - } catch (CoreException e) { - eHolder[0] = wrapException(e); - // If there was a problem, don't visit the children - return false; - } - // Always return true and let the depth determine if children are visited - return true; - } - }, IResource.DEPTH_INFINITE, false); - } else if (resource.getType() == IResource.FILE) { - // If the resource doesn't exist but is a file, queue it for removal - files.add(resource.getProjectRelativePath().toString()); - } - } catch (CoreException e) { - throw wrapException(e); - } - } - subProgress.done(); - // If an exception occured during the visit, throw it here - if (eHolder[0] != null) throw eHolder[0]; - // If there are no files to delete, we are done - if (files.isEmpty()) return; - - // Remove the files remotely - IStatus status; - Session s = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot()); - s.open(Policy.subMonitorFor(progress, 10)); - try { - status = Command.REMOVE.execute(s, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - (String[])files.toArray(new String[files.size()]), - null, - Policy.subMonitorFor(progress, 60)); - } finally { - s.close(); - } - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - progress.done(); - } - } - - /** - * Diff the resources with the repository and write the output to the provided - * PrintStream in a form that is usable as a patch. The patch is rooted at the - * project. - */ - public void diff(IResource resource, LocalOption[] options, PrintStream stream, - IProgressMonitor progress) throws TeamException { - - boolean includeNewFiles = false; - boolean doNotRecurse = false; - int format = STANDARD_FORMAT; - - // Determine the command root and arguments arguments list - ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(resource); - ICVSFolder commandRoot; - String[] arguments; - if (cvsResource.isFolder()) { - commandRoot = (ICVSFolder)cvsResource; - arguments = new String[] {Session.CURRENT_LOCAL_FOLDER}; - } else { - commandRoot = cvsResource.getParent(); - arguments = new String[] {cvsResource.getName()}; - } - - Session s = new Session(workspaceRoot.getRemoteLocation(), commandRoot); - progress.beginTask(null, 100); - try { - s.open(Policy.subMonitorFor(progress, 20)); - Command.DIFF.execute(s, - Command.NO_GLOBAL_OPTIONS, - options, - arguments, - new DiffListener(stream), - Policy.subMonitorFor(progress, 80)); - } finally { - s.close(); - progress.done(); - } - - // Append our diff output to the server diff output. - // Our diff output includes new files and new files in new directories. - - for (int i = 0; i < options.length; i++) { - LocalOption option = options[i]; - if (option.equals(Diff.INCLUDE_NEWFILES)) { - includeNewFiles = true; - } else if (option.equals(Diff.DO_NOT_RECURSE)) { - doNotRecurse = true; - } else if (option.equals(Diff.UNIFIED_FORMAT)) { - format = UNIFIED_FORMAT; - } else if (option.equals(Diff.CONTEXT_FORMAT)) { - format = CONTEXT_FORMAT; - } - } - - if (includeNewFiles) { - newFileDiff(commandRoot, stream, doNotRecurse, format); - } - } - - /** - * This diff adds new files and directories to the stream. - * @param resource - * @param stream - * @param doNotRecurse - * @param format - * @throws CVSException - */ - private void newFileDiff(final ICVSResource resource, final PrintStream stream, final boolean doNotRecurse, final int format) throws CVSException { - resource.accept(new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - if (!(file.isIgnored() || file.isManaged())) { - addFileToDiff(file, stream, format); - } - } - public void visitFolder(ICVSFolder folder) throws CVSException { - // Even if we are not supposed to recurse we still need to go into - // the root directory. - if (!folder.exists() || folder.isIgnored() || (doNotRecurse && !folder.equals(resource))) { - return; - } else { - folder.acceptChildren(this); - } - } - }); - } - - private void addFileToDiff(ICVSFile file, PrintStream stream, int format) throws CVSException { - - String nullFilePrefix = ""; //$NON-NLS-1$ - String newFilePrefix = ""; //$NON-NLS-1$ - String positionInfo = ""; //$NON-NLS-1$ - String linePrefix = ""; //$NON-NLS-1$ - - String pathString = file.getIResource().getProjectRelativePath().toString(); - - BufferedReader fileReader = new BufferedReader(new InputStreamReader(file.getContents())); - int lines = 0; - try { - while (fileReader.readLine() != null) { - lines++; - } - fileReader.close(); - - switch (format) { - case UNIFIED_FORMAT : - nullFilePrefix = "--- "; //$NON-NLS-1$ - newFilePrefix = "+++ "; //$NON-NLS-1$ - positionInfo = "@@ -0,0 +1," + lines + " @@" ; //$NON-NLS-1$ //$NON-NLS-2$ - linePrefix = "+"; //$NON-NLS-1$ - break; - - case CONTEXT_FORMAT : - nullFilePrefix = "*** "; //$NON-NLS-1$ - newFilePrefix = "--- "; //$NON-NLS-1$ - positionInfo = "--- 1," + lines + " ----"; //$NON-NLS-1$ //$NON-NLS-2$ - linePrefix = "+ "; //$NON-NLS-1$ - break; - - default : - positionInfo = "0a1," + lines; //$NON-NLS-1$ - linePrefix = "> "; //$NON-NLS-1$ - break; - } - - fileReader = new BufferedReader(new InputStreamReader(file.getContents())); - - stream.println("Index: " + pathString); //$NON-NLS-1$ - stream.println("==================================================================="); //$NON-NLS-1$ - stream.println("RCS file: " + pathString); //$NON-NLS-1$ - stream.println("diff -N " + pathString); //$NON-NLS-1$ - - if (lines > 0) { - - if (format != STANDARD_FORMAT) { - stream.println(nullFilePrefix + "/dev/null 1 Jan 1970 00:00:00 -0000"); //$NON-NLS-1$ - // Technically this date should be the local file date but nobody really cares. - stream.println(newFilePrefix + pathString + " 1 Jan 1970 00:00:00 -0000"); //$NON-NLS-1$ - } - - if (format == CONTEXT_FORMAT) { - stream.println("***************"); //$NON-NLS-1$ - stream.println("*** 0 ****"); //$NON-NLS-1$ - } - - stream.println(positionInfo); - - for (int i = 0; i < lines; i++) { - stream.print(linePrefix); - stream.println(fileReader.readLine()); - } - } - } catch (IOException e) { - throw CVSException.wrapException(file.getIResource(), Policy.bind("CVSTeamProvider.errorAddingFileToDiff", pathString), e); //$NON-NLS-1$ - } finally { - try { - fileReader.close(); - } catch (IOException e1) { - } - } - } - - /** - * Replace the local version of the provided resources with the remote using "cvs update -C ..." - * - * @see ITeamProvider#get(IResource[], int, IProgressMonitor) - */ - public void get(IResource[] resources, final int depth, IProgressMonitor progress) throws TeamException { - get(resources, depth, null, progress); - } - - public void get(final IResource[] resources, final int depth, final CVSTag tag, IProgressMonitor progress) throws TeamException { - - // Handle the retrival of the base in a special way - if (tag != null && tag.equals(CVSTag.BASE)) { - new ReplaceWithBaseVisitor().replaceWithBase(getProject(), resources, depth, progress); - return; - } - - // Make a connection before preparing for the replace to avoid deletion of resources before a failed connection - progress.beginTask(null, 100); - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(progress,10)); - try { - new PrepareForReplaceVisitor().visitResources(getProject(), resources, "CVSTeamProvider.scrubbingResource", depth, Policy.subMonitorFor(progress, 20)); //$NON-NLS-1$ - - List options = new ArrayList(); - options.add(Update.IGNORE_LOCAL_CHANGES); - if(depth != IResource.DEPTH_INFINITE) { - options.add(Command.DO_NOT_RECURSE); - } - LocalOption[] commandOptions = (LocalOption[]) options.toArray(new LocalOption[options.size()]); - - update(session, resources, commandOptions, tag, true /*createBackups*/, Policy.subMonitorFor(progress, 70)); - } finally { - session.close(); - progress.done(); - } - } - - /** - * Return the remote location to which the receiver's project is mapped. - */ - public ICVSRepositoryLocation getRemoteLocation() throws CVSException { - try { - return workspaceRoot.getRemoteLocation(); - } catch (CVSException e) { - // If we can't get the remote location, we should disconnect since nothing can be done with the provider - try { - RepositoryProvider.unmap(project); - } catch (TeamException ex) { - CVSProviderPlugin.log(ex); - } - // We need to trigger a decorator refresh - throw e; - } - } - - /* - * Use specialiazed tagging to move all local changes (including additions and - * deletions) to the specified branch. - */ - public void makeBranch(IResource[] resources, final CVSTag versionTag, final CVSTag branchTag, boolean moveToBranch, IProgressMonitor monitor) throws TeamException { - - // Determine the total amount of work - int totalWork = (versionTag!= null ? 60 : 40) + (moveToBranch ? 20 : 0); - monitor.beginTask(Policy.bind("CVSTeamProvider.makeBranch"), totalWork); //$NON-NLS-1$ - try { - // Build the arguments list - final ICVSResource[] arguments = getCVSArguments(resources); - - // Tag the remote resources - IStatus status = null; - if (versionTag != null) { - // Version using a custom tag command that skips added but not commited reesources - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 5)); - try { - status = Command.CUSTOM_TAG.execute( - session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - versionTag, - arguments, - null, - Policy.subMonitorFor(monitor, 35)); - } finally { - session.close(); - } - if (status.isOK()) { - // Branch using the tag - session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 5)); - try { - status = Command.CUSTOM_TAG.execute( - session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - branchTag, - arguments, - null, - Policy.subMonitorFor(monitor, 15)); - } finally { - session.close(); - } - } - } else { - // Just branch using tag - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 5)); - try { - status = Command.CUSTOM_TAG.execute( - session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - branchTag, - arguments, - null, - Policy.subMonitorFor(monitor, 35)); - } finally { - session.close(); - } - - } - if ( ! status.isOK()) { - throw new CVSServerException(status); - } - - // Set the tag of the local resources to the branch tag (The update command will not - // properly update "cvs added" and "cvs removed" resources so a custom visitor is used - if (moveToBranch) { - setTag(resources, branchTag, Policy.subMonitorFor(monitor, 20)); - } - } finally { - monitor.done(); - } - } - - /** - * Update the sync info of the local resource associated with the sync element such that - * the revision of the local resource matches that of the remote resource. - * This will allow commits on the local resource to succeed. - * - * Only file resources can be merged. - */ - public void merged(IRemoteSyncElement[] elements) throws TeamException { - for (int i=0;i<elements.length;i++) { - ((CVSRemoteSyncElement)elements[i]).makeOutgoing(Policy.monitorFor(null)); - } - } - - /** - * @see ITeamProvider#move(IResource, IPath, IProgressMonitor) - */ - public void moved(IPath source, IResource resource, IProgressMonitor progress) throws TeamException { - } - - /** - * Set the comment to be used on the next checkin - */ - public void setComment(String comment) { - this.comment = comment; - } - - /** - * Set the connection method for the given resource's - * project. If the conection method name is invalid (i.e. - * no corresponding registered connection method), false is returned. - */ - public boolean setConnectionInfo(IResource resource, String methodName, IUserInfo userInfo, IProgressMonitor monitor) throws TeamException { - checkIsChild(resource); - try { - monitor.beginTask(Policy.bind("CVSTeamProvider.connectionInfo", project.getName()), 100); //$NON-NLS-1$ - - if (!CVSRepositoryLocation.validateConnectionMethod(methodName)) - return false; - - // Get the original location - ICVSRepositoryLocation location = workspaceRoot.getRemoteLocation(); - - // Make a copy to work on - CVSRepositoryLocation newLocation = CVSRepositoryLocation.fromString(location.getLocation()); - newLocation.setMethod(methodName); - newLocation.setUserInfo(userInfo); - - // Validate that a connection can be made with the new location - boolean isKnown = CVSProviderPlugin.getPlugin().isKnownRepository(newLocation.getLocation()); - try { - newLocation.validateConnection(Policy.subMonitorFor(monitor, 20)); - } catch (CVSException e) { - if (!isKnown) - CVSProviderPlugin.getPlugin().disposeRepository(newLocation); - throw e; - } - - // Add the location to the provider - CVSProviderPlugin.getPlugin().addRepository(newLocation); - - // Set the project to use the new Locations - setRemoteRoot(newLocation, Policy.subMonitorFor(monitor, 80)); - return true; - } finally { - monitor.done(); - } - } - - /* - * This method sets the tag for a project. - * It expects to be passed an InfiniteSubProgressMonitor - */ - private void setTag(final IResource[] resources, final CVSTag tag, IProgressMonitor monitor) throws TeamException { - - workspaceRoot.getLocalRoot().run(new ICVSRunnable() { - public void run(IProgressMonitor progress) throws CVSException { - try { - // 512 ticks gives us a maximum of 2048 which seems reasonable for folders and files in a project - progress.beginTask(null, 100); - final IProgressMonitor monitor = Policy.infiniteSubMonitorFor(progress, 100); - monitor.beginTask(Policy.bind("CVSTeamProvider.folderInfo", project.getName()), 512); //$NON-NLS-1$ - - // Visit all the children folders in order to set the root in the folder sync info - for (int i = 0; i < resources.length; i++) { - CVSWorkspaceRoot.getCVSResourceFor(resources[i]).accept(new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - monitor.worked(1); - //ResourceSyncInfo info = file.getSyncInfo(); - byte[] syncBytes = file.getSyncBytes(); - if (syncBytes != null) { - monitor.subTask(Policy.bind("CVSTeamProvider.updatingFile", file.getName())); //$NON-NLS-1$ - file.setSyncBytes(ResourceSyncInfo.setTag(syncBytes, tag), ICVSFile.UNKNOWN); - } - }; - public void visitFolder(ICVSFolder folder) throws CVSException { - monitor.worked(1); - FolderSyncInfo info = folder.getFolderSyncInfo(); - if (info != null) { - monitor.subTask(Policy.bind("CVSTeamProvider.updatingFolder", info.getRepository())); //$NON-NLS-1$ - folder.setFolderSyncInfo(new FolderSyncInfo(info.getRepository(), info.getRoot(), tag, info.getIsStatic())); - folder.acceptChildren(this); - } - }; - }); - } - } finally { - progress.done(); - } - } - }, monitor); - } - - /** - * Generally useful update. - * - * The tag parameter determines any stickyness after the update is run. If tag is null, any tagging on the - * resources being updated remain the same. If the tag is a branch, version or date tag, then the resources - * will be appropriatly tagged. If the tag is HEAD, then there will be no tag on the resources (same as -A - * clear sticky option). - * - * @param createBackups if true, creates .# files for updated files - */ - public void update(IResource[] resources, LocalOption[] options, CVSTag tag, boolean createBackups, IProgressMonitor progress) throws TeamException { - progress.beginTask(null, 100); - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(progress,10)); - try { - update(session, resources, options, tag, createBackups, Policy.subMonitorFor(progress, 90)); - } finally { - session.close(); - } - } - - private void update(Session session, IResource[] resources, LocalOption[] options, CVSTag tag, boolean createBackups, IProgressMonitor progress) throws TeamException { - // Build the local options - List localOptions = new ArrayList(); - - // Use the appropriate tag options - if (tag != null) { - localOptions.add(Update.makeTagOption(tag)); - } - - // Build the arguments list - localOptions.addAll(Arrays.asList(options)); - final LocalOption[] commandOptions = (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]); - final ICVSResource[] arguments = getCVSArguments(resources); - - IStatus status = Command.UPDATE.execute( - session, - Command.NO_GLOBAL_OPTIONS, - commandOptions, - arguments, - null, - progress); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } - - /* - * @see ITeamProvider#refreshState(IResource[], int, IProgressMonitor) - */ - public void refreshState(IResource[] resources, int depth, IProgressMonitor progress) throws TeamException { - Assert.isTrue(false); - } - - /* - * @see ITeamProvider#isDirty(IResource) - */ - public boolean isDirty(IResource resource) { - Assert.isTrue(false); - return false; - } - - public CVSWorkspaceRoot getCVSWorkspaceRoot() { - return workspaceRoot; - } - - /* - * Generate an exception if the resource is not a child of the project - */ - private void checkIsChild(IResource resource) throws CVSException { - if (!isChildResource(resource)) - throw new CVSException(new Status(IStatus.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, - Policy.bind("CVSTeamProvider.invalidResource", //$NON-NLS-1$ - new Object[] {resource.getFullPath().toString(), project.getName()}), - null)); - } - - /* - * Get the arguments to be passed to a commit or update - */ - private String[] getValidArguments(IResource[] resources, LocalOption[] options) throws CVSException { - List arguments = new ArrayList(resources.length); - for (int i=0;i<resources.length;i++) { - checkIsChild(resources[i]); - IPath cvsPath = resources[i].getFullPath().removeFirstSegments(1); - if (cvsPath.segmentCount() == 0) { - arguments.add(Session.CURRENT_LOCAL_FOLDER); - } else { - arguments.add(cvsPath.toString()); - } - } - return (String[])arguments.toArray(new String[arguments.size()]); - } - - private ICVSResource[] getCVSArguments(IResource[] resources) { - ICVSResource[] cvsResources = new ICVSResource[resources.length]; - for (int i = 0; i < cvsResources.length; i++) { - cvsResources[i] = CVSWorkspaceRoot.getCVSResourceFor(resources[i]); - } - return cvsResources; - } - - /* - * This method expects to be passed an InfiniteSubProgressMonitor - */ - public void setRemoteRoot(ICVSRepositoryLocation location, IProgressMonitor monitor) throws TeamException { - - // Check if there is a differnece between the new and old roots - final String root = location.getLocation(); - if (root.equals(workspaceRoot.getRemoteLocation())) - return; - - try { - workspaceRoot.getLocalRoot().run(new ICVSRunnable() { - public void run(IProgressMonitor progress) throws CVSException { - try { - // 256 ticks gives us a maximum of 1024 which seems reasonable for folders is a project - progress.beginTask(null, 100); - final IProgressMonitor monitor = Policy.infiniteSubMonitorFor(progress, 100); - monitor.beginTask(Policy.bind("CVSTeamProvider.folderInfo", project.getName()), 256); //$NON-NLS-1$ - - // Visit all the children folders in order to set the root in the folder sync info - workspaceRoot.getLocalRoot().accept(new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException {}; - public void visitFolder(ICVSFolder folder) throws CVSException { - monitor.worked(1); - FolderSyncInfo info = folder.getFolderSyncInfo(); - if (info != null) { - monitor.subTask(Policy.bind("CVSTeamProvider.updatingFolder", info.getRepository())); //$NON-NLS-1$ - folder.setFolderSyncInfo(new FolderSyncInfo(info.getRepository(), root, info.getTag(), info.getIsStatic())); - folder.acceptChildren(this); - } - }; - }); - } finally { - progress.done(); - } - } - }, monitor); - } finally { - monitor.done(); - } - } - - /* - * Helper to indicate if the resource is a child of the receiver's project - */ - private boolean isChildResource(IResource resource) { - return resource.getProject().getName().equals(project.getName()); - } - - private static TeamException wrapException(CoreException e) { - return CVSException.wrapException(e); - } - - public void configureProject() throws CoreException { - CVSProviderPlugin.broadcastProjectConfigured(getProject()); - } - /** - * Sets the keyword substitution mode for the specified resources. - * <p> - * Applies the following rules in order:<br> - * <ul> - * <li>If a file is not managed, skips it.</li> - * <li>If a file is not changing modes, skips it.</li> - * <li>If a file is being changed from binary to text, corrects line delimiters - * then commits it, then admins it.</li> - * <li>If a file is added, changes the resource sync information locally.</li> - * <li>Otherwise commits the file (with FORCE to create a new revision), then admins it.</li> - * </ul> - * All files that are admin'd are committed with FORCE to prevent other developers from - * casually trying to commit pending changes to the repository without first checking out - * a new copy. This is not a perfect solution, as they could just as easily do an UPDATE - * and not obtain the new keyword sync info. - * </p> - * - * @param changeSet a map from IFile to KSubstOption - * @param monitor the progress monitor - * @return a status code indicating success or failure of the operation - * - * @throws TeamException - */ - public IStatus setKeywordSubstitution(final Map /* from IFile to KSubstOption */ changeSet, - final String comment, - IProgressMonitor monitor) throws TeamException { - final IStatus[] result = new IStatus[] { ICommandOutputListener.OK }; - workspaceRoot.getLocalRoot().run(new ICVSRunnable() { - public void run(final IProgressMonitor monitor) throws CVSException { - final Map /* from KSubstOption to List of String */ filesToAdmin = new HashMap(); - final List /* of ICVSResource */ filesToCommit = new ArrayList(); - final Collection /* of ICVSFile */ filesToCommitAsText = new HashSet(); // need fast lookup - - /*** determine the resources to be committed and/or admin'd ***/ - for (Iterator it = changeSet.entrySet().iterator(); it.hasNext();) { - Map.Entry entry = (Map.Entry) it.next(); - IFile file = (IFile) entry.getKey(); - KSubstOption toKSubst = (KSubstOption) entry.getValue(); - - // only set keyword substitution if resource is a managed file - checkIsChild(file); - ICVSFile mFile = CVSWorkspaceRoot.getCVSFileFor(file); - if (! mFile.isManaged()) continue; - - // only set keyword substitution if new differs from actual - byte[] syncBytes = mFile.getSyncBytes(); - KSubstOption fromKSubst = ResourceSyncInfo.getKeywordMode(syncBytes); - if (toKSubst.equals(fromKSubst)) continue; - - // change resource sync info immediately for an outgoing addition - if (ResourceSyncInfo.isAddition(syncBytes)) { - mFile.setSyncBytes(ResourceSyncInfo.setKeywordMode(syncBytes, toKSubst), ICVSFile.UNKNOWN); - continue; - } - - // nothing do to for deletions - if (ResourceSyncInfo.isDeletion(syncBytes)) continue; - - // file exists remotely so we'll have to commit it - if (fromKSubst.isBinary() && ! toKSubst.isBinary()) { - // converting from binary to text - cleanLineDelimiters(file, IS_CRLF_PLATFORM, new NullProgressMonitor()); // XXX need better progress monitoring - // remember to commit the cleaned resource as text before admin - filesToCommitAsText.add(mFile); - } - // force a commit to bump the revision number - makeDirty(file); - filesToCommit.add(mFile); - // remember to admin the resource - List list = (List) filesToAdmin.get(toKSubst); - if (list == null) { - list = new ArrayList(); - filesToAdmin.put(toKSubst, list); - } - list.add(mFile); - } - - /*** commit then admin the resources ***/ - // compute the total work to be performed - int totalWork = filesToCommit.size() + 1; - for (Iterator it = filesToAdmin.values().iterator(); it.hasNext();) { - List list = (List) it.next(); - totalWork += list.size(); - totalWork += 1; // Add 1 for each connection that needs to be made - } - if (totalWork != 0) { - monitor.beginTask(Policy.bind("CVSTeamProvider.settingKSubst"), totalWork); //$NON-NLS-1$ - try { - // commit files that changed from binary to text - // NOTE: The files are committed as text with conversions even if the - // resource sync info still says "binary". - if (filesToCommit.size() != 0) { - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 1)); - try { - String keywordChangeComment = comment; - if (keywordChangeComment == null || keywordChangeComment.length() == 0) - keywordChangeComment = Policy.bind("CVSTeamProvider.changingKeywordComment"); //$NON-NLS-1$ - result[0] = Command.COMMIT.execute( - session, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] { Commit.DO_NOT_RECURSE, Commit.FORCE, - Commit.makeArgumentOption(Command.MESSAGE_OPTION, keywordChangeComment) }, - (ICVSResource[]) filesToCommit.toArray(new ICVSResource[filesToCommit.size()]), - filesToCommitAsText, - null, - Policy.subMonitorFor(monitor, filesToCommit.size())); - } finally { - session.close(); - } - - // if errors were encountered, abort - if (! result[0].isOK()) return; - } - - // admin files that changed keyword substitution mode - // NOTE: As confirmation of the completion of a command, the server replies - // with the RCS command output if a change took place. Rather than - // assume that the command succeeded, we listen for these lines - // and update the local ResourceSyncInfo for the particular files that - // were actually changed remotely. - for (Iterator it = filesToAdmin.entrySet().iterator(); it.hasNext();) { - Map.Entry entry = (Map.Entry) it.next(); - final KSubstOption toKSubst = (KSubstOption) entry.getKey(); - final List list = (List) entry.getValue(); - // do it - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 1)); - try { - result[0] = Command.ADMIN.execute( - session, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] { toKSubst }, - (ICVSResource[]) list.toArray(new ICVSResource[list.size()]), - new AdminKSubstListener(toKSubst), - Policy.subMonitorFor(monitor, list.size())); - } finally { - session.close(); - } - // if errors were encountered, abort - if (! result[0].isOK()) return; - } - } finally { - monitor.done(); - } - } - } - }, Policy.monitorFor(monitor)); - return result[0]; - } - - /** - * Fixes the line delimiters in the local file to reflect the platform's - * native encoding. Performs CR/LF -> LF or LF -> CR/LF conversion - * depending on the platform but does not affect delimiters that are - * already correctly encoded. - */ - public static void cleanLineDelimiters(IFile file, boolean useCRLF, IProgressMonitor progress) - throws CVSException { - try { - // convert delimiters in memory - ByteArrayOutputStream bos = new ByteArrayOutputStream(); - InputStream is = new BufferedInputStream(file.getContents()); - try { - is = new CRLFtoLFInputStream(is); - if (useCRLF) is = new LFtoCRLFInputStream(is); - for (int b; (b = is.read()) != -1;) bos.write(b); - bos.close(); - } finally { - is.close(); - } - // write file back to disk with corrected delimiters if changes were made - ByteArrayInputStream bis = new ByteArrayInputStream(bos.toByteArray()); - file.setContents(bis, false /*force*/, false /*keepHistory*/, progress); - } catch (CoreException e) { - throw CVSException.wrapException(file, Policy.bind("CVSTeamProvider.cleanLineDelimitersException"), e); //$NON-NLS-1$ - } catch (IOException e) { - throw CVSException.wrapException(file, Policy.bind("CVSTeamProvider.cleanLineDelimitersException"), e); //$NON-NLS-1$ - } - } - - /* - * Marks a file as dirty. - */ - private static void makeDirty(IFile file) throws CVSException { - ICVSFile mFile = CVSWorkspaceRoot.getCVSFileFor(file); - ResourceSyncInfo origInfo = mFile.getSyncInfo(); - MutableResourceSyncInfo info = origInfo.cloneMutable(); - info.setTimeStamp(null);/*set the sync timestamp to null to trigger dirtyness*/ - mFile.setSyncInfo(info, ICVSFile.UNKNOWN); - } - - /* - * @see RepositoryProvider#getID() - */ - public String getID() { - return CVSProviderPlugin.getTypeId(); - } - - /* - * @see RepositoryProvider#getMoveDeleteHook() - */ - public IMoveDeleteHook getMoveDeleteHook() { - return moveDeleteHook; - } - - /* - * Return the currently registered Move/Delete Hook - */ - public static MoveDeleteHook getRegisteredMoveDeleteHook() { - return moveDeleteHook; - } - - /** - * @see org.eclipse.team.core.RepositoryProvider#getFileModificationValidator() - */ - public IFileModificationValidator getFileModificationValidator() { - if (CVSTeamProvider.fileModificationValidator == null) { - CVSTeamProvider.fileModificationValidator = CVSTeamProvider.getPluggedInValidator(); - if (CVSTeamProvider.fileModificationValidator == null) { - CVSTeamProvider.fileModificationValidator =super.getFileModificationValidator(); - } - } - return CVSTeamProvider.fileModificationValidator; - } - - /** - * Checkout (cvs edit) the provided resources so they can be modified locally and committed. - * This will make any read-only resources in the list writable and will notify the server - * that the file is being edited. This notification may be done immediately or at some - * later point depending on whether contact with the server is possble at the time of - * invocation or the value of the notify server parameter. - * - * The recurse parameter is equivalent to the cvs local options -l (<code>true</code>) and - * -R (<code>false</code>). The notifyServer parameter can be used to defer server contact - * until the next command. This may be approrpiate if no shell or progress monitor is available - * to the caller. The notification bit field indicates what temporary watches are to be used while - * the file is being edited. The possible values that can be ORed together are ICVSFile.EDIT, - * ICVSFile.UNEDIT and ICVSFile.COMMIT. There pre-ORed convenience values ICVSFile.NO_NOTIFICATION - * and ICVSFile.NOTIFY_ON_ALL are also available. - * - * @param resources the resources to be edited - * @param recurse indicates whether to recurse (-R) or not (-l) - * @param notifyServer indicates whether to notify the server now, if possible, - * or defer until the next command. - * @param notification the temporary watches. - * @param progress progress monitor to provide progress indication/cancellation or <code>null</code> - * @exception CVSException if this method fails. - * @since 2.1 - * - * @see CVSTeamProvider#unedit - */ - public void edit(IResource[] resources, boolean recurse, boolean notifyServer, final int notification, IProgressMonitor progress) throws CVSException { - notifyEditUnedit(resources, recurse, notifyServer, new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - if (file.isReadOnly()) - file.edit(notification, Policy.monitorFor(null)); - } - public void visitFolder(ICVSFolder folder) throws CVSException { - // nothing needs to be done here as the recurse will handle the traversal - } - }, progress); - } - - /** - * Unedit the given resources. Any writtable resources will be reverted to their base contents - * and made read-only and the server will be notified that the file is no longer being edited. - * This notification may be done immediately or at some - * later point depending on whether contact with the server is possble at the time of - * invocation or the value of the notify server parameter. - * - * The recurse parameter is equivalent to the cvs local options -l (<code>true</code>) and - * -R (<code>false</code>). The notifyServer parameter can be used to defer server contact - * until the next command. This may be approrpiate if no shell or progress monitor is available - * to the caller. - * - * @param resources the resources to be unedited - * @param recurse indicates whether to recurse (-R) or not (-l) - * @param notifyServer indicates whether to notify the server now, if possible, - * or defer until the next command. - * @param progress progress monitor to provide progress indication/cancellation or <code>null</code> - * @exception CVSException if this method fails. - * @since 2.1 - * - * @see CVSTeamProvider#edit - */ - public void unedit(IResource[] resources, boolean recurse, boolean notifyServer, IProgressMonitor progress) throws CVSException { - notifyEditUnedit(resources, recurse, notifyServer, new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - if (!file.isReadOnly()) - file.unedit(Policy.monitorFor(null)); - } - public void visitFolder(ICVSFolder folder) throws CVSException { - // nothing needs to be done here as the recurse will handle the traversal - } - }, progress); - } - - /* - * This method captures the common behavior between the edit and unedit methods. - */ - private void notifyEditUnedit(final IResource[] resources, final boolean recurse, final boolean notifyServer, final ICVSResourceVisitor editUneditVisitor, IProgressMonitor monitor) throws CVSException { - final CVSException[] exception = new CVSException[] { null }; - IWorkspaceRunnable workspaceRunnable = new IWorkspaceRunnable() { - public void run(IProgressMonitor monitor) throws CoreException { - final ICVSResource[] cvsResources = getCVSArguments(resources); - - // mark the files locally as being checked out - try { - for (int i = 0; i < cvsResources.length; i++) { - cvsResources[i].accept(editUneditVisitor, recurse); - } - } catch (CVSException e) { - exception[0] = e; - return; - } - - // send the noop command to the server in order to deliver the notifications - if (notifyServer) { - monitor.beginTask(null, 100); - Session session = new Session(workspaceRoot.getRemoteLocation(), workspaceRoot.getLocalRoot(), true); - try { - session.open(Policy.subMonitorFor(monitor, 10)); - } catch (CVSException e1) { - // If the connection cannot be opened, just exit normally. - // The notifications will be sent when a connection can be made - return; - } - try { - Command.NOOP.execute( - session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - cvsResources, - null, - Policy.subMonitorFor(monitor, 90)); - } catch (CVSException e) { - exception[0] = e; - } finally { - monitor.done(); - } - } - } - }; - try { - ResourcesPlugin.getWorkspace().run(workspaceRunnable, Policy.monitorFor(monitor)); - } catch (CoreException e) { - if (exception[0] == null) { - throw CVSException.wrapException(e); - } else { - CVSProviderPlugin.log(CVSException.wrapException(e)); - } - } - if (exception[0] != null) { - throw exception[0]; - } - } - - /** - * Gets the etchAbsentDirectories. - * @return Returns a boolean - */ - public boolean getFetchAbsentDirectories() throws CVSException { - try { - String property = getProject().getPersistentProperty(FETCH_ABSENT_DIRECTORIES_PROP_KEY); - if (property == null) return CVSProviderPlugin.getPlugin().getFetchAbsentDirectories(); - return Boolean.valueOf(property).booleanValue(); - } catch (CoreException e) { - throw new CVSException(new CVSStatus(IStatus.ERROR, Policy.bind("CVSTeamProvider.errorGettingFetchProperty", project.getName()), e)); //$NON-NLS-1$ - } - } - - /** - * Sets the fetchAbsentDirectories. - * @param etchAbsentDirectories The etchAbsentDirectories to set - */ - public void setFetchAbsentDirectories(boolean fetchAbsentDirectories) throws CVSException { - try { - getProject().setPersistentProperty(FETCH_ABSENT_DIRECTORIES_PROP_KEY, fetchAbsentDirectories ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); - } catch (CoreException e) { - throw new CVSException(new CVSStatus(IStatus.ERROR, Policy.bind("CVSTeamProvider.errorSettingFetchProperty", project.getName()), e)); //$NON-NLS-1$ - } - } - - /** - * @see org.eclipse.team.core.RepositoryProvider#canHandleLinkedResources() - */ - public boolean canHandleLinkedResources() { - return true; - } - - /** - * @see org.eclipse.team.core.RepositoryProvider#validateCreateLink(org.eclipse.core.resources.IResource, int, org.eclipse.core.runtime.IPath) - */ - public IStatus validateCreateLink(IResource resource, int updateFlags, IPath location) { - ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor(resource.getParent().getFolder(new Path(resource.getName()))); - try { - if (cvsFolder.isCVSFolder()) { - // There is a remote folder that overlaps with the link so disallow - return new CVSStatus(IStatus.ERROR, Policy.bind("CVSTeamProvider.overlappingRemoteFolder", resource.getFullPath().toString())); //$NON-NLS-1$ - } else { - ICVSFile cvsFile = CVSWorkspaceRoot.getCVSFileFor(resource.getParent().getFile(new Path(resource.getName()))); - if (cvsFile.isManaged()) { - // there is an outgoing file deletion that overlaps the link so disallow - return new CVSStatus(IStatus.ERROR, Policy.bind("CVSTeamProvider.overlappingFileDeletion", resource.getFullPath().toString())); //$NON-NLS-1$ - } - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - return e.getStatus(); - } - - return super.validateCreateLink(resource, updateFlags, location); - } - - /** - * Get the editors of the resources by calling the <code>cvs editors</code> command. - * - * @author <a href="mailto:gregor.kohlwes@csc.com,kohlwes@gmx.net">Gregor Kohlwes</a> - * @param resources - * @param progress - * @return IEditorsInfo[] - * @throws CVSException - */ - public EditorsInfo[] editors( - IResource[] resources, - IProgressMonitor progress) - throws CVSException { - - // Build the local options - LocalOption[] commandOptions = new LocalOption[] { - }; - - // Build the arguments list - String[] arguments = getValidArguments(resources, commandOptions); - - // Build the listener for the command - EditorsListener listener = new EditorsListener(); - - // Check if canceled - if (progress.isCanceled()) { - return new EditorsInfo[0]; - } - // Build the session - Session session = - new Session( - workspaceRoot.getRemoteLocation(), - workspaceRoot.getLocalRoot()); - - // Check if canceled - if (progress.isCanceled()) { - return new EditorsInfo[0]; - } - progress.beginTask(null, 100); - try { - // Opening the session takes 20% of the time - session.open(Policy.subMonitorFor(progress, 20)); - - if (!progress.isCanceled()) { - // Execute the editors command - Command.EDITORS.execute( - session, - Command.NO_GLOBAL_OPTIONS, - commandOptions, - arguments, - listener, - Policy.subMonitorFor(progress, 80)); - } - } finally { - session.close(); - progress.done(); - } - // Return the infos about the editors - return listener.getEditorsInfos(); - } - - /** - * Return the commit comment template that was provided by the server. - * - * @return String - * @throws CVSException - */ - public String getCommitTemplate() throws CVSException { - ICVSFolder localFolder = getCVSWorkspaceRoot().getLocalRoot(); - ICVSFile templateFile = CVSWorkspaceRoot.getCVSFileFor( - SyncFileWriter.getTemplateFile( - (IContainer)localFolder.getIResource())); - if (!templateFile.exists()) return null; - InputStream in = new BufferedInputStream(templateFile.getContents()); - try { - ByteArrayOutputStream out = new ByteArrayOutputStream(); - int b; - do { - b = in.read(); - if (b != -1) - out.write((byte)b); - } while (b != -1); - out.close(); - return new String(out.toString()); - } catch (IOException e) { - throw CVSException.wrapException(e); - } finally { - try { - in.close(); - } catch (IOException e) { - // Since we already have the contents, just log this exception - CVSProviderPlugin.log(CVSException.wrapException(e)); - } - } - } - - /** - * Return true if the project is configured to use watch/edit. A project will use - * watch/edit if it was checked out when the global preference to use watch/edit is - * turned on. - * @return boolean - */ - public boolean isWatchEditEnabled() throws CVSException { - try { - IProject project = getProject(); - String property = (String)project.getSessionProperty(WATCH_EDIT_PROP_KEY); - if (property == null) { - property = project.getPersistentProperty(WATCH_EDIT_PROP_KEY); - if (property == null) { - // The persistant property for the project was never set (i.e. old project) - // Use the global preference to determinw if the project is using watch/edit - return CVSProviderPlugin.getPlugin().isWatchEditEnabled(); - } else { - project.setSessionProperty(WATCH_EDIT_PROP_KEY, property); - } - } - return Boolean.valueOf(property).booleanValue(); - } catch (CoreException e) { - throw new CVSException(new CVSStatus(IStatus.ERROR, Policy.bind("CVSTeamProvider.errorGettingWatchEdit", project.getName()), e)); //$NON-NLS-1$ - } - } - - public void setWatchEditEnabled(boolean enabled) throws CVSException { - try { - IProject project = getProject(); - project.setPersistentProperty(WATCH_EDIT_PROP_KEY, enabled ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); - project.setSessionProperty(WATCH_EDIT_PROP_KEY, enabled ? Boolean.TRUE.toString() : Boolean.FALSE.toString()); - } catch (CoreException e) { - throw new CVSException(new CVSStatus(IStatus.ERROR, Policy.bind("CVSTeamProvider.errorSettingWatchEdit", project.getName()), e)); //$NON-NLS-1$ - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTeamProviderType.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTeamProviderType.java deleted file mode 100644 index b59f85a7d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSTeamProviderType.java +++ /dev/null @@ -1,31 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.team.core.RepositoryProviderType; - - -/** - * This class represents the CVS Provider's capabilities in the absence of a - * particular project. - */ - -public class CVSTeamProviderType extends RepositoryProviderType { - - /** - * @see org.eclipse.team.core.RepositoryProviderType#supportsProjectSetImportRelocation() - */ - public boolean supportsProjectSetImportRelocation() { - return false; - } - - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSWorkspaceSubscriber.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSWorkspaceSubscriber.java deleted file mode 100644 index f7a88ac90..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/CVSWorkspaceSubscriber.java +++ /dev/null @@ -1,220 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceVisitor; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.subscribers.SyncInfo; -import org.eclipse.team.core.subscribers.TeamDelta; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.syncinfo.OptimizedRemoteSynchronizer; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer; - -/** - * CVSWorkspaceSubscriber - */ -public class CVSWorkspaceSubscriber extends CVSSyncTreeSubscriber implements IResourceStateChangeListener { - - private OptimizedRemoteSynchronizer remoteSynchronizer; - - // qualified name for remote sync info - private static final String REMOTE_RESOURCE_KEY = "remote-resource-key"; //$NON-NLS-1$ - - CVSWorkspaceSubscriber(QualifiedName id, String name, String description) { - super(id, name, description); - - // install sync info participant - remoteSynchronizer = new OptimizedRemoteSynchronizer(REMOTE_RESOURCE_KEY); - - // TODO: temporary proxy for CVS events - CVSProviderPlugin.addResourceStateChangeListener(this); - } - - /* - * Return the list of projects shared with a CVS team provider. - * - * [Issue : this will have to change when folders can be shared with - * a team provider instead of the current project restriction] - * (non-Javadoc) - * @see org.eclipse.team.core.sync.ISyncTreeSubscriber#roots() - */ - public IResource[] roots() { - List result = new ArrayList(); - IProject[] projects = ResourcesPlugin.getWorkspace().getRoot().getProjects(); - for (int i = 0; i < projects.length; i++) { - IProject project = projects[i]; - if(project.isOpen()) { - RepositoryProvider provider = RepositoryProvider.getProvider(project, CVSProviderPlugin.getTypeId()); - if(provider != null) { - result.add(project); - } - } - } - return (IProject[]) result.toArray(new IProject[result.size()]); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.IResourceStateChangeListener#resourceSyncInfoChanged(org.eclipse.core.resources.IResource[]) - */ - public void resourceSyncInfoChanged(IResource[] changedResources) { - - // TODO: hack for clearing the remote state when anything to the resource - // sync is changed. Should be able to set the *right* remote/base based on - // the sync being set. - // TODO: This will throw exceptions if performed during the POST_CHANGE delta phase!!! - for (int i = 0; i < changedResources.length; i++) { - IResource resource = changedResources[i]; - try { - // TODO should use revision and tag to determine if remote is stale - // TODO outgoing deletions would require special handling - if (resource.getType() == IResource.FILE - && (resource.exists() || resource.isPhantom())) { - remoteSynchronizer.removeSyncBytes(resource, IResource.DEPTH_ZERO, true /* silent */); - } else if (resource.getType() == IResource.FOLDER) { - // If the base has sync info for the folder, purge the remote bytes - if (getBaseSynchronizer().getSyncBytes(resource) != null) { - remoteSynchronizer.removeSyncBytes(resource, IResource.DEPTH_ZERO, true /* silent */); - } - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - } - - fireTeamResourceChange(TeamDelta.asSyncChangedDeltas(this, changedResources)); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.IResourceStateChangeListener#resourceModified(org.eclipse.core.resources.IResource[]) - */ - public void resourceModified(IResource[] changedResources) { - // TODO: This is only ever called from a delta POST_CHANGE - // which causes problems since the workspace tree is closed - // for modification and we flush the sync info in resourceSyncInfoChanged - - // Since the listeners of the Subscriber will also listen to deltas - // we don't need to propogate this. - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.IResourceStateChangeListener#projectConfigured(org.eclipse.core.resources.IProject) - */ - public void projectConfigured(IProject project) { - TeamDelta delta = new TeamDelta(this, TeamDelta.PROVIDER_CONFIGURED, project); - fireTeamResourceChange(new TeamDelta[] {delta}); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.IResourceStateChangeListener#projectDeconfigured(org.eclipse.core.resources.IProject) - */ - public void projectDeconfigured(IProject project) { - try { - remoteSynchronizer.removeSyncBytes(project, IResource.DEPTH_INFINITE, false /* not silent */); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - TeamDelta delta = new TeamDelta(this, TeamDelta.PROVIDER_DECONFIGURED, project); - fireTeamResourceChange(new TeamDelta[] {delta}); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getRemoteSynchronizer() - */ - protected ResourceSynchronizer getRemoteSynchronizer() { - return remoteSynchronizer; - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getBaseSynchronizer() - */ - protected ResourceSynchronizer getBaseSynchronizer() { - return remoteSynchronizer.getBaseSynchronizer(); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.TeamSubscriber#getAllOutOfSync(org.eclipse.core.resources.IResource[], int, org.eclipse.core.runtime.IProgressMonitor) - */ - public SyncInfo[] getAllOutOfSync(IResource[] resources, final int depth, IProgressMonitor monitor) throws TeamException { - monitor.beginTask(null, resources.length * 100); - final List result = new ArrayList(); - for (int i = 0; i < resources.length; i++) { - IResource resource = resources[i]; - ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(resource); - final IProgressMonitor infinite = Policy.infiniteSubMonitorFor(monitor, 100); - try { - infinite.beginTask(null, 512); - resource.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - try { - if (isOutOfSync(resource, infinite)) { - SyncInfo info = getSyncInfo(resource, infinite); - if (info != null && info.getKind() != 0) { - result.add(info); - } - } - return true; - } catch (TeamException e) { - // TODO: This is probably not the right thing to do here - throw new CoreException(e.getStatus()); - } - } - }, depth, true /* include phantoms */); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - infinite.done(); - } - } - monitor.done(); - return (SyncInfo[]) result.toArray(new SyncInfo[result.size()]); - } - - private boolean isOutOfSync(IResource resource, IProgressMonitor monitor) throws CVSException { - return (hasIncomingChange(resource) || hasOutgoingChange(CVSWorkspaceRoot.getCVSResourceFor(resource), monitor)); - } - - private boolean hasOutgoingChange(ICVSResource resource, IProgressMonitor monitor) throws CVSException { - if (resource.isFolder()) { - // A folder is an outgoing change if it is not a CVS folder and not ignored - ICVSFolder folder = (ICVSFolder)resource; - // TODO: The parent caches the dirty state so we only need to check - // the file if the parent is dirty. - // TODO: Unfortunately, the modified check on the parent still loads - // the CVS folder information so not much is gained - if (folder.getParent().isModified(monitor)) { - return !folder.isCVSFolder() && !folder.isIgnored(); - } - } else { - // A file is an outgoing change if it is modified - ICVSFile file = (ICVSFile)resource; - // TODO: The parent chaches the dirty state so we only need to check - // the file if the parent is dirty - if (file.getParent().isModified(monitor)) { - return file.isModified(monitor); - } - } - return false; - } - - private boolean hasIncomingChange(IResource resource) throws CVSException { - return remoteSynchronizer.getRemoteBytes(resource) != null; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/DateUtil.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/DateUtil.java deleted file mode 100644 index 2c9022a67..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/DateUtil.java +++ /dev/null @@ -1,92 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import java.text.ParseException; -import java.text.SimpleDateFormat; -import java.util.Date; -import java.util.Locale; -import java.util.TimeZone; - -/** - * Utilities to handle time stamps in a cvs client. - */ -public class DateUtil { - - private static final String ENTRY_TIMESTAMP_FORMAT= "EEE MMM dd HH:mm:ss yyyy";//$NON-NLS-1$ - private static final String ENTRY_TIMESTAMP_TIME_ZONE= "GMT";//$NON-NLS-1$ - private static final Locale ENTRY_TIMESTAMP_LOCALE= Locale.US; - - private static final String MODTIME_TIMESTAMP_FORMAT= "dd MMM yyyy HH:mm:ss zz";//$NON-NLS-1$ - private static final Locale MODTIME_TIMESTAMP_LOCALE= Locale.US; - - private static final String LOG_TIMESTAMP_FORMAT= "yyyy/MM/dd HH:mm:ss zzz";//$NON-NLS-1$ - private static final Locale LOG_TIMESTAMP_LOCALE= Locale.US; - - private static final String HISTORY_TIMESTAMP_FORMAT= "yyyy-MM-dd HH:mm zzzz";//$NON-NLS-1$ - private static final Locale HISTORY_TIMESTAMP_LOCALE= Locale.US; - - /** - * Converts a time stamp as sent from a cvs server for a "log" command into a - * <code>Date</code>. - */ - public static Date convertFromLogTime(String modTime) { - SimpleDateFormat format= new SimpleDateFormat(LOG_TIMESTAMP_FORMAT, - LOG_TIMESTAMP_LOCALE); - try { - return format.parse(modTime); - } catch (ParseException e) { - // fallback is to return null - return null; - } - } - /** - * Converts a modifcation time stamp as send from a cvs server into a - * <code>Date</code>. The format of the modification time stamp is defined - * in the document CVS Client/Server for CVS 1.11 section 5.6 Dates - */ - public static Date convertFromModTime(String modTime) { - SimpleDateFormat format= new SimpleDateFormat(MODTIME_TIMESTAMP_FORMAT, - MODTIME_TIMESTAMP_LOCALE); - try { - return format.parse(modTime); - } catch (ParseException e) { - // fallback is to return null - return null; - } - } - /** - * Converts a history time stamp as sent from a cvs server into a - * <code>Date</code>. - */ - public static Date convertFromHistoryTime(String historyTime) { - SimpleDateFormat format= new SimpleDateFormat(HISTORY_TIMESTAMP_FORMAT, - HISTORY_TIMESTAMP_LOCALE); - try { - return format.parse(historyTime); - } catch (ParseException e) { - // fallback is to return null - return null; - } - } - /** - * Converts a date into an entry time format as specified in the document - * Version Management with CVS for CVS 1.10.6 page 14. Note that the - * time format is always in GMT also not specified in the document. - */ - public static String toEntryFormat(Date date) { - SimpleDateFormat format= new SimpleDateFormat(ENTRY_TIMESTAMP_FORMAT, - ENTRY_TIMESTAMP_LOCALE); - format.setTimeZone(TimeZone.getTimeZone(ENTRY_TIMESTAMP_TIME_ZONE)); - return format.format(date); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/EditorsInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/EditorsInfo.java deleted file mode 100644 index 7612f9446..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/EditorsInfo.java +++ /dev/null @@ -1,95 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2003 CSC SoftwareConsult GmbH & Co. OHG, Germany and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * CSC - Intial implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -/** - * Instances of EditorsInfo represent information for a CVS resurce that results - * from the cvs editors command. - * - * @author <a href="mailto:gregor.kohlwes@csc.com,kohlwes@gmx.net">Gregor Kohlwes</a> - */ - -public class EditorsInfo { - public EditorsInfo() { - } - - private String userName; - private String fileName; - private String dateString; - private String computerName; - - - /** - * Returns the userName. - * @return String - */ - public String getUserName() { - return userName; - } - - /** - * Sets the userName. - * @param userName The userName to set - */ - public void setUserName(String userName) { - this.userName = userName; - } - - /** - * Returns the dateString. - * @return String - */ - public String getDateString() { - return dateString; - } - - /** - * Returns the fileName. - * @return String - */ - public String getFileName() { - return fileName; - } - - /** - * Sets the dateString. - * @param dateString The dateString to set - */ - public void setDateString(String dateString) { - this.dateString = dateString; - } - - /** - * Sets the fileName. - * @param fileName The fileName to set - */ - public void setFileName(String fileName) { - this.fileName = fileName; - } - - /** - * Returns the computerName. - * @return String - */ - public String getComputerName() { - return computerName; - } - - /** - * Sets the computerName. - * @param computerName The computerName to set - */ - public void setComputerName(String computerName) { - this.computerName = computerName; - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSDecoratorEnablementListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSDecoratorEnablementListener.java deleted file mode 100644 index 935cc0d25..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSDecoratorEnablementListener.java +++ /dev/null @@ -1,30 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -/** - * A decorator enablement listener is notified of changes to the enablement - * of CVS state decorators. - * <p> - * Clients may implement this interface. - * </p> - * @see CVSProviderPlugin#addDecoratorEnablementListener(ICVSDecoratorEnablementListener) - */ -public interface ICVSDecoratorEnablementListener { - /** - * Called when CVS decoration is enabled or disabled. Implementers can use the - * decorator enablement change as a chance to create or destroy cached CVS information - * that would help decorate CVS elements. - * - * @param enabled a flag indicating the enablement state of the decorators. - */ - void decoratorEnablementChanged(boolean enabled); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFile.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFile.java deleted file mode 100644 index 4abc9c0cf..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFile.java +++ /dev/null @@ -1,208 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.io.InputStream; -import java.util.Date; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * The CVS analog of a file. CVS files have access to synchronization information - * that describes their association with the CVS repository. CVS files also provide - * mechanisms for sending and receiving content. - * - * @see ICVSResource - */ -public interface ICVSFile extends ICVSResource { - - // Constants used to indicate the type of updated response from the server - public static final int UPDATED = 1; - public static final int MERGED = 2; - public static final int UPDATE_EXISTING = 3; - public static final int CREATED = 4; - - // Constants used to indicate temporary watches - public static final int NO_NOTIFICATION = 0; - public static final int NOTIFY_ON_EDIT = 1; - public static final int NOTIFY_ON_UNEDIT = 2; - public static final int NOTIFY_ON_COMMIT = 4; - public static final int NOTIFY_ON_ALL = NOTIFY_ON_EDIT | NOTIFY_ON_UNEDIT | NOTIFY_ON_COMMIT; - - // Constants used to indicate modification state when setting sync info - public static final int UNKNOWN = 0; - public static final int CLEAN = 1; - public static final int DIRTY = 2; - - /** - * Answers the size of the file. - */ - long getSize(); - - /** - * Gets an input stream for reading from the file. - * It is the responsibility of the caller to close the stream when finished. - */ - InputStream getContents() throws CVSException; - - /** - * Set the contents of the file to the contents of the provided input stream. - * - * This method is used by the command framework and should not be used by other clients. - * Other clients should set the contents of the underlying <code>IFile</code> which - * can be obtained using <code>getIResource()</code>. - * - * @param responseType the type of reponse that was received from the server - * - * UPDATED - could be a new file or an existing file - * MERGED - merging remote changes with local changes. Failure could result in loss of local changes - * CREATED - contents for a file that doesn't exist locally - * UPDATE_EXISTING - Replacing a local file with no local changes with remote changes. - */ - public void setContents(InputStream stream, int responseType, boolean keepLocalHistory, IProgressMonitor monitor) throws CVSException; - - /** - * Answers the workspace synchronization information for this resource. This would - * typically include information from the <b>Entries</b> file that is used to track - * the base revisions of local CVS resources. - * - * @return the synchronization information for this resource, or <code>null</code> - * if the resource does not have synchronization information available. - */ - public byte[] getSyncBytes() throws CVSException; - - /** - * Called to set the workspace synchronization information for a resource. To - * clear sync information call <code>unmanage</code>. The sync info will - * become the persisted between workbench sessions. - * - * Note: This method makes use of a ResourceSyncInfo object which has the parsed - * contents of the resource sync info. Clients can manipulate the values using - * MutableResourceSyncInfo and then set the sync info using this method. - * - * @param info the resource synchronization to associate with this resource. - */ - public void setSyncInfo(ResourceSyncInfo info, int modificationState) throws CVSException; - - /** - * Called to set the workspace synchronization information for a resource. To - * clear sync information call <code>unmanage</code>. The sync info will - * become the persisted between workbench sessions. - * - * Note: This method sets the sync info to the bytes provided as-is. It is the caller's - * responsibility to ensure that these bytes are of the proper format. Use with caution. - * - * @param info the resource synchronization to associate with this resource. - */ - public void setSyncBytes(byte[] syncBytes, int modificationState) throws CVSException; - - /** - * Sets the file to read-only (<code>true</code>) or writable (<code>false</code>). - * - * This method is used by the command framework and should not be used by other clients. - * Other clients should use <code>edit</code> and <code>unedit</code> instead as they - * will report the change to the server if appropriate. - */ - void setReadOnly(boolean readOnly) throws CVSException; - - /** - * Answers whether the file is read-only or not. If a file is read-only, <code>edit</code> - * should be invoked to make the file editable. - */ - boolean isReadOnly() throws CVSException; - - /** - * Copy the resource to another file in the same directory - * - * This method is used by the command framework and should not be used by other clients. - */ - void copyTo(String filename) throws CVSException; - - /** - * Answers the current timestamp for this file with second precision. - * - * This method is used by the command framework and should not be used by other clients. - */ - Date getTimeStamp(); - - /** - * If the date is <code>null</code> then the current time is used. - * - * This method is used by the command framework and should not be used by other clients. - */ - void setTimeStamp(Date date) throws CVSException; - - /** - * Answers <code>true</code> if the file has changed since it was last updated - * from the repository, if the file does not exist, or is not managed. And <code>false</code> - * if it has not changed. - */ - boolean isModified(IProgressMonitor monitor) throws CVSException; - - /** - * Answers the revision history for this file. This is similar to the - * output of the log command. - */ - public ILogEntry[] getLogEntries(IProgressMonitor monitor) throws TeamException; - - /** - * Mark the file as checked out to allow local editing (analogous to "cvs edit"). - * If this method is invoked when <code>isCheckedOut()</code> returns <code>false</code>, - * a notification message that will be sent to the server on the next connection - * If <code>isCheckedOut()</code> returns <code>true</code> then nothing is done. - * - * @param notifications the set of operations for which the local user would like notification - * while the local file is being edited. - */ - public void edit(int notifications, IProgressMonitor monitor) throws CVSException; - - /** - * Undo a checkout of the file (analogous to "cvs unedit"). - * If this method is invoked when <code>isCheckedOut()</code> returns <code>true</code>, - * a notification message that will be sent to the server on the next connection - * If <code>isCheckedOut()</code> returns <code>false</code> then nothing is done. - */ - public void unedit(IProgressMonitor monitor) throws CVSException; - - /** - * This method is invoked by the checked-in handler after the file - * has been committed. - */ - public void checkedIn(String entryLine) throws CVSException; - - /** - * Answer any pending notification information associated with the receiver. - * - * This method is used by the command framework and should not be used by other clients. - */ - public NotifyInfo getPendingNotification() throws CVSException; - - /** - * Indicate to the file that the pending notification was successfully communicated to the server. - * - * This method is used by the command framework and should not be used by other clients. - */ - public void notificationCompleted() throws CVSException; - - /** - * Indicate whether the file has been "cvs edit"ed. This is determined by - * looking in the CVS/Base folder for a file of the same name as the - * file (i.e. no files are read so the method can be called by time critical - * code like menu enablement). - * - * @return boolean - */ - public boolean isEdited() throws CVSException; - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFileModificationValidator.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFileModificationValidator.java deleted file mode 100644 index a45887e9b..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFileModificationValidator.java +++ /dev/null @@ -1,30 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFileModificationValidator; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; - -/** - * @author Administrator - * - * To change this generated comment edit the template variable "typecomment": - * Window>Preferences>Java>Templates. - * To enable and disable the creation of type comments go to - * Window>Preferences>Java>Code Generation. - */ -public interface ICVSFileModificationValidator extends IFileModificationValidator { - - public IStatus validateMoveDelete(IFile[] files, IProgressMonitor monitor); - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFolder.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFolder.java deleted file mode 100644 index b636adc78..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSFolder.java +++ /dev/null @@ -1,181 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; - -/** - * The CVS analog of a directory. CVS folders have access to synchronization information - * that describes the association between the folder and the remote repository. - * - * @see ICVSResource - * @see ICVSFile - */ -public interface ICVSFolder extends ICVSResource { - - public static final int FILE_MEMBERS = 1; - public static final int FOLDER_MEMBERS = 2; - public static final int IGNORED_MEMBERS = 4; - public static final int UNMANAGED_MEMBERS = 8; - public static final int MANAGED_MEMBERS = 16; - public static final int EXISTING_MEMBERS = 32; - public static final int PHANTOM_MEMBERS = 64; - public static final int ALL_MEMBERS = FILE_MEMBERS - | FOLDER_MEMBERS - | IGNORED_MEMBERS - | UNMANAGED_MEMBERS - | MANAGED_MEMBERS - | EXISTING_MEMBERS - | PHANTOM_MEMBERS; - public static final int ALL_EXISTING_MEMBERS = FILE_MEMBERS - | FOLDER_MEMBERS - | IGNORED_MEMBERS - | UNMANAGED_MEMBERS - | MANAGED_MEMBERS - | EXISTING_MEMBERS; - public static final int ALL_UNIGNORED_MEMBERS = FILE_MEMBERS - | FOLDER_MEMBERS - | UNMANAGED_MEMBERS - | MANAGED_MEMBERS - | EXISTING_MEMBERS - | PHANTOM_MEMBERS; - - /** - * Answers and array of <code>ICVSResource</code> elements that are immediate - * children of this remote resource, in no particular order. The server may be contacted. - * - * @param monitor a progress monitor to indicate the duration of the operation, or - * <code>null</code> if progress reporting is not required. - * - * @return array of immediate children of this remote resource. - */ - public ICVSResource[] fetchChildren(IProgressMonitor monitor) throws CVSException; - - /** - * Answer the immediate children of the resource that are known - * at the time of invocation. The server is never contacted. - * The flags indicate the type of members to be included. - * Here are the rules for specifying just one flag: - * - * a) FILE_MEMBERS and FOLDER_MEMBERS will return managed - * and unmanaged resource of the corresponding type - * b) IGNORED_MEMBERS, MANAGED_RESOURCES and UNMANAGED_RESOURCES - * will return files and folders of the given type - * c) EXISTING_MEMBERS and PHANTOM_MEMBERS will return existing - * and phatom resource of the corresponding type - * - * Note: Unmanaged resources are those that are neither managed or ignored. - * - * If all of the flags from either group a), group b) or group c) - * are not present, the same rule for default types applies. - * For example, - * - FILE_MEMBERS | FOLDER_MEMBERS will return all managed - * and unmanaged, existing and phantom files and folders. - * - IGNORED_MEMBERS | UNMANAGED_MEMBERS will return all - * ignored or unmanaged, existing or phantom files and folders - * If a flag from each group is present, the result is the - * union of the sets. For example, - * - FILE_MEMBERS | IGNORED_MEMBERS | EXISTING_MEMBERS will return all - * existing ignored files. - */ - public ICVSResource[] members(int flags) throws CVSException; - - /** - * Answers a child folder of this resource with the given name or <code>null</code> if - * the given folder does not have a child with that name. - */ - public ICVSFolder getFolder(String name) throws CVSException; - - /** - * Answers a child file of this resource with the given name or <code>null</code> if - * the given folder does not have a child with that name. - */ - public ICVSFile getFile(String name) throws CVSException; - - /** - * Return the child resource at the given path relative to - * the receiver. - */ - public ICVSResource getChild(String path) throws CVSException; - - /** - * Create the folder if it did not exist before. Does only - * work if the direct subfolder did exist. - * - * @throws CVSException if for some reason it was not possible to create the folder - */ - public void mkdir() throws CVSException; - - /** - * Answers the folder's synchronization information or <code>null</code> if the folder - * is not a CVS folder. - * <p> - * To modify the folder sync info the caller must call <code>setFolderSyncInfo</code> with - * new sync information.</p> - */ - public FolderSyncInfo getFolderSyncInfo() throws CVSException; - - /** - * Set the folder sync information for this folder. Setting the folder information - * to <code>null</code> is not supported. The only mechanism for removing an existing - * CVS folder is to delete the resource. - */ - public void setFolderSyncInfo(FolderSyncInfo folderInfo) throws CVSException; - - /** - * Accepts the visitor on all files and all subFolder in the folder. Files are - * visited first, then all the folders.. - */ - public void acceptChildren(ICVSResourceVisitor visitor) throws CVSException; - - /** - * Answers <code>true</code> if the folder has valid CVS synchronization information and - * <code>false</code> otherwise. - * - * Note: This method does not throw an exception so this method does not differentiate - * between a folder not be shared with CVS and a folder that is shared but whose sync info has - * become corrupt. Use getFolderSyncInfo() to differentiate between these situations. - * - * Also Note: A folder that is a CVS folder may not exist in the workspace. The purpose of - * such a folder is to act as a remotely existing folder that does not exist locally. - * This is normally done in order to remember outgoing file deletions when a parent - * folder is deleted. - * Creating the folder will result in a folder that is mapped to a remote folder. - */ - public boolean isCVSFolder() throws CVSException; - - /** - * Runs the given action as an atomic cvs local workspace operation - * rooted at this cvs folder. - * <p> - * After running a method that modifies cvs resource state in the - * local workspace, registered listeners receive after-the-fact - * notification in the form of a resource state change event. In addition, - * any resource state information persistance is batched. - * This method allows clients to call a number of - * methods that modify resources and only have resource - * change event notifications reported at the end of the entire - * batch. - * </p> - * <p> - * If this method is called in the dynamic scope of another such - * call, this method simply runs the action. - * </p> - * - * @param job the action to perform - * @param monitor a progress monitor, or <code>null</code> if progress - * reporting and cancellation are not desired - * @exception CVSException if the operation failed. - */ - public void run(ICVSRunnable job, IProgressMonitor monitor) throws CVSException; -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSListener.java deleted file mode 100644 index 7bde4aed5..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSListener.java +++ /dev/null @@ -1,19 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - - -public interface ICVSListener { - public void repositoryAdded(ICVSRepositoryLocation root); - public void repositoryRemoved(ICVSRepositoryLocation root); -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteFile.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteFile.java deleted file mode 100644 index fd0e29abc..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteFile.java +++ /dev/null @@ -1,48 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.TeamException; - - /** - * This interface represents a file in a repository. - * Instances of this interface can be used to fetch the contents - * of the remote file. - * - * In the future, additional information should be available (tags, revisions, etc.) - * - * Clients are not expected to implement this interface. - */ -public interface ICVSRemoteFile extends ICVSRemoteResource, ICVSFile { - - /** - * Get the log entry for the revision the remote file represents. - * This method will return null until after the getContents(IProgressMonitor) - * method is called (i.e. the call to getContents also fetches the entry. - */ - public ILogEntry getLogEntry(IProgressMonitor monitor) throws TeamException; - - /** - * Get all the log entries of the remote file - */ - public ILogEntry[] getLogEntries(IProgressMonitor monitor) throws TeamException; - - /** - * Get the revision of the remote file (e.g. 1.1) - * - * The revision depends on any tagging associated with the remote parent used - * to access the file. - */ - public String getRevision() throws TeamException; -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteFolder.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteFolder.java deleted file mode 100644 index 39950f6c5..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteFolder.java +++ /dev/null @@ -1,54 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; - - /** - * This interface represents a remote folder in a repository. It provides - * access to the members (remote files and folders) of a remote folder - * - * Clients are not expected to implement this interface. - */ -public interface ICVSRemoteFolder extends ICVSRemoteResource, ICVSFolder { - - /** - * Return the context of this handle. The returned tag can be a branch or - * version tag. - */ - public CVSTag getTag(); - - /** - * Return the local options that are used to determine how memebers are retrieved. - * - * Interesting options are: - * Checkout.ALIAS - * Command.DO_NOT_RECURSE - */ - public LocalOption[] getLocalOptions(); - - /** - * Indicates whether the remote folder can be expanded. - * - * This is a temporary (hopefully) means of indicating certain types of folders - * (i.e. module definitions) that are not expandable due to lack of mdoule expansion. - * They can still be checked out. - */ - public boolean isExpandable(); - - /** - * Indicates whether the remote folder is an actual remote folder is a - * module defined in the CVSROOT/modules file (or some other module - * definition). - */ - public boolean isDefinedModule(); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteResource.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteResource.java deleted file mode 100644 index c69a64eff..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRemoteResource.java +++ /dev/null @@ -1,75 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; - -/** - * The interface represents a resource that exists in a CVS repository. - * It purpose is to provide information about the remote resource from - * the repository. - * - * Clients are not expected to implement this interface. - */ -public interface ICVSRemoteResource extends IRemoteResource, ICVSResource { - - /** - * Return the repository - */ - public ICVSRepositoryLocation getRepository(); - - /** - * Returns the parent of this remote resource or <code>null</code> if the - * remote resource does not have a parent. - */ - public ICVSRemoteResource getRemoteParent(); - - /** - * Does the remote resource represented by this handle exist on the server. This - * method may contact the server and be long running. - */ - public boolean exists(IProgressMonitor monitor) throws TeamException; - - /** - * Answers the repository relative path of this remote folder. - */ - public String getRepositoryRelativePath(); - - /** - * Compares two objects for equality; for cvs remote resources, equality is defined in - * terms of their handles: same cvs resource type, equal relative paths, and - * for files, identical revision numbers. Remote resources are not equal to objects other - * than cvs remote resources. - * - * @param other the other object - * @return an indication of whether the objects are equals - */ - public boolean equals(Object other); - - /** - * Allows a client to change the context of a remote resource handle. For - * example, if a remote resource was created with the HEAD context (e.g. can - * be used to browse the main branch) use this method to change the - * context to another branch tag or to a version tag. - */ - public ICVSRemoteResource forTag(CVSTag tagName); - - /** - * Tag the remote resources referenced by the receiver (using rtag) - */ - public IStatus tag(CVSTag tag, LocalOption[] localOptions, IProgressMonitor monitor) throws CVSException; - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRepositoryLocation.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRepositoryLocation.java deleted file mode 100644 index b849b2158..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRepositoryLocation.java +++ /dev/null @@ -1,113 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.runtime.IAdaptable; -import org.eclipse.core.runtime.IProgressMonitor; - -/** - * This interface provides access to the specific portions of - * the repository location string for use by connection methods - * and the user authenticator. - * - * It is not intended to implemented by clients. - * - * @see IUserAuthenticator - * @see IConnectionMethod - */ -public interface ICVSRepositoryLocation extends IAdaptable { - - /** - * port value which indicates to a connection method to use the default port - */ - public static int USE_DEFAULT_PORT = 0; - - /** - * Return the connection method for making the connection - */ - public IConnectionMethod getMethod(); - - /** - * Returns the host where the repository is located - */ - public String getHost(); - - /** - * Returns the port to connect to or USE_DEFAULT_PORT if - * the connection method is to use its default port. - */ - public int getPort(); - - /** - * Returns the root directory of the repository. - */ - public String getRootDirectory(); - - /** - * Returns the string representing the receiver. This string - * should contain enough information to recreate the receiver. - */ - public String getLocation(); - - /** - * Returns the immediate children of this location. If tag is <code>null</code> the - * HEAD branch is assumed. - * - * If modules is true, then the module definitions from the CVSROOT/modules file are returned. - * Otherwise, the root level projects are returned. - * - * @param tag the context in which to return the members (e.g. branch or version). - */ - public ICVSRemoteResource[] members(CVSTag tag, boolean modules, IProgressMonitor progress) throws CVSException; - - /** - * Returns a handle to a remote file at this repository location using the given tag as the - * context. The corresponding remote file may not exist or may be a folder. - */ - public ICVSRemoteFile getRemoteFile(String remotePath, CVSTag tag); - - /** - * Returns a handle to a remote folder at this repository location using the given tag as the - * context. The corresponding remote folder may not exist or may be a file. - */ - public ICVSRemoteFolder getRemoteFolder(String remotePath, CVSTag tag); - - /** - * Return the conection timeout value in milliseconds. - * A value of 0 means there is no timeout value. - */ - public int getTimeout(); - - /** - * Return the username - */ - public String getUsername(); - - /** - * Returns the user information for the location. - */ - public IUserInfo getUserInfo(boolean allowModificationOfUsername); - - /** - * Flush any cahced user information related to the repository location - */ - public void flushUserInfo() throws CVSException; - - /** - * Validate that the receiver can be used to connect to a repository. - * An exception is thrown if connection fails - * - * @param monitor the progress monitor used while validating - */ - public void validateConnection(IProgressMonitor monitor) throws CVSException; -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSResource.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSResource.java deleted file mode 100644 index 9ec8465e5..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSResource.java +++ /dev/null @@ -1,167 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * The CVS analog of file system files and directories. These are handles to - * state maintained by a CVS client. That is, the CVS resource does not - * actually contain data but rather represents CVS state and behavior. You are - * free to manipulate handles for CVS resources that do not exist but be aware - * that some methods require that an actual resource be available. - * <p> - * The CVS client has been designed to work on these handles uniquely. As such, the - * handle could be to a remote resource or a local resource and the client could - * perform CVS operations ignoring the actual location of the resources.</p> - * - * @see ICVSFolder - * @see ICVSFile - */ -public interface ICVSResource { - - /** - * Answers the name of the resource. - * - * @return the name of the resource this handle represents. It can never - * be <code>null</code>. - */ - public String getName(); - - /** - * Answers if this resource has CVS synchronization information associated - * with it. - * - * @return <code>true</code> if the resource is - */ - public boolean isManaged() throws CVSException; - - /** - * Unmanage the given resource by purging any CVS synchronization associated with the - * resource. The only way a resource can become managed is by running the - * appropriate CVS commands (e.g. add/commit/update). - */ - public void unmanage(IProgressMonitor monitor) throws CVSException; - - /** - * Answer whether the resource could be ignored because it is in the one of the - * ignore lists maintained by CVS. Even if a resource is ignored, it can still be - * added to a repository, at which time it should never be ignored by the CVS - * client. - * - * @return <code>true</code> if this resource is listed in one of the ignore - * files maintained by CVS and <code>false</code> otherwise. - */ - public boolean isIgnored() throws CVSException; - - /** - * Add the following file to the parent's ignore list - */ - public void setIgnored() throws CVSException; - - /** - * Add the following pattern to the file's parent ignore list - * - * XXX This should really be a method of ICVSFolder - */ - public void setIgnoredAs(String pattern) throws CVSException; - - /** - * Answers if the handle is a file or a folder handle. - * - * @return <code>true</code> if this is a folder handle and <code>false</code> if - * it is a file handle. - */ - public boolean isFolder(); - - /** - * Answers if the resource identified by this handle exists. - * - * @return <code>true</code> if the resource represented by this handle - * exists and <code>false</code> false otherwise. - */ - public boolean exists() throws CVSException; - - /** - * Answers the underlying IResource for the cvs resource (or null if there - * is not a corresponding local resource). - * - * @return the IResource that corresponds to the CVS resource - */ - public IResource getIResource() throws CVSException; - - /** - * Answers the local relative path from the given ancestor to the receiver. - * - * @return the ancestor relative path for this resource. - */ - public String getRelativePath(ICVSFolder ancestor) throws CVSException; - - /** - * Get the absolute remote location of a resource. This method is used by - * the CVS command infrastructure during command execution. The root is used - * in situations where the resource is not under CVS control. The remote - * path that the resource would have if it was is determined by recursively - * searching the resource's parent until a managed folder is found. The - * provided root is used to stop the recursive search if no managed parent - * is found. - * - * @param root the root folder of the command. - * - * @return the remote location. - */ - public String getRemoteLocation(ICVSFolder root) throws CVSException; - - /** - * Answers the workspace synchronization information for this resource. This would - * typically include information from the <b>Entries</b> file that is used to track - * the base revisions of local CVS resources. - * - * @return the synchronization information for this resource, or <code>null</code> - * if the resource does not have synchronization information available. - */ - public ResourceSyncInfo getSyncInfo() throws CVSException; - - /** - * Deletes the resource represented by the handle. - */ - public void delete() throws CVSException; - - /** - * Give the folder that contains this resource. If the resource is not managed - * then the result of the operation is not specified. - * - * @return a handle to the parent of this resource. - */ - public ICVSFolder getParent(); - - /** - * Accept a vistor to this resource. - */ - public void accept(ICVSResourceVisitor visitor) throws CVSException; - - /** - * Accept a visitor to this resource. The recurse parameter corresponds to the CVS - * -l (do not recurse) and -R (recurse) options. If recurse is false, only the resource - * and it's children are visited. Otherwise, the resource and all it's decendants are - * visited. - */ - public void accept(ICVSResourceVisitor visitor, boolean recurse) throws CVSException; - - /** - * Method isModified. - * @return boolean - */ - public boolean isModified(IProgressMonitor monitor) throws CVSException; -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSResourceVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSResourceVisitor.java deleted file mode 100644 index 28cc5cd29..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSResourceVisitor.java +++ /dev/null @@ -1,23 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - - - -/** - * Interface for an visitor of the IManagedResources. - */ -public interface ICVSResourceVisitor { - public void visitFile(ICVSFile file) throws CVSException; - public void visitFolder(ICVSFolder folder) throws CVSException; -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRunnable.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRunnable.java deleted file mode 100644 index 378147b8a..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ICVSRunnable.java +++ /dev/null @@ -1,42 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import org.eclipse.core.runtime.IProgressMonitor; - -/** - * A runnable which executes as a batch operation within a specific cvs local - * workspace. - * The <code>ICVSRunnable</code> interface should be implemented by any class whose - * instances are intended to be run by <code>IWorkspace.run</code>. - * <p> - * Clients may implement this interface. - * </p> - * @see - */ -public interface ICVSRunnable { - /** - * Runs the operation reporting progress to and accepting - * cancellation requests from the given progress monitor. - * <p> - * Implementors of this method should check the progress monitor - * for cancellation when it is safe and appropriate to do so. The cancellation - * request should be propagated to the caller by throwing - * <code>OperationCanceledException</code>. - * </p> - * - * @param monitor a progress monitor, or <code>null</code> if progress - * reporting and cancellation are not desired - * @exception CoreException if this operation fails. - */ - public void run(IProgressMonitor monitor) throws CVSException; -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IConnectionMethod.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IConnectionMethod.java deleted file mode 100644 index 6bb199784..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IConnectionMethod.java +++ /dev/null @@ -1,51 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -/** - * Implementators of this class can act as factories for creating connections to a CVS server - * with the desired custom communication protocol. Providers of CVS connection methods must implement - * this interface and register the implementation with the extension point: - * - * org.eclipse.team.cvs.core.connectionmethods - * - * The <code>createConnection()</code> method will be invoked by the CVS client when the user - * is attempting to make a connection to the server using the connection name which matches - * the <code>String</code> returned by <code>getName()</code> (e.g. "pserver", "ext", etc.). - */ -public interface IConnectionMethod { - - /** - * Returns the name of this connection method (e.g."local", "ext"). - */ - public String getName(); - - /** - * Creates a new server connection using the given repository root - * (which includes the user name) and the given password. - */ - public IServerConnection createConnection(ICVSRepositoryLocation location, String password); - - /** - * Some connection method may persist the physical connection to the server - * through several IServerConnections. For example, when making several - * successive connections to the same location using SSH2, it would be very - * expensive to re-connect, re-negotiate and re-authenticate for each - * operation; therefore the SSH2 connection method will create one SSH - * session and open several channels (one for each IServerConnection - * created), and keep the session open until disconnect() is called. - * <p> - * This method actually closes any connection to the indicated location. - * </p> - */ - public void disconnect(ICVSRepositoryLocation location); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ILogEntry.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ILogEntry.java deleted file mode 100644 index 339c51476..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/ILogEntry.java +++ /dev/null @@ -1,66 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import java.util.Date; - -import org.eclipse.core.runtime.IAdaptable; - -/** - * Instances of ILogEntry represent an entry for a CVS file that results - * from the cvs log command. - * - * Clients are not expected to implement this interface - */ -public interface ILogEntry extends IAdaptable { - - /** - * Get the revision for the entry - */ - public String getRevision(); - - /** - * Get the author of the revision - */ - public String getAuthor(); - - /** - * Get the date the revision was committed - */ - public Date getDate(); - - /** - * Get the comment for the revision - */ - public String getComment(); - - /** - * Get the state - */ - public String getState(); - - /** - * Get the tags associated with the revision - */ - public CVSTag[] getTags(); - - /** - * Get the remote file for this entry - */ - public ICVSRemoteFile getRemoteFile(); - - /** - * Does the log entry represent a deletion (stat = "dead") - */ - public boolean isDeletion(); -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IResourceStateChangeListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IResourceStateChangeListener.java deleted file mode 100644 index 619c9b0fc..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IResourceStateChangeListener.java +++ /dev/null @@ -1,86 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import java.util.EventListener; - -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; - -/** - * A resource state change listener is notified of changes to resources - * regarding their team state. - * <p> - * Clients may implement this interface. - * </p> - * @see ITeamManager#addResourceStateChangeListener(IResourceStateChangeListener) - */ -public interface IResourceStateChangeListener extends EventListener{ - - /** - * Notifies this listener that some resource sync info state changes have - * already happened. For example, a resource's base revision may have - * changed. The resource tree is open for modification when this method is - * invoked, so markers can be created, etc. - * <p> - * Note: This method is called by the CVS core; it is not intended to be - * called directly by clients. - * </p> - * - * @param changedResources that have sync info state changes - * - * [Note: The changed state event is purposely vague. For now it is only - * a hint to listeners that they should query the provider to determine the - * resources new sync info.] - */ - public void resourceSyncInfoChanged(IResource[] changedResources); - - /** - * Notifies this listener that the resource's have been modified. This - * doesn't necessarily mean that the resource state isModified. The listener - * must check the state. - * <p> - * Note: This method is called by CVS team core; it is not intended to be - * called directly by clients. - * </p> - * - * @param changedResources that have changed state - * @param changeType the type of state change. - */ - public void resourceModified(IResource[] changedResources); - - /** - * Notifies this listener that the project has just been configured - * to be a CVS project. - * <p> - * Note: This method is called by the CVS core; it is not intended to be - * called directly by clients. - * </p> - * - * @param project The project that has just been configured - */ - public void projectConfigured(IProject project); - - /** - * Notifies this listener that the project has just been deconfigured - * and no longer has the CVS nature. - * <p> - * Note: This method is called by the CVS core; it is not intended to be - * called directly by clients. - * </p> - * - * @param project The project that has just been configured - */ - public void projectDeconfigured(IProject project); - -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IServerConnection.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IServerConnection.java deleted file mode 100644 index 7ecfc3055..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IServerConnection.java +++ /dev/null @@ -1,48 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.connection.CVSAuthenticationException; -/** -* CVS supports different connection methods for communicating between a client and the server. -* Furthermore, custom connection methods can be added. Connection methods are added -* to the CVS client as an IConnectionMethod, which can be used to create connections of -* type IServerConnection. -* -* @see IConnectionMethod -*/ -public interface IServerConnection { - /** - * Open a connection to the CVS server. - * - * Throw CVSAuthenticationException if the username or password is invalid. - * Throw IOExceptions for other failures. - */ - public void open(IProgressMonitor monitor) throws IOException, CVSAuthenticationException; - /** - * Close the connection - * - * Throw IOException on failures - */ - public void close() throws IOException; - /** - * Get the input stream to receive responses from the server - */ - public InputStream getInputStream(); - /** - * Get the output stream to send requests to the server - */ - public OutputStream getOutputStream(); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IUserAuthenticator.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IUserAuthenticator.java deleted file mode 100644 index 0182e6136..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IUserAuthenticator.java +++ /dev/null @@ -1,38 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - - - -/** - * IUserAuthenticators are used to ensure that the user - * is validated for access to a given repository. The - * user is prompted for a username and password as - * appropriate for the given repository type. - */ -public interface IUserAuthenticator { - /** - * Authenticates the user for access to a given repository. - * The obtained values for user name and password will be placed - * into the supplied user info object. Implementors are allowed to - * save user names and passwords. The user should be prompted for - * user name and password if there is no saved one, or if <code>retry</code> - * is <code>true</code>. - * - * @param location The repository location to authenticate the user for. - * @param info The object to place user validation information into. - * @param retry <code>true</code> if a previous attempt to log in failed. - * @param message An optional message to display if, e.g., previous authentication failed. - * @return true if the validation was successful, and false otherwise. - */ - public void promptForUserInfo(ICVSRepositoryLocation location, IUserInfo userInfo, String message) throws CVSException; -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IUserInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IUserInfo.java deleted file mode 100644 index be8a9f26e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/IUserInfo.java +++ /dev/null @@ -1,40 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -/** - * Instances of this class represent a username password pair. - * Both values can be set and the username can be retrieved. - * However, it is possible that the username is not mutable. - * Users must check before trying to set the username. - * - * Clients are not expected to implement this interface - */ -public interface IUserInfo { - /** - * Get the username for this user. - */ - public String getUsername(); - /** - * Return true if the username is mutable. If not, setUsername should not be called. - */ - public boolean isUsernameMutable(); - /** - * Sets the password for this user. - */ - public void setPassword(String password); - /** - * Sets the username for this user. This should not be called if - * isUsernameMutable() returns false. - */ - public void setUsername(String username); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/Policy.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/Policy.java deleted file mode 100644 index 8691fe188..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/Policy.java +++ /dev/null @@ -1,130 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core; - - -import java.text.MessageFormat; -import java.util.MissingResourceException; -import java.util.ResourceBundle; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.NullProgressMonitor; -import org.eclipse.core.runtime.OperationCanceledException; -import org.eclipse.core.runtime.Platform; -import org.eclipse.core.runtime.SubProgressMonitor; -import org.eclipse.team.internal.core.InfiniteSubProgressMonitor; - -public class Policy { - protected static ResourceBundle bundle = null; - - //debug constants - public static boolean DEBUG_METAFILE_CHANGES = false; - public static boolean DEBUG_CVS_PROTOCOL = false; - public static boolean DEBUG_THREADING = false; - public static boolean DEBUG_DIRTY_CACHING = false; - - static { - //init debug options - if (CVSProviderPlugin.getPlugin().isDebugging()) { - DEBUG_METAFILE_CHANGES = "true".equalsIgnoreCase(Platform.getDebugOption(CVSProviderPlugin.ID + "/metafiles"));//$NON-NLS-1$ //$NON-NLS-2$ - DEBUG_CVS_PROTOCOL = "true".equalsIgnoreCase(Platform.getDebugOption(CVSProviderPlugin.ID + "/cvsprotocol"));//$NON-NLS-1$ //$NON-NLS-2$ - DEBUG_THREADING = "true".equalsIgnoreCase(Platform.getDebugOption(CVSProviderPlugin.ID + "/threading"));//$NON-NLS-1$ //$NON-NLS-2$ - DEBUG_DIRTY_CACHING = "true".equalsIgnoreCase(Platform.getDebugOption(CVSProviderPlugin.ID + "/dirtycaching"));//$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /** - * Creates a NLS catalog for the given locale. - */ - public static void localize(String bundleName) { - bundle = ResourceBundle.getBundle(bundleName); - } - - /** - * Lookup the message with the given ID in this catalog and bind its - * substitution locations with the given string. - */ - public static String bind(String id, String binding) { - return bind(id, new String[] { binding }); - } - - /** - * Lookup the message with the given ID in this catalog and bind its - * substitution locations with the given strings. - */ - public static String bind(String id, String binding1, String binding2) { - return bind(id, new String[] { binding1, binding2 }); - } - - /** - * Gets a string from the resource bundle. We don't want to crash because of a missing String. - * Returns the key if not found. - */ - public static String bind(String key) { - try { - return bundle.getString(key); - } catch (MissingResourceException e) { - return key; - } catch (NullPointerException e) { - return "!" + key + "!"; //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /** - * Gets a string from the resource bundle and binds it with the given arguments. If the key is - * not found, return the key. - */ - public static String bind(String key, Object[] args) { - try { - return MessageFormat.format(bind(key), args); - } catch (MissingResourceException e) { - return key; - } catch (NullPointerException e) { - return "!" + key + "!"; //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /** - * Progress monitor helpers - */ - public static void checkCanceled(IProgressMonitor monitor) { - if (monitor.isCanceled()) - throw new OperationCanceledException(); - } - public static IProgressMonitor monitorFor(IProgressMonitor monitor) { - if (monitor == null) - return new NullProgressMonitor(); - return monitor; - } - - public static IProgressMonitor subMonitorFor(IProgressMonitor monitor, int ticks) { - if (monitor == null) - return new NullProgressMonitor(); - if (monitor instanceof NullProgressMonitor) - return monitor; - return new SubProgressMonitor(monitor, ticks); - } - public static IProgressMonitor subMonitorFor(IProgressMonitor monitor, int ticks, int style) { - if (monitor == null) - return new NullProgressMonitor(); - if (monitor instanceof NullProgressMonitor) - return monitor; - return new SubProgressMonitor(monitor, ticks, style); - } - - public static IProgressMonitor infiniteSubMonitorFor(IProgressMonitor monitor, int ticks) { - if (monitor == null) - return new NullProgressMonitor(); - if (monitor instanceof NullProgressMonitor) - return monitor; - return new InfiniteSubProgressMonitor(monitor, ticks); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AbstractMessageCommand.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AbstractMessageCommand.java deleted file mode 100644 index 3cfd0472d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AbstractMessageCommand.java +++ /dev/null @@ -1,36 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -/** - * Superclass for commands that do not change the structure on - * the local working copy (it can change the content of the files).<br> - * Most of the subclasses are asking the server for response in - * message format (log, status) - */ -abstract class AbstractMessageCommand extends Command { - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Send all folders that are already managed to the server - new FileStructureVisitor(session, false, false, monitor).visit(session, resources); - return resources; - } - -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AbstractStructureVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AbstractStructureVisitor.java deleted file mode 100644 index c3693a804..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AbstractStructureVisitor.java +++ /dev/null @@ -1,249 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collections; -import java.util.Comparator; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSEntryLineTag; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * An ICVSResourceVisitor that is superclass to all ICVSResourceVisitor's used - * by Command and it's subclasses. - * Provides helper methods to send files and folders with modifications - * to the server. - */ -abstract class AbstractStructureVisitor implements ICVSResourceVisitor { - - protected Session session; - private ICVSFolder lastFolderSent; - protected IProgressMonitor monitor; - protected boolean sendQuestionable; - protected boolean sendModifiedContents; - private boolean sendBinary; - - public AbstractStructureVisitor(Session session, boolean sendQuestionable, boolean sendModifiedContents, IProgressMonitor monitor) { - this(session, sendQuestionable, sendModifiedContents, true, monitor); - } - - public AbstractStructureVisitor(Session session, boolean sendQuestionable, boolean sendModifiedContents, boolean sendBinary, IProgressMonitor monitor) { - this.session = session; - this.sendQuestionable = sendQuestionable; - this.sendModifiedContents = sendModifiedContents; - this.sendBinary = sendBinary; - this.monitor = Policy.infiniteSubMonitorFor(monitor, 256); - } - - /** - * Helper method to indicate if a directory has already been sent to the server - */ - protected boolean isLastSent(ICVSFolder folder) { - return folder.equals(lastFolderSent); - } - - /** - * Helper method to record if a directory has already been sent to the server - */ - protected void recordLastSent(ICVSFolder folder) { - lastFolderSent = folder; - } - - /** - * Helper which indicates if a folder is an orphaned subtree. - * That is, a directory which contains a CVS subdirectory but is - * not managed by its parent. The root directory of the session - * is not considered orphaned even if it is not managed by its - * parent. - */ - protected boolean isOrphanedSubtree(ICVSFolder mFolder) throws CVSException { - return mFolder.isCVSFolder() && ! mFolder.isManaged() && ! mFolder.equals(session.getLocalRoot()) && mFolder.getParent().isCVSFolder(); - } - - /** - * Send the folder relative to the root to the server. Send all - * appropiate modifier like Sticky, Questionable, Static-directory. - * <br> - * Folders will only be sent once. - */ - protected void sendFolder(ICVSFolder mFolder) throws CVSException { - - Policy.checkCanceled(monitor); - - boolean exists = mFolder.exists(); - boolean isCVSFolder = mFolder.isCVSFolder(); - - // We are only interested in folders that exist or are CVS folders - // A folder could be a non-existant CVS folder if it is a holder for outgoing file deletions - if ( ! exists && ! isCVSFolder) return; - - // Do not send the same folder twice - if (isLastSent(mFolder)) return; - - String localPath = mFolder.getRelativePath(session.getLocalRoot()); - - monitor.subTask(Policy.bind("AbstractStructureVisitor.sendingFolder", Util.toTruncatedPath(mFolder, session.getLocalRoot(), 3))); //$NON-NLS-1$ - - // Deal with questionable directories - boolean isQuestionable = exists && (! isCVSFolder || isOrphanedSubtree(mFolder)); - if (isQuestionable) { - if (sendQuestionable) { - // We need to make sure the parent folder was sent - sendFolder(mFolder.getParent()); - session.sendQuestionable(mFolder); - } - return; - } - - // Send the directory to the server - String remotePath = mFolder.getRemoteLocation(session.getLocalRoot()); - if (remotePath == null) { - throw new CVSException(Policy.bind("AbstractStructureVisitor.noRemote")); //$NON-NLS-1$ - } - session.sendDirectory(localPath, remotePath); - - // Send any directory properties to the server - FolderSyncInfo info = mFolder.getFolderSyncInfo(); - if (info != null) { - - if (info.getIsStatic()) { - session.sendStaticDirectory(); - } - - CVSEntryLineTag tag = info.getTag(); - - if (tag != null && tag.getType() != CVSTag.HEAD) { - session.sendSticky(tag.toEntryLineFormat(false)); - } - } - - // Record that we sent this folder - recordLastSent(mFolder); - - monitor.worked(1); - } - - /** - * Send the information about the file to the server. - * - * If the file is modified, its contents are sent as well. - */ - protected void sendFile(ICVSFile mFile) throws CVSException { - - Policy.checkCanceled(monitor); - - // Send the parent folder if it hasn't been sent already - sendFolder(mFile.getParent()); - - // Send the file's entry line to the server - byte[] syncBytes = mFile.getSyncBytes(); - boolean isManaged = syncBytes != null; - if (isManaged) { - sendPendingNotification(mFile); - session.sendEntry(syncBytes, ResourceSyncInfo.getTimestampToServer(syncBytes, mFile.getTimeStamp())); - } else { - // If the file is not managed, send a questionable to the server if the file exists locally - // A unmanaged, locally non-existant file results from the explicit use of the file name as a command argument - if (sendQuestionable) { - if (mFile.exists()) { - session.sendQuestionable(mFile); - } - return; - } - // else we are probably doing an import so send the file contents below - } - - // If the file exists, send the appropriate indication to the server - if (mFile.exists()) { - if (mFile.isModified(null)) { - boolean binary = ResourceSyncInfo.isBinary(syncBytes); - if (sendModifiedContents) { - session.sendModified(mFile, binary, sendBinary, monitor); - } else { - session.sendIsModified(mFile, binary, monitor); - } - } else { - session.sendUnchanged(mFile); - } - } - } - - protected void sendPendingNotification(ICVSFile mFile) throws CVSException { - NotifyInfo notify = mFile.getPendingNotification(); - if (notify != null) { - sendFolder(mFile.getParent()); - session.sendNotify(mFile.getParent(), notify); - } - } - - /** - * This method is used to visit a set of ICVSResources. Using it ensures - * that a common parent between the set of resources is only sent once - */ - public void visit(Session session, ICVSResource[] resources) throws CVSException { - - // Sort the resources to avoid sending the same directory multiple times - List resourceList = new ArrayList(resources.length); - resourceList.addAll(Arrays.asList(resources)); - final ICVSFolder localRoot = session.getLocalRoot(); - Collections.sort(resourceList, new Comparator() { - public int compare(Object object1, Object object2) { - ICVSResource resource1 = (ICVSResource)object1; - ICVSResource resource2 = (ICVSResource)object2; - try { - String path1 = resource1.getParent().getRelativePath(localRoot); - String path2 = resource2.getParent().getRelativePath(localRoot); - int pathCompare = path1.compareTo(path2); - if (pathCompare == 0) { - if (resource1.isFolder() == resource2.isFolder()) { - return resource1.getName().compareTo(resource2.getName()); - } else if (resource1.isFolder()) { - return 1; - } else { - return -1; - } - } else { - return pathCompare; - } - } catch (CVSException e) { - return resource1.getName().compareTo(resource2.getName()); - } - } - }); - - // Visit all the resources - session.setSendFileTitleKey(getSendFileTitleKey()); - for (int i = 0; i < resourceList.size(); i++) { - ((ICVSResource)resourceList.get(i)).accept(this); - } - - monitor.done(); - } - - protected String getSendFileTitleKey() { - return "AbstractStructureVisitor.sendingFile"; //$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Add.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Add.java deleted file mode 100644 index 5f99078cc..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Add.java +++ /dev/null @@ -1,77 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -public class Add extends Command { - /*** Local options: specific to add ***/ - - protected Add() { } - protected String getRequestId() { - return "add"; //$NON-NLS-1$ - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Check that all the arguments can give you an - // repo that you will need while traversing the - // file-structure - for (int i = 0; i < resources.length; i++) { - Assert.isNotNull(resources[i].getRemoteLocation(session.getLocalRoot())); - } - - // Get a vistor and use it on every resource we should - // work on - AddStructureVisitor visitor = new AddStructureVisitor(session, monitor); - visitor.visit(session, resources); - return resources; - } - - /** - * If the add succeeded then folders have to be initialized with the - * sync info - */ - protected IStatus commandFinished(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor, - IStatus status) throws CVSException { - - if (status.getCode() == CVSStatus.SERVER_ERROR) { - return status; - } - - for (int i = 0; i < resources.length; i++) { - if (resources[i].isFolder()) { - ICVSFolder mFolder = (ICVSFolder) resources[i]; - FolderSyncInfo info = mFolder.getParent().getFolderSyncInfo(); - if (info == null) { - status = mergeStatus(status, new CVSStatus(CVSStatus.ERROR, Policy.bind("Add.invalidParent", mFolder.getRelativePath(session.getLocalRoot())))); //$NON-NLS-1$ - } else { - String repository = info.getRepository() + "/" + mFolder.getName(); //$NON-NLS-1$ - mFolder.setFolderSyncInfo(new FolderSyncInfo(repository, info.getRoot(), info.getTag(), info.getIsStatic())); - } - } - } - return status; - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AddStructureVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AddStructureVisitor.java deleted file mode 100644 index 23f715001..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/AddStructureVisitor.java +++ /dev/null @@ -1,65 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * This visitor is used by the Add command to ensure that the parent - * folder is sent along with the added resource. - */ -class AddStructureVisitor extends AbstractStructureVisitor { - - public AddStructureVisitor(Session session, IProgressMonitor monitor) { - super(session, false, true, monitor); - } - - /** - * @see ICVSResourceVisitor#visitFile(IManagedFile) - */ - public void visitFile(ICVSFile mFile) throws CVSException { - - // Send the parent folder - sendFolder(mFile.getParent()); - - // Sends the Is-modified request if it is supported, otherwise - // the file contents are sent as binary. The server does not - // need the contents at this stage so this should not be a problem. - session.sendIsModified(mFile, true, monitor); - - } - - /** - * @see ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder mFolder) throws CVSException { - - Assert.isNotNull(mFolder); - - // Send the parent folder - sendFolder(mFolder.getParent()); - - // Send the directory - String localPath = mFolder.getRelativePath(session.getLocalRoot()); - String remotePath = mFolder.getRemoteLocation(session.getLocalRoot()); - session.sendDirectory(localPath, remotePath); - - // Record that we sent this folder - recordLastSent(mFolder); - } - -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Admin.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Admin.java deleted file mode 100644 index f4e5dd2c6..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Admin.java +++ /dev/null @@ -1,22 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -public class Admin extends AbstractMessageCommand { - /*** Local options: specific to admin ***/ - - protected Admin() { } - protected String getRequestId() { - return "admin"; //$NON-NLS-1$ - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Annotate.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Annotate.java deleted file mode 100644 index f47b0a82d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Annotate.java +++ /dev/null @@ -1,31 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -public class Annotate extends AbstractMessageCommand { - -/** - * The CVS Annotate Command. - * Answers a resource with each line annotated with the revision the line - * was added/changed and the user making the change. - */ - - protected Annotate() { } - - protected String getRequestId() { - return "annotate"; //$NON-NLS-1$ - } - - // Local options specific to Annotate - revision (can be tag or revision) - public static LocalOption makeRevisionOption(String revision) { - return new LocalOption("-r" + revision, null); //$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ByteCountOutputStream.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ByteCountOutputStream.java deleted file mode 100644 index e81e91cf0..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ByteCountOutputStream.java +++ /dev/null @@ -1,25 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.io.*; - -class ByteCountOutputStream extends OutputStream { - - private long size = 0; - - public void write(int b) throws IOException { - size++; - } - public long getSize() { - return size; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CheckedInHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CheckedInHandler.java deleted file mode 100644 index 1f52af4ba..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CheckedInHandler.java +++ /dev/null @@ -1,57 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * Handles a "Checked-in" response from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Checked-in ??? \n - * [...] - * </pre> - * Then - * </p> - */ -class CheckedInHandler extends ResponseHandler { - public String getResponseID() { - return "Checked-in"; //$NON-NLS-1$ - } - - public void handle(Session session, String localDir, IProgressMonitor monitor) throws CVSException { - // read additional data for the response - String repositoryFile = session.readLine(); - String entryLine = session.readLine(); - - // clear file update modifiers - session.setModTime(null); - - // Get the local file - String fileName = repositoryFile.substring(repositoryFile.lastIndexOf("/") + 1); //$NON-NLS-1$ - ICVSFolder mParent = session.getLocalRoot().getFolder(localDir); - ICVSFile mFile = mParent.getFile(fileName); - - // Marked the local file as checked-in - monitor.subTask(Policy.bind("CheckInHandler.checkedIn", Util.toTruncatedPath(mFile, session.getLocalRoot(), 3))); //$NON-NLS-1$ - mFile.checkedIn(entryLine); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Checkout.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Checkout.java deleted file mode 100644 index ea18c928e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Checkout.java +++ /dev/null @@ -1,186 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.ModuleDefinitionsListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.UpdateListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; -import org.eclipse.team.internal.ccvs.core.resources.RemoteModule; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -public class Checkout extends Command { - /*** Local options: specific to checkout ***/ - public static final LocalOption DO_NOT_SHORTEN = new LocalOption("-N"); //$NON-NLS-1$ - public static final LocalOption FETCH_MODULE_ALIASES = new LocalOption("-c"); //$NON-NLS-1$ - public static LocalOption makeDirectoryNameOption(String moduleName) { - return new LocalOption("-d", moduleName); //$NON-NLS-1$ - } - - /*** Default command output listener ***/ - private static final ICommandOutputListener DEFAULT_OUTPUT_LISTENER = new UpdateListener(null); - - /** Command options found in the CVSROOT/modules file */ - public static LocalOption ALIAS = new LocalOption("-a"); //$NON-NLS-1$ - public static LocalOption makeStatusOption(String status) { - return new LocalOption("-s", status); //$NON-NLS-1$ - } - - protected Checkout() { } - protected String getRequestId() { - return "co"; //$NON-NLS-1$ - } - - protected ICommandOutputListener getDefaultCommandOutputListener() { - return DEFAULT_OUTPUT_LISTENER; - } - - protected ICVSResource[] computeWorkResources(Session session, LocalOption[] localOptions, - String[] arguments) throws CVSException { - - // We shouldn't have any arguments if we're fetching the module definitions - if (arguments.length < 1 && ! FETCH_MODULE_ALIASES.isElementOf(localOptions)) throw new IllegalArgumentException(); - - // We can determine the local directories using either the -d option or the module expansions - Option dOption = findOption(localOptions, "-d"); //$NON-NLS-1$ - if (dOption != null) { - // Should we append the expansions to the -d argument? - return new ICVSResource[] {session.getLocalRoot().getFolder(dOption.argument)}; - } - String[] modules = session.getModuleExpansions(); - ICVSResource[] resources = new ICVSResource[modules.length]; - for (int i = 0; i < resources.length; i++) { - resources[i] = session.getLocalRoot().getFolder(modules[i]); - } - return resources; - } - - /** - * Start the Checkout command: - * Send the module that is going to be checked-out to the server - * by reading the name of the resource given - * (This has to change to we give it the name of the modul and the - * Checkout creates everything for us) - */ - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // We need a folder to put the project(s) we checkout into - Assert.isTrue(session.getLocalRoot().isFolder()); - - // Send the information about the local workspace resources to the server - List resourcesToSend = new ArrayList(resources.length); - for (int i = 0; i < resources.length; i++) { - ICVSResource resource = resources[i]; - if (resource.exists() && resource.isFolder() && ((ICVSFolder)resource).isCVSFolder()) { - resourcesToSend.add(resource); - } - } - if ( ! resourcesToSend.isEmpty()) { - resources = (ICVSResource[]) resourcesToSend.toArray(new ICVSResource[resourcesToSend.size()]); - new FileStructureVisitor(session, true, true, monitor).visit(session, resources); - } - return resources; - } - - protected void sendLocalWorkingDirectory(Session session) throws CVSException { - session.sendConstructedRootDirectory(); - } - - /** - * On sucessful finish, prune empty directories if - * the -P option was specified (or is implied by -D or -r) - */ - protected IStatus commandFinished(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor, - IStatus status) throws CVSException { - // If we didn't succeed, don't do any post processing - if (status.getCode() == CVSStatus.SERVER_ERROR) { - return status; - } - - // If we are retrieving the modules file, ignore other options - if (FETCH_MODULE_ALIASES.isElementOf(localOptions)) return status; - - // If we are pruning (-P) or getting a sticky copy (-D or -r), then prune empty directories - if (PRUNE_EMPTY_DIRECTORIES.isElementOf(localOptions) || - (findOption(localOptions, "-D") != null) || //$NON-NLS-1$ - (findOption(localOptions, "-r") != null)) { //$NON-NLS-1$ - - // Prune empty directories - new PruneFolderVisitor().visit(session, resources); - } - - session.handleCaseCollisions(); - return status; - } - - /** - * Override execute to perform a expand-modules before the checkout - */ - protected IStatus doExecute(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, String[] arguments, ICommandOutputListener listener, - IProgressMonitor monitor) throws CVSException { - monitor.beginTask(null, 100); - - if ( ! FETCH_MODULE_ALIASES.isElementOf(localOptions)) { - // Execute the expand-modules command. - // This will put the expansions in the session for later retrieval - IStatus status = Request.EXPAND_MODULES.execute(session, arguments, Policy.subMonitorFor(monitor, 10)); - if (status.getCode() == CVSStatus.SERVER_ERROR) - return status; - - // If -d is not included in the local options, then send -N (do not shorten directory paths) - // to the server (as is done by other cvs clients) - if (findOption(localOptions, "-d") == null) { //$NON-NLS-1$ - if ( ! DO_NOT_SHORTEN.isElementOf(localOptions)) { - LocalOption[] newLocalOptions = new LocalOption[localOptions.length + 1]; - newLocalOptions[0] = DO_NOT_SHORTEN; - System.arraycopy(localOptions, 0, newLocalOptions, 1, localOptions.length); - localOptions = newLocalOptions; - } - } - } - - return super.doExecute(session, globalOptions, localOptions, arguments, listener, Policy.subMonitorFor(monitor, 90)); - } - - /** - * Perform a checkout to get the module expansions defined in the CVSROOT/modules file - */ - public RemoteModule[] getRemoteModules(Session session, CVSTag tag, IProgressMonitor monitor) - throws CVSException { - - ModuleDefinitionsListener moduleDefinitionListener = new ModuleDefinitionsListener(); - - IStatus status = super.execute(session, NO_GLOBAL_OPTIONS, new LocalOption[] {FETCH_MODULE_ALIASES}, NO_ARGUMENTS, - moduleDefinitionListener, monitor); - - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - - return RemoteModule.createRemoteModules(moduleDefinitionListener.getModuleExpansions(), session.getCVSRepositoryLocation(), tag); - } -} 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 deleted file mode 100644 index 9779eb93d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Command.java +++ /dev/null @@ -1,760 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -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.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSRunnable; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.IConsoleListener; - -/** - * Abstract base class for command requests. - * Provides a framework for implementing command execution. - */ -public abstract class Command extends Request { - /*** Command singleton instances ***/ - public final static Add ADD = new Add(); - public final static Admin ADMIN = new Admin(); - public final static Annotate ANNOTATE = new Annotate(); - public final static Checkout CHECKOUT = new Checkout(); - public final static Commit COMMIT = new Commit(); - public final static Diff DIFF = new Diff(); - public final static Editors EDITORS = new Editors(); - public final static Import IMPORT = new Import(); - public final static Log LOG = new Log(); - public final static Remove REMOVE = new Remove(); - public final static Status STATUS = new Status(); - public final static Tag TAG = new Tag(); - // The CUSTOM_TAG command has special handling for added and removed resources. - // This behavior supports branching with local changes in the workspace - public final static Tag CUSTOM_TAG = new Tag(true); - public final static RTag RTAG = new RTag(); - public final static Update UPDATE = new Update(); - public final static SyncUpdate SYNCUPDATE = new SyncUpdate(); - public final static Version VERSION = new Version(); - public final static NOOPCommand NOOP = new NOOPCommand(); - - // Empty argument array - public final static String[] NO_ARGUMENTS = new String[0]; - - /*** Global options ***/ - // Empty global option array - public static final GlobalOption[] NO_GLOBAL_OPTIONS = new GlobalOption[0]; - // Do not change file contents - public static final GlobalOption DO_NOT_CHANGE = new GlobalOption("-n"); //$NON-NLS-1$ - // Do not record this operation into CVS command history - public static final GlobalOption DO_NOT_LOG = new GlobalOption("-l"); //$NON-NLS-1$ - // Make new working files read-only - public static final GlobalOption MAKE_READ_ONLY = new GlobalOption("-r"); //$NON-NLS-1$ - // Trace command execution - public static final GlobalOption TRACE_EXECUTION = new GlobalOption("-t"); //$NON-NLS-1$ - - /*** Global options: quietness ***/ - // Don't be quiet (normal verbosity) - public static final QuietOption VERBOSE = new QuietOption(""); //$NON-NLS-1$ - // Be somewhat quiet (suppress informational messages) - public static final QuietOption PARTLY_QUIET = new QuietOption("-q"); //$NON-NLS-1$ - // Be really quiet (silent but for serious problems) - public static final QuietOption SILENT = new QuietOption("-Q"); //$NON-NLS-1$ - - /*** Local options: common to many commands ***/ - // Empty local option array - public static final LocalOption[] NO_LOCAL_OPTIONS = new LocalOption[0]; - // valid for: annotate checkout commit diff export log rdiff remove rtag status tag update - public static final LocalOption DO_NOT_RECURSE = new LocalOption("-l"); //$NON-NLS-1$ - // valid for: checkout export update - public static final LocalOption PRUNE_EMPTY_DIRECTORIES = new LocalOption("-P"); //$NON-NLS-1$ - // valid for: checkout export update - public static final LocalOption MESSAGE_OPTION = new LocalOption("-m"); //$NON-NLS-1$ - - /*** Local options: keyword substitution mode ***/ - // valid for: add admin checkout export import update - private static final Map ksubstOptionMap = new HashMap(); - public static final KSubstOption KSUBST_BINARY = new KSubstOption("-kb"); //$NON-NLS-1$ - public static final KSubstOption KSUBST_TEXT = new KSubstOption("-ko"); //$NON-NLS-1$ - public static final KSubstOption KSUBST_TEXT_EXPAND = new KSubstOption("-kkv"); //$NON-NLS-1$ - public static final KSubstOption KSUBST_TEXT_EXPAND_LOCKER = new KSubstOption("-kkvl"); //$NON-NLS-1$ - public static final KSubstOption KSUBST_TEXT_VALUES_ONLY = new KSubstOption("-kv"); //$NON-NLS-1$ - public static final KSubstOption KSUBST_TEXT_KEYWORDS_ONLY = new KSubstOption("-kk"); //$NON-NLS-1$ - - /*** Default command output listener ***/ - protected static final ICommandOutputListener DEFAULT_OUTPUT_LISTENER = new CommandOutputListener(); - - /** - * Prevents client code from instantiating us. - */ - protected Command() { } - - /** - * Provides the default command output listener which is used to accumulate errors. - * - * Subclasses can override this method in order to properly interpret information - * received from the server. - */ - protected ICommandOutputListener getDefaultCommandOutputListener() { - return DEFAULT_OUTPUT_LISTENER; - } - - /** - * Sends the command's arguments to the server. - * [template method] - * <p> - * The default implementation sends all arguments. Subclasses may override - * this method to provide alternate behaviour. - * </p> - * - * @param session the CVS session - * @param arguments the arguments that were supplied by the caller of execute() - */ - protected void sendArguments(Session session, String[] arguments) throws CVSException { - for (int i = 0; i < arguments.length; ++i) { - session.sendArgument(arguments[i]); - } - } - - /** - * Describes the local resource state to the server prior to command execution. - * [template method] - * <p> - * Commands must override this method to inform the server about the state of - * local resources using the Entries, Modified, Unchanged, and Questionable - * requests as needed. - * </p> - * <p> - * This method should return the resources that are of interest to the - * <code>Command#commandFinished()</code> method. In most cases, it - * is the same resources that are provided but in some cases (e.g. Commit) - * the resources to be passed to the above method are different. - * </p> - * - * @param session the CVS session - * @param globalOptions the global options for the command - * @param localOptions the local options for the command - * @param resources the resource arguments for the command - * @param monitor the progress monitor - * @return ICVSResource[] - */ - protected abstract ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException; - - /** - * Cleans up after command execution. - * [template method] - * <p> - * The default implementation is a no-op. Subclasses may override this - * method to follow up command execution on the server with clean up - * operations on local resources. - * </p> - * - * @param session the CVS session - * @param globalOptions the global options for the command - * @param localOptions the local options for the command - * @param resources the resource arguments for the command - * @param monitor the progress monitor - * @param status the status accumulated so far. If the code == CVSStatus.SERVER_ERROR - * then the command failed - * @return status the status past in plus any additional status accumulated during the finish - */ - protected IStatus commandFinished(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor, - IStatus status) throws CVSException { - return status; - } - - /** - * Sends the local working directory path prior to command execution. - * [template method] - * <p> - * The default implementation sends the paths of local root directory - * (assuming it exists). Subclasses may override this method to provide - * alternate behaviour. - * </p> - * - * @param session the CVS session - */ - protected void sendLocalWorkingDirectory(Session session) throws CVSException { - ICVSFolder localRoot = session.getLocalRoot(); - if (localRoot.isCVSFolder()) { - session.sendLocalRootDirectory(); - } else { - session.sendConstructedRootDirectory(); - } - } - - /** - * Computes an array of ICVSResources corresponding to command arguments. - * [template method] - * <p> - * The default implementation assumes that all arguments supplied to the - * command represent resources in the local root that are to be manipulated. - * Subclasses must override this method if this assumption does not hold. - * </p> - * @param session the CVS session - * @param localOptions the command local options - * @param arguments the command arguments - * @return the resource arguments for the command - */ - protected ICVSResource[] computeWorkResources(Session session, - LocalOption[] localOptions, String[] arguments) throws CVSException { - ICVSFolder localRoot = session.getLocalRoot(); - - if (arguments.length == 0) { - // As a convenience, passing no arguments to the CVS command - // implies the command will operate on the local root folder. - return new ICVSResource[] { localRoot }; - } else { - // Assume all arguments represent resources that are descendants - // of the local root folder. - ICVSResource[] resources = new ICVSResource[arguments.length]; - for (int i = 0; i < arguments.length; i++) { - ICVSResource resource = localRoot.getChild(arguments[i]); - // file does not exist, it could have been deleted. It doesn't matter - // which type we return since only the name of the resource is used - // and sent to the server. - if(resource==null) { - if(localRoot.getName().length()==0) { - // Return a folder because it is the safest choice when - // localRoot is a handle to the IWorkspaceRoot! - resource = localRoot.getFolder(arguments[i]); - } else { - resource = localRoot.getFile(arguments[i]); - } - } - resources[i] = resource; - } - return resources; - } - } - - /** - * Send an array of Resources. - * - * @see Command#sendFileStructure(ICVSResource,IProgressMonitor,boolean,boolean,boolean) - */ - protected void sendFileStructure(Session session, ICVSResource[] resources, - boolean emptyFolders, IProgressMonitor monitor) throws CVSException { - checkResourcesManaged(resources); - - new FileStructureVisitor(session, emptyFolders, true, monitor).visit(session, resources); - } - - /** - * Checks that all work resources are managed. - * - * @param resources the resource arguments for the command - * @throws CVSException if some resources are not managed - */ - protected void checkResourcesManaged(ICVSResource[] resources) throws CVSException { - for (int i = 0; i < resources.length; ++i) { - ICVSFolder folder; - if (resources[i].isFolder()) { - folder = (ICVSFolder) resources[i]; - } - else { - folder = resources[i].getParent(); - } - if (folder==null || (!folder.isCVSFolder() && folder.exists())) { - throw new CVSException(Policy.bind("Command.argumentNotManaged", folder.getName()));//$NON-NLS-1$ - } - } - } - - /** - * Executes a CVS command. - * <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 session the open CVS session - * @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(final Session session, final GlobalOption[] globalOptions, - final LocalOption[] localOptions, final String[] arguments, final ICommandOutputListener listener, - IProgressMonitor pm) throws CVSException { - final IStatus[] status = new IStatus[1]; - ICVSRunnable job = new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - // update the global and local options - GlobalOption[] gOptions = filterGlobalOptions(session, globalOptions); - LocalOption[] lOptions = filterLocalOptions(session, gOptions, localOptions); - - // print the invocation string to the console - if (session.isOutputToConsole() || Policy.DEBUG_CVS_PROTOCOL) { - IPath commandRootPath; - IResource resource = session.getLocalRoot().getIResource(); - if (resource == null) { - commandRootPath = Path.EMPTY; - } else { - commandRootPath = resource.getFullPath(); - } - String line = constructCommandInvocationString(commandRootPath, gOptions, lOptions, arguments); - if (session.isOutputToConsole()) { - IConsoleListener consoleListener = CVSProviderPlugin.getPlugin().getConsoleListener(); - if (consoleListener != null) consoleListener.commandInvoked(line); - } - if (Policy.DEBUG_CVS_PROTOCOL) System.out.println("CMD> " + line); //$NON-NLS-1$ - } - - // run the command - try { - status[0] = doExecute(session, gOptions, lOptions, arguments, listener, monitor); - notifyConsoleOnCompletion(session, status[0], null); - } catch (CVSException e) { - notifyConsoleOnCompletion(session, null, e); - throw e; - } catch (RuntimeException e) { - notifyConsoleOnCompletion(session, null, e); - throw e; - } - } - }; - session.getLocalRoot().run(job, pm); - return status[0]; - } - - private void notifyConsoleOnCompletion(Session session, IStatus status, Exception exception) { - if (session.isOutputToConsole()) { - IConsoleListener consoleListener = CVSProviderPlugin.getPlugin().getConsoleListener(); - if (consoleListener != null) consoleListener.commandCompleted(status, exception); - } - if (Policy.DEBUG_CVS_PROTOCOL) { - if (status != null) System.out.println("RESULT> " + status.toString()); //$NON-NLS-1$ - else System.out.println("RESULT> " + exception.toString()); //$NON-NLS-1$ - } - } - - protected IStatus doExecute(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, String[] arguments, ICommandOutputListener listener, - IProgressMonitor monitor) throws CVSException { - ICVSResource[] resources = null; - /*** setup progress monitor ***/ - monitor = Policy.monitorFor(monitor); - monitor.beginTask(Policy.bind("Command.server"), 100); //$NON-NLS-1$ - Policy.checkCanceled(monitor); - try { - /*** prepare for command ***/ - // clear stale command state from previous runs - session.setNoLocalChanges(DO_NOT_CHANGE.isElementOf(globalOptions)); - session.setModTime(null); - - /*** initiate command ***/ - // send global options - for (int i = 0; i < globalOptions.length; i++) { - globalOptions[i].send(session); - } - Policy.checkCanceled(monitor); - // send local options - for (int i = 0; i < localOptions.length; i++) { - localOptions[i].send(session); - } - Policy.checkCanceled(monitor); - // compute the work resources - resources = computeWorkResources(session, localOptions, arguments); - Policy.checkCanceled(monitor); - // send local working directory state contributes 25% of work - resources = sendLocalResourceState(session, globalOptions, localOptions, - resources, Policy.subMonitorFor(monitor, 25)); - Policy.checkCanceled(monitor); - // send arguments - sendArguments(session, arguments); - // send local working directory path - sendLocalWorkingDirectory(session); - - // if no listener was provided, use the command's default in order to get error reporting - if (listener == null) listener = getDefaultCommandOutputListener(); - - /*** execute command and process responses ***/ - // Processing responses contributes 70% of work. - IStatus status = executeRequest(session, listener, Policy.subMonitorFor(monitor, 70)); - - // Finished adds last 5% of work. - status = commandFinished(session, globalOptions, localOptions, resources, Policy.subMonitorFor(monitor, 5), - status); - return status; - } finally { - monitor.done(); - } - } - - /** - * Constucts the CVS command invocation string corresponding to the arguments. - * - * @param globalOptions the global options - * @param localOption the local options - * @param arguments the arguments - * @return the command invocation string - */ - private String constructCommandInvocationString(IPath commandRootPath, GlobalOption[] globalOptions, - LocalOption[] localOptions, String[] arguments) { - StringBuffer commandLine = new StringBuffer("cvs"); //$NON-NLS-1$ - for (int i = 0; i < globalOptions.length; ++i) { - String option = globalOptions[i].toString(); - if (option.length() == 0) continue; - commandLine.append(' '); - commandLine.append(option); - } - commandLine.append(' '); - commandLine.append(getRequestId()); - for (int i = 0; i < localOptions.length; ++i) { - String option = localOptions[i].toString(); - if (option.length() == 0) continue; - commandLine.append(' '); - commandLine.append(option); - } - for (int i = 0; i < arguments.length; ++i) { - if (arguments[i].length() == 0) continue; - commandLine.append(" \""); //$NON-NLS-1$ - IPath completePath = commandRootPath; - if (!arguments[i].equals(Session.CURRENT_LOCAL_FOLDER)) { - completePath = completePath.append(arguments[i]); - } - commandLine.append(completePath.toString()); - commandLine.append('"'); //$NON-NLS-1$ - } - return commandLine.toString(); - } - - /** - * Superclass for all CVS command options - */ - protected static abstract class Option { - protected String option, argument; - protected Option(String option, String argument) { - this.option = option; - this.argument = argument; - } - /** - * Determines if this option is an element of an array of options - * @param array the array of options - * @return true iff the array contains this option - */ - public boolean isElementOf(Option[] array) { - return findOption(array, option) != null; - } - /** - * Returns the option part of the option - */ - String getOption() { - return option; - } - /** - * Compares two options for equality. - * @param other the other option - */ - public boolean equals(Object other) { - if (this == other) return true; - if (other instanceof Option) { - Option otherOption = (Option) other; - return option.equals(otherOption.option); - } - return false; - } - /** - * Sends the option to a CVS server - * @param session the CVS session - */ - public abstract void send(Session session) throws CVSException; - /* - * To make debugging a tad easier. - */ - public String toString() { - if (argument != null && argument.length() != 0) { - return option + " \"" + argument + '"'; //$NON-NLS-1$ - } else { - return option; - } - } - } - /** - * Option subtype for global options that are common to all commands. - */ - public static class GlobalOption extends Option { - protected GlobalOption(String option) { - super(option, null); - } - public void send(Session session) throws CVSException { - session.sendGlobalOption(option); - } - /** - * Add the given global option to the end of the provided list - * - * @param newOption - * @param options - * @return GlobalOption[] - */ - protected GlobalOption[] addToEnd(GlobalOption[] options) { - GlobalOption[] globalOptions = new GlobalOption[options.length + 1]; - System.arraycopy(options, 0, globalOptions, 0, options.length); - globalOptions[globalOptions.length - 1] = this; - return globalOptions; - } - } - /** - * Option subtype for global quietness options. - */ - public static final class QuietOption extends GlobalOption { - private QuietOption(String option) { - super(option); - } - public void send(Session session) throws CVSException { - if (option.length() != 0) super.send(session); - } - } - /** - * Option subtype for local options that vary from command to command. - */ - public static class LocalOption extends Option { - protected LocalOption(String option) { - super(option, null); - } - protected LocalOption(String option, String argument) { - super(option, argument); - } - public void send(Session session) throws CVSException { - session.sendArgument(option); - if (argument != null) session.sendArgument(argument); - } - } - /** - * Options subtype for keyword substitution options. - */ - public static class KSubstOption extends LocalOption { - private boolean isUnknownMode; - private KSubstOption(String option) { - this(option, false); - } - private KSubstOption(String option, boolean isUnknownMode) { - super(option); - this.isUnknownMode = isUnknownMode; - ksubstOptionMap.put(option, this); - } - /** - * Gets the KSubstOption instance for the specified mode. - * - * @param mode the mode, e.g. -kb - * @return an instance for that mode - */ - public static KSubstOption fromMode(String mode) { - if (mode.length() == 0) mode = "-kkv"; // use default //$NON-NLS-1$ - KSubstOption option = (KSubstOption) ksubstOptionMap.get(mode); - if (option == null) option = new KSubstOption(mode, true); - return option; - } - /** - * Gets the KSubstOption instance for the specified file. - * - * @param file the file to get the option for - * @return an instance for that mode - */ - public static KSubstOption fromFile(IFile file) { - if (CVSProviderPlugin.isText(file)) - return CVSProviderPlugin.getPlugin().getDefaultTextKSubstOption(); - return KSUBST_BINARY; - } - /** - * Returns an array of all valid modes. - */ - public static KSubstOption[] getAllKSubstOptions() { - return (KSubstOption[]) ksubstOptionMap.values().toArray(new KSubstOption[ksubstOptionMap.size()]); - } - /** - * Returns the entry line mode string for this instance. - */ - public String toMode() { - if (KSUBST_TEXT_EXPAND.equals(this)) return ""; //$NON-NLS-1$ - return getOption(); - } - /** - * Returns true if the substitution mode requires no data translation - * during file transfer. - */ - public boolean isBinary() { - return KSUBST_BINARY.equals(this); - } - /** - * Returns a short localized text string describing this mode. - */ - public String getShortDisplayText() { - if (isUnknownMode) return Policy.bind("KSubstOption.unknown.short", option); //$NON-NLS-1$ - return Policy.bind("KSubstOption." + option + ".short"); //$NON-NLS-1$ //$NON-NLS-2$ - } - /** - * Returns a long localized text string describing this mode. - */ - public String getLongDisplayText() { - if (isUnknownMode) return Policy.bind("KSubstOption.unknown.long", option); //$NON-NLS-1$ - return Policy.bind("KSubstOption." + option + ".long"); //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /** - * Makes a -m log message option. - * Valid for: add commit import - */ - public static LocalOption makeArgumentOption(LocalOption option, String argument) { - if(argument == null) { - argument = ""; //$NON-NLS-1$ - } - return new LocalOption(option.getOption(), argument); //$NON-NLS-1$ - } - - /** - * Makes a -r or -D option for a tag. - * Valid for: checkout export history rdiff update - */ - public static LocalOption makeTagOption(CVSTag tag) { - int type = tag.getType(); - switch (type) { - case CVSTag.BRANCH: - case CVSTag.VERSION: - return new LocalOption("-r", tag.getName()); //$NON-NLS-1$ - case CVSTag.DATE: - return new LocalOption("-D", tag.getName()); //$NON-NLS-1$ - default: - // tag must not be HEAD - throw new IllegalArgumentException(Policy.bind("Command.invalidTag")); //$NON-NLS-1$ - } - } - - /** - * Find a specific option in an array of options - * @param array the array of options - * @param option the option string to search for - * @return the first element matching the option string, or null if none - */ - public static Option findOption(Option[] array, String option) { - for (int i = 0; i < array.length; ++i) { - if (array[i].getOption().equals(option)) return array[i]; - } - return null; - } - - /** - * Collect all arguments of a specific option from an array of options - * @param array the array of options - * @param option the option string to search for - * @return an array of all arguments of belonging to matching options - */ - protected static String[] collectOptionArguments(Option[] array, String option) { - List /* of String */ list = new ArrayList(); - for (int i = 0; i < array.length; ++i) { - if (array[i].getOption().equals(option)) { - list.add(array[i].argument); - } - } - return (String[]) list.toArray(new String[list.size()]); - } - - /** - * Allows commands to filter the set of global options to be sent. - * This method invokes the method of the same name on the session - * itself in order to get any session wide or globally set options. - * Subclasses that override this method should call the superclass. - * - * @param session the session - * @param globalOptions the global options, read-only - * @return the filtered global options - */ - protected GlobalOption[] filterGlobalOptions(Session session, GlobalOption[] globalOptions) { - return session.filterGlobalOptions(globalOptions); - } - - /** - * Allows commands to filter the set of local options to be sent. - * Subclasses that override this method should call the superclass. - * - * @param session the session - * @param globalOptions the global options, read-only - * @param localOptions the local options, read-only - * @return the filtered local options - */ - protected LocalOption[] filterLocalOptions(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions) { - return localOptions; - } - - /** - * Execute a CVS command on an array of ICVSResource. This method simply converts - * the ICVSResource to String paths relative to the local root of the session and - * invokes <code>execute(Session, GlobalOption[], LocalOption[], String[], ICommandOutputListener, IProgressMonitor)</code>. - * </p> - * @param session the open CVS session - * @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 ICVSResource to be operated on - * @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) - * - * @see Command#execute(Session, GlobalOption[], LocalOption[], String[], ICommandOutputListener, IProgressMonitor) - */ - public final IStatus execute(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions, ICVSResource[] arguments, - ICommandOutputListener listener, IProgressMonitor pm) throws CVSException { - - String[] stringArguments = convertArgumentsForOpenSession(arguments, session); - return execute(session, globalOptions, localOptions, stringArguments, listener, pm); - } - - protected String[] convertArgumentsForOpenSession(ICVSResource[] arguments, Session openSession) throws CVSException { - // Convert arguments - List stringArguments = new ArrayList(arguments.length); - for (int i = 0; i < arguments.length; i++) { - stringArguments.add(arguments[i].getRelativePath(openSession.getLocalRoot())); - } - return (String[]) stringArguments.toArray(new String[stringArguments.size()]); - } - - /** - * Method mergeStatus. - * @param status - * @param cVSStatus - * @return IStatus - */ - protected IStatus mergeStatus(IStatus accumulatedStatus, IStatus newStatus) { - if (accumulatedStatus.isMultiStatus()) { - ((MultiStatus)accumulatedStatus).merge(newStatus); - return accumulatedStatus; - } - if (accumulatedStatus.isOK()) return newStatus; - if (newStatus.isOK()) return accumulatedStatus; - MultiStatus result = new MultiStatus(CVSProviderPlugin.ID, CVSStatus.INFO, - new IStatus[] {accumulatedStatus, newStatus}, - Policy.bind("Command.warnings", Policy.bind("Command." + getRequestId())), null); //$NON-NLS-1$ //$NON-NLS-2$ - return result; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CommandOutputListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CommandOutputListener.java deleted file mode 100644 index 2ed422c99..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CommandOutputListener.java +++ /dev/null @@ -1,59 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; - -public class CommandOutputListener implements ICommandOutputListener { - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - return OK; - } - public IStatus errorLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - String protocolError = getProtocolError(line, location); - if (protocolError != null) { - return new CVSStatus(CVSStatus.ERROR, CVSStatus.PROTOCOL_ERROR, commandRoot, protocolError); - } - return new CVSStatus(CVSStatus.ERROR, CVSStatus.ERROR_LINE, commandRoot, line); - } - - /** - * Return the portion of the line that describes the error if the error line - * is a protocol error or null if the line is not a protocol error. - * - * @param line the error line received from the server - * @param location the repository location - * @return String the potocol error or null - */ - protected String getProtocolError(String line, ICVSRepositoryLocation location) { - if (line.startsWith("Protocol error:")) { //$NON-NLS-1$ - return line; - } - return null; - } - - public String getServerMessage(String line, ICVSRepositoryLocation location) { - return ((CVSRepositoryLocation)location).getServerMessageWithoutPrefix(line, SERVER_PREFIX); - } - - public String getServerAbortedMessage(String line, ICVSRepositoryLocation location) { - return ((CVSRepositoryLocation)location).getServerMessageWithoutPrefix(line, SERVER_ABORTED_PREFIX); - } - - public String getServerRTagMessage(String line, ICVSRepositoryLocation location) { - return ((CVSRepositoryLocation)location).getServerMessageWithoutPrefix(line, RTAG_PREFIX); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Commit.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Commit.java deleted file mode 100644 index 9bff4204f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Commit.java +++ /dev/null @@ -1,123 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.Collection; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Status; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; - -public class Commit extends Command { - /*** Local options: specific to commit ***/ - // Forces a file to be committed even if it has not been modified; implies -l. - // NOTE: This option is not fully supported -- a file will not be sent - // unless it is dirty. The primary use is to resend a file that may - // or may not be changed (e.g. could depend on CR/LF translations, etc...) - // and force the server to create a new revision and reply Checked-in. - public static final LocalOption FORCE = new LocalOption("-f"); //$NON-NLS-1$ - - protected Commit() { } - protected String getRequestId() { - return "ci"; //$NON-NLS-1$ - } - - /** - * Send all files under the workingFolder as changed files to - * the server. - */ - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Get the folders we want to work on - checkResourcesManaged(resources); - - // Send all changed files to the server - ModifiedFileSender visitor = new ModifiedFileSender(session, monitor); - visitor.visit(session, resources); - - // Send the changed files as arguments (because this is what other cvs clients do) - ICVSFile[] changedFiles = visitor.getModifiedFiles(); - for (int i = 0; i < changedFiles.length; i++) { - session.sendArgument(changedFiles[i].getRelativePath(session.getLocalRoot())); - } - return changedFiles; - } - - /** - * On successful finish, prune empty directories if the -P or -D option was specified. - */ - protected IStatus commandFinished(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor, - IStatus status) throws CVSException { - // If we didn't succeed, don't do any post processing - if (status.getCode() == CVSStatus.SERVER_ERROR) { - return status; - } - - // If pruning is enable, prune empty directories after a commit - if (CVSProviderPlugin.getPlugin().getPruneEmptyDirectories()) { //$NON-NLS-1$ - new PruneFolderVisitor().visit(session, resources); - } - - // Reset the timestamps of any committed files that are still dirty - if (CVSProviderPlugin.getPlugin().getResetTimestampOfFalseChange()) { - for (int i = 0; i < resources.length; i++) { - ICVSResource resource = resources[i]; - if (!resource.isFolder()) { - ICVSFile cvsFile = (ICVSFile)resources[i]; - if (cvsFile.exists() && cvsFile.isModified(null)) { - status = mergeStatus(status, clearModifiedState(cvsFile)); - } - } - } - } - return status; - } - - protected IStatus clearModifiedState(ICVSFile cvsFile) throws CVSException { - byte[] info = cvsFile.getSyncBytes(); - if (info == null) { - // There should be sync info. Log the problem - return new Status(IStatus.WARNING, CVSProviderPlugin.ID, 0, Policy.bind("Commit.syncInfoMissing", cvsFile.getIResource().getFullPath().toString()), null); //$NON-NLS-1$ - } - cvsFile.checkedIn(null); - return new Status(IStatus.INFO, CVSProviderPlugin.ID, 0, Policy.bind("Commit.timestampReset", cvsFile.getIResource().getFullPath().toString()), null); //$NON-NLS-1$; - } - - /** - * We do not want to send the arguments here, because we send - * them in sendRequestsToServer (special handling). - */ - protected void sendArguments(Session session, String[] arguments) throws CVSException { - } - - public final IStatus execute(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions, - ICVSResource[] arguments, Collection filesToCommitAsText, - ICommandOutputListener listener, IProgressMonitor pm) throws CVSException { - - session.setTextTransferOverride(filesToCommitAsText); - try { - return super.execute(session, globalOptions, localOptions, arguments, listener, pm); - } finally { - session.setTextTransferOverride(null); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CopyHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CopyHandler.java deleted file mode 100644 index 67f042950..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/CopyHandler.java +++ /dev/null @@ -1,61 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Handles a "Copy-file" response from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Copy-file myproject/ \n - * /u/cvsroot/myproject/oldfile.txt \n - * newfile.txt - * [...] - * </pre> - * Then we copy (or optionally rename) the local file "oldfile.txt" in - * folder "myproject" to "newfile.txt". This response is used to create - * a backup copy of an existing file before merging in new changes. - * </p> - */ -class CopyHandler extends ResponseHandler { - public String getResponseID() { - return "Copy-file"; //$NON-NLS-1$ - } - - public void handle(Session session, String localDir, - IProgressMonitor monitor) throws CVSException { - // read additional data for the response - String repositoryFile = session.readLine(); - String newFile = session.readLine(); - if (session.isNoLocalChanges() || ! session.isCreateBackups()) return; - - // Get the local file - String fileName = repositoryFile.substring(repositoryFile.lastIndexOf("/") + 1); //$NON-NLS-1$ - ICVSFolder mParent = session.getLocalRoot().getFolder(localDir); - ICVSFile mFile = mParent.getFile(fileName); - - Assert.isTrue(mParent.exists()); - Assert.isTrue(mFile.exists() && mFile.isManaged()); - - // rename the file - mFile.copyTo(newFile); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Diff.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Diff.java deleted file mode 100644 index 00442d0d9..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Diff.java +++ /dev/null @@ -1,63 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; - -/** - * Runs the CVS diff command. - */ -public class Diff extends Command { - /*** Local options: specific to diff ***/ - public static final LocalOption UNIFIED_FORMAT = new LocalOption("-u"); //$NON-NLS-1$ - public static final LocalOption CONTEXT_FORMAT = new LocalOption("-c"); //$NON-NLS-1$ - public static final LocalOption INCLUDE_NEWFILES = new LocalOption("-N"); //$NON-NLS-1$ - - protected Diff() { } - protected String getRequestId() { - return "diff"; //$NON-NLS-1$ - } - - /** - * Overwritten to throw the CVSDiffException if the server returns an error, because it just does - * so when there is a difference between the checked files. - */ - protected IStatus doExecute(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions, - String[] arguments, ICommandOutputListener listener, IProgressMonitor monitor) throws CVSException { - try { - return super.doExecute(session, globalOptions, localOptions, arguments, listener, monitor); - } catch (CVSServerException e) { - if (e.containsErrors()) throw e; - return e.getStatus(); - } - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - checkResourcesManaged(resources); - DiffStructureVisitor visitor = new DiffStructureVisitor(session, monitor); - visitor.visit(session, resources); - return resources; - } - - protected String getServerErrorMessage() { - return Policy.bind("Diff.serverError"); //$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/DiffStructureVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/DiffStructureVisitor.java deleted file mode 100644 index 0bf3945b6..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/DiffStructureVisitor.java +++ /dev/null @@ -1,54 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * The diff command needs to send a file structure to the server that differs somewhat from the canonical - * format sent by other commands. Instead of sending new files as questionables this class sends - * new files as modified and fakes them being added. The contents are sent to the server and are - * included in the returned diff report. - */ -class DiffStructureVisitor extends FileStructureVisitor { - - public DiffStructureVisitor(Session session, IProgressMonitor monitor) { - super(session, false, true, monitor); - } - - /** - * Send unmanaged files as modified with a default entry line. - */ - protected void sendFile(ICVSFile mFile) throws CVSException { - byte[] info = mFile.getSyncBytes(); - if (info==null) { - return; - } - - // Send the parent folder if it hasn't been sent already - sendFolder(mFile.getParent()); - Policy.checkCanceled(monitor); - session.sendEntry(info, null); - - if (!mFile.exists()) { - return; - } - - if (mFile.isModified(null)) { - session.sendModified(mFile, ResourceSyncInfo.isBinary(info), monitor); - } else { - session.sendUnchanged(mFile); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Editors.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Editors.java deleted file mode 100644 index dd1645d15..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Editors.java +++ /dev/null @@ -1,29 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2003 CSC SoftwareConsult GmbH & Co. OHG, Germany and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * CSC - Intial implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -/** - * - * The editors command - * - * @author <a href="mailto:kohlwes@gmx.net">Gregor Kohlwes</a> - */ -public class Editors extends AbstractMessageCommand { - - /** - * @see org.eclipse.team.internal.ccvs.core.client.Request#getRequestId() - */ - protected String getRequestId() { - return "editors"; //$NON-NLS-1$ - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ExpandModules.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ExpandModules.java deleted file mode 100644 index 55364fd36..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ExpandModules.java +++ /dev/null @@ -1,31 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; - -public class ExpandModules extends Request { - protected ExpandModules() { } - protected String getRequestId() { - return "expand-modules"; //$NON-NLS-1$ - } - - public IStatus execute(Session session, String[] modules, IProgressMonitor monitor) throws CVSException { - // Reset the module expansions before the responses arrive - session.resetModuleExpansion(); - for (int i = 0; i < modules.length; ++i) { - session.sendArgument(modules[i]); - } - return executeRequest(session, Command.DEFAULT_OUTPUT_LISTENER, monitor); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/FileStructureVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/FileStructureVisitor.java deleted file mode 100644 index 87cd60822..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/FileStructureVisitor.java +++ /dev/null @@ -1,119 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -/** - * Visitor to send the local file structure to the CVS Server. - * - * Files are sent as Unchanged or Modified. - * Folders are sent if they contain files unless sendEmptyFolders is true - * in which case all folders are sent. - * - * @param sendEmptyFolders sends the folder-entrie even if there is no file - to send in it - */ - -class FileStructureVisitor extends AbstractStructureVisitor { - - private boolean sendEmptyFolders; - - public FileStructureVisitor(Session session, boolean sendEmptyFolders, boolean sendModifiedContents, IProgressMonitor monitor) { - this(session, sendEmptyFolders, sendModifiedContents, true, monitor); - } - - public FileStructureVisitor(Session session, boolean sendEmptyFolders, boolean sendModifiedContents, boolean sendBinary, IProgressMonitor monitor) { - super(session, true, sendModifiedContents, sendBinary, monitor); - this.sendEmptyFolders = sendEmptyFolders; - } - - /** - * @see ICVSResourceVisitor#visitFile(IManagedFile) - */ - public void visitFile(ICVSFile mFile) throws CVSException { - sendFile(mFile); - } - - /** - * @see ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder mFolder) throws CVSException { - - if (sendEmptyFolders) { - // If we want to send empty folder, that just send it when - // we come to it - sendFolder(mFolder); - } - - boolean exists = mFolder.exists(); - boolean isCVSFolder = mFolder.isCVSFolder(); - - // We are only interested in CVS folders - // A folder could be a non-existant CVS folder if it is a holder for outgoing file deletions - if ( ! isCVSFolder) return; - - if (exists && isOrphanedSubtree(mFolder)) { - return; - } - - // Send files, then the questionable folders, then the managed folders - ICVSResource[] children = mFolder.members(ICVSFolder.ALL_UNIGNORED_MEMBERS); - sendFiles(children); - sendQuestionableFolders(children); - sendManagedFolders(children); - } - - /** - * Method sendManagedFolders. - * @param children - */ - private void sendManagedFolders(ICVSResource[] children) throws CVSException { - for (int i = 0; i < children.length; i++) { - ICVSResource resource = children[i]; - if (resource.isFolder() && resource.isManaged()) { - resource.accept(this); - } - } - } - - /** - * Method sendQuestionableFolders. - * @param children - */ - private void sendQuestionableFolders(ICVSResource[] children) throws CVSException { - for (int i = 0; i < children.length; i++) { - ICVSResource resource = children[i]; - if (resource.isFolder() && ! resource.isManaged()) { - resource.accept(this); - } - } - } - - /** - * Method sendFiles. - * @param children - */ - private void sendFiles(ICVSResource[] children) throws CVSException { - for (int i = 0; i < children.length; i++) { - ICVSResource resource = children[i]; - if (!resource.isFolder()) { - resource.accept(this); - } - } - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Import.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Import.java deleted file mode 100644 index e654bf075..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Import.java +++ /dev/null @@ -1,69 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; - - -public class Import extends Command { - /*** Local options: specific to import ***/ - public static LocalOption makeBinaryWrapperOption(String pattern) { - return new LocalOption("-W", pattern + " -k 'b'"); //$NON-NLS-1$ //$NON-NLS-2$ - } - - protected Import() { } - protected String getRequestId() { - return "import"; //$NON-NLS-1$ - } - - protected ICVSResource[] computeWorkResources(Session session, LocalOption[] localOptions, - String[] arguments) throws CVSException { - if (arguments.length < 3) throw new IllegalArgumentException(); - return new ICVSResource[0]; - } - - protected IStatus doExecute(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, String[] arguments, ICommandOutputListener listener, - IProgressMonitor monitor) throws CVSException { - - // If the branch option is not provided, a default value of 1.1.1 is used. - // This is done to maintain reference client compatibility - if (findOption(localOptions, "-b") == null) { //$NON-NLS-1$ - LocalOption[] newLocalOptions = new LocalOption[localOptions.length + 1]; - newLocalOptions[0] = new LocalOption("-b", "1.1.1"); //$NON-NLS-1$ //$NON-NLS-2$ - System.arraycopy(localOptions, 0, newLocalOptions, 1, localOptions.length); - localOptions = newLocalOptions; - } - return super.doExecute(session, globalOptions, localOptions, arguments, listener, monitor); - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - ICVSResourceVisitor visitor = new ImportStructureVisitor(session, - collectOptionArguments(localOptions, "-W"), monitor); //$NON-NLS-1$ - session.getLocalRoot().accept(visitor); - return resources; - } - - protected void sendLocalWorkingDirectory(Session session) throws CVSException { - session.sendConstructedRootDirectory(); - } - -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ImportStructureVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ImportStructureVisitor.java deleted file mode 100644 index 6aaa205f7..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ImportStructureVisitor.java +++ /dev/null @@ -1,140 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.Set; -import java.util.StringTokenizer; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.Team; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command.KSubstOption; -import org.eclipse.team.internal.ccvs.core.util.FileNameMatcher; - -/** - * The ImportStructureVisitor sends the content of the folder it is - * used on to the server. It constructs the locations of the resources - * because the resources do not yet have a remote-location.<br> - * It can also ignore certain files and decides wether to send - * a file in binary or text mode due to a specification that is passed - * as a "wrapper" argument. - */ -class ImportStructureVisitor implements ICVSResourceVisitor { - - private static final String KEYWORD_OPTION = "-k"; //$NON-NLS-1$ - private static final String QUOTE = "'"; //$NON-NLS-1$ - - protected Session session; - private Set sentFolders; - protected IProgressMonitor monitor; - private String[] wrappers; - - private FileNameMatcher ignoreMatcher; - private FileNameMatcher wrapMatcher; - - /** - * Constructor for ImportStructureVisitor. - * @param requestSender - * @param mRoot - * @param monitor - */ - public ImportStructureVisitor(Session session, - String[] wrappers, IProgressMonitor monitor) { - - this.session = session; - this.monitor = Policy.infiniteSubMonitorFor(monitor, 512); - this.wrappers = wrappers; - wrapMatcher = initWrapMatcher(wrappers); - } - - - /** - * Inits the wrapMatcher, that is responsible to find out - * whether a file is to be send as a binary (on an import) - * or not. - * - * Takes wrappers of this format: - * *.class -k 'o' - * - * and inits the FileNameMatcher to give - * -ko back if you call it with match("somename.class") - * - * ignores all wrappers, that do not contain -k - */ - private FileNameMatcher initWrapMatcher(String[] wrappers) { - - FileNameMatcher wrapMatcher; - - if (wrappers == null) { - return null; - } - - wrapMatcher = new FileNameMatcher(); - - for (int i = 0; i < wrappers.length; i++) { - - if (wrappers[i].indexOf(KEYWORD_OPTION) == -1) { - continue; - } - - StringTokenizer st = new StringTokenizer(wrappers[i]); - String pattern = st.nextToken(); - String option = st.nextToken(); - // get rid of the quotes - StringTokenizer quoteSt = - new StringTokenizer(st.nextToken(),QUOTE); - option += quoteSt.nextToken(); - - wrapMatcher.register(pattern,option); - } - - return wrapMatcher; - } - - /** - * @see ICVSResourceVisitor#visitFile(IManagedFile) - */ - public void visitFile(ICVSFile mFile) throws CVSException { - if (ignoreMatcher != null && ignoreMatcher.match(mFile.getName())) { - return; - } - - boolean binary = Team.getType((IFile)mFile.getIResource()) == Team.BINARY; - if (wrapMatcher != null) { - String mode = wrapMatcher.getMatch(mFile.getName()); - if (mode != null) binary = KSubstOption.fromMode(mode).isBinary(); - } - session.sendModified(mFile, binary, monitor); - } - - /** - * @see ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder mFolder) throws CVSException { - - if (ignoreMatcher != null && ignoreMatcher.match(mFolder.getName())) { - return; - } - - String localPath = mFolder.getRelativePath(session.getLocalRoot()); - monitor.subTask(Policy.bind("AbstractStructureVisitor.sendingFolder", localPath)); //$NON-NLS-1$ - - session.sendConstructedDirectory(localPath); - mFolder.acceptChildren(this); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Log.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Log.java deleted file mode 100644 index 45d6086cb..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Log.java +++ /dev/null @@ -1,40 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -public class Log extends AbstractMessageCommand { - /*** Local options: specific to log ***/ - - public static LocalOption makeRevisionOption(String revision) { - return new LocalOption("-r" + revision, null); //$NON-NLS-1$ - } - public static final LocalOption RCS_FILE_NAMES_ONLY = new LocalOption("-R"); //$NON-NLS-1$ - - protected Log() { } - protected String getRequestId() { - return "log"; //$NON-NLS-1$ - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Send all folders that are already managed to the server - boolean sendEmptyFolders = Command.findOption(localOptions, RCS_FILE_NAMES_ONLY.getOption()) != null; - new FileStructureVisitor(session, sendEmptyFolders, false /* send modified contents */, monitor).visit(session, resources); - return resources; - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/MTHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/MTHandler.java deleted file mode 100644 index 6e7f20fc3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/MTHandler.java +++ /dev/null @@ -1,105 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; - -public class MTHandler extends ResponseHandler { - - private String nextLine; - private boolean isLineAvailable; - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.client.ResponseHandler#getInstance() - */ - ResponseHandler getInstance() { - return new MTHandler(); - } - - /** - * @see ResponseHandler#getResponseID() - */ - public String getResponseID() { - return "MT"; //$NON-NLS-1$ - } - - /** - * @see ResponseHandler#handle(Session, String, IProgressMonitor) - */ - public void handle(Session session, String argument, IProgressMonitor monitor) - throws CVSException { - - // If there was a line available from before, clear it - if (isLineAvailable()) { - startNextLine(); - } - - if (argument.charAt(0) == '+') { - // Reset any previously accumulated text - startNextLine(); - } else if (argument.charAt(0) == '-') { - // Mark the line as available in case there was no trailing newline - if (nextLine != null) { - isLineAvailable = true; - } - } else { - // Extract the tag and text from the line - String tag; - String text; - int spaceIndex = argument.indexOf(' '); - if (spaceIndex == -1) { - tag = argument; - text = null; - } else { - tag = argument.substring(0, spaceIndex); - text = argument.substring(spaceIndex + 1); - } - - // Accumulate the line and indicate if its available for use - if (tag.equals("newline")) { //$NON-NLS-1$ - isLineAvailable = true; - } else if (text != null) { - // Reset the previous line if required - if (isLineAvailable()) { - startNextLine(); - } - // Accumulate the line - if (nextLine == null) { - nextLine = text; - } else { - // The text from the sevrver contains spaces when appropriate so just append - nextLine = nextLine + text; - } - } - } - } - - /** - * Check if there is a line available. If there is, it should be fetched with - * getLine() immediatly before the next MT response is processed. - */ - public boolean isLineAvailable() { - return isLineAvailable; - } - - /** - * Get the available line. This purges the line from the handler - */ - public String getLine() { - return nextLine; - } - - private void startNextLine() { - isLineAvailable = false; - nextLine = null; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModTimeHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModTimeHandler.java deleted file mode 100644 index 7ccc793e4..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModTimeHandler.java +++ /dev/null @@ -1,49 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.text.ParseException; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.util.CVSDateFormatter; - -/** - * Handles a "Mod-time" response from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Mod-time 18 Oct 2001 20:21:13 -0330\n - * [...] - * </pre> - * Then we parse and remember the date for use in subsequent - * file transfer responses such as Updated. - * </p> - */ -class ModTimeHandler extends ResponseHandler { - public String getResponseID() { - return "Mod-time"; //$NON-NLS-1$ - } - - public void handle(Session session, String timeStamp, - IProgressMonitor monitor) throws CVSException { - try { - session.setModTime(CVSDateFormatter.serverStampToDate(timeStamp)); - } catch (ParseException e) { - throw new CVSException(Policy.bind("ModTimeHandler.invalidFormat", timeStamp), e); //$NON-NLS-1$ - } - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModifiedFileSender.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModifiedFileSender.java deleted file mode 100644 index 27c925d5c..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModifiedFileSender.java +++ /dev/null @@ -1,54 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.HashSet; -import java.util.Set; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; - -/** - * Visit the CVS file structure, only sending files if they are modified. - */ -class ModifiedFileSender extends FileStructureVisitor { - - private final Set modifiedFiles; - - public ModifiedFileSender(Session session, IProgressMonitor monitor) { - super(session, false, true, monitor); - modifiedFiles = new HashSet(); - } - - /** - * Override sendFile to only send modified files - */ - protected void sendFile(ICVSFile mFile) throws CVSException { - // Only send the file if its modified - if (mFile.isManaged() && mFile.isModified(null)) { - super.sendFile(mFile); - modifiedFiles.add(mFile); - } - } - - protected String getSendFileTitleKey() { - return null; - } - - /** - * Return all the files that have been send to the server - */ - public ICVSFile[] getModifiedFiles() { - return (ICVSFile[]) modifiedFiles.toArray(new ICVSFile[modifiedFiles.size()]); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModuleExpansionHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModuleExpansionHandler.java deleted file mode 100644 index f4797416a..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ModuleExpansionHandler.java +++ /dev/null @@ -1,35 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; - -public class ModuleExpansionHandler extends ResponseHandler { - - /* - * @see ResponseHandler#getResponseID() - */ - public String getResponseID() { - return "Module-expansion";//$NON-NLS-1$ - } - - /* - * @see ResponseHandler#handle(Session, String, IProgressMonitor) - */ - public void handle(Session session, String expansion, IProgressMonitor monitor) - throws CVSException { - - session.addModuleExpansion(expansion); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NOOPCommand.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NOOPCommand.java deleted file mode 100644 index 02862e71f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NOOPCommand.java +++ /dev/null @@ -1,57 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -/** - * @author Administrator - * - * To change this generated comment edit the template variable "typecomment": - * Window>Preferences>Java>Templates. - * To enable and disable the creation of type comments go to - * Window>Preferences>Java>Code Generation. - */ -public class NOOPCommand extends Command { - - /** - * @see org.eclipse.team.internal.ccvs.core.client.Command#sendLocalResourceState(Session, GlobalOption[], LocalOption[], ICVSResource[], IProgressMonitor) - */ - protected ICVSResource[] sendLocalResourceState( - Session session, - GlobalOption[] globalOptions, - LocalOption[] localOptions, - ICVSResource[] resources, - IProgressMonitor monitor) - throws CVSException { - - // The noop visitor will send any pending notifications - new NOOPVisitor(session, monitor).visit(session, resources); - return resources; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.client.Request#getRequestId() - */ - protected String getRequestId() { - return "noop"; //$NON-NLS-1$ - } - - /** - * @see org.eclipse.team.internal.ccvs.core.client.Command#sendArguments(Session, String[]) - */ - protected void sendArguments(Session session, String[] arguments)throws CVSException { - // don't send any arguments - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NOOPVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NOOPVisitor.java deleted file mode 100644 index d2eb8ad27..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NOOPVisitor.java +++ /dev/null @@ -1,44 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; - -/** - * Send the contents of the CVS/Notify files to the server - */ -public class NOOPVisitor extends AbstractStructureVisitor { - - public NOOPVisitor(Session session, IProgressMonitor monitor) { - // Only send non-empty folders - super(session, false, false, monitor); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor#visitFile(ICVSFile) - */ - public void visitFile(ICVSFile file) throws CVSException { - sendPendingNotification(file); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder folder) throws CVSException { - if (folder.isCVSFolder()) { - folder.acceptChildren(this); - } - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NewEntryHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NewEntryHandler.java deleted file mode 100644 index 2b143e9f1..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NewEntryHandler.java +++ /dev/null @@ -1,53 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -public class NewEntryHandler extends ResponseHandler { - - /* - * @see ResponseHandler#getResponseID() - */ - public String getResponseID() { - return "New-entry"; //$NON-NLS-1$ - } - - /* - * @see ResponseHandler#handle(Session, String, IProgressMonitor) - */ - public void handle(Session session, String localDir, IProgressMonitor monitor) - throws CVSException { - - // read additional data for the response - String repositoryFile = session.readLine(); - String entryLine = session.readLine(); - - // Clear the recorded mod-time - session.setModTime(null); - - // Get the local file - String fileName = repositoryFile.substring(repositoryFile.lastIndexOf("/") + 1); //$NON-NLS-1$ - ICVSFolder mParent = session.getLocalRoot().getFolder(localDir); - ICVSFile mFile = mParent.getFile(fileName); - - ResourceSyncInfo fileInfo = mFile.getSyncInfo(); - MutableResourceSyncInfo newInfo = fileInfo.cloneMutable(); - newInfo.setEntryLine(entryLine); - mFile.setSyncInfo(newInfo, ICVSFile.UNKNOWN); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NotifiedHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NotifiedHandler.java deleted file mode 100644 index 741a884a2..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/NotifiedHandler.java +++ /dev/null @@ -1,55 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; - -/** - * @author Administrator - * - * To change this generated comment edit the template variable "typecomment": - * Window>Preferences>Java>Templates. - * To enable and disable the creation of type comments go to - * Window>Preferences>Java>Code Generation. - */ -public class NotifiedHandler extends ResponseHandler { - - /** - * @see org.eclipse.team.internal.ccvs.core.client.ResponseHandler#getResponseID() - */ - public String getResponseID() { - return "Notified"; //$NON-NLS-1$ - } - - /** - * @see org.eclipse.team.internal.ccvs.core.client.ResponseHandler#handle(Session, String, IProgressMonitor) - */ - public void handle( - Session session, - String localDir, - IProgressMonitor monitor) - throws CVSException { - - // read additional data for the response - // (which is the full repository path of the file) - String repositoryFilePath = session.readLine(); - - // clear the notify info for the file - ICVSFolder folder = session.getLocalRoot().getFolder(localDir); - ICVSFile file = folder.getFile(new Path(repositoryFilePath).lastSegment()); - file.notificationCompleted(); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/PruneFolderVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/PruneFolderVisitor.java deleted file mode 100644 index 58f2b392e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/PruneFolderVisitor.java +++ /dev/null @@ -1,106 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.HashSet; -import java.util.Iterator; -import java.util.Set; - -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; - -/** - * Goes recursivly through the folders checks if they are empyty - * and deletes them. Of course it is starting at the leaves of the - * recusion (the folders that do not have subfolders). - */ -public class PruneFolderVisitor implements ICVSResourceVisitor { - - private ICVSFolder localRoot; - - public PruneFolderVisitor() { - } - - /** - * This method is used to visit a set of ICVSResources. - */ - public void visit(Session s, ICVSResource[] resources) throws CVSException { - visit(s.getLocalRoot(), resources); - } - - /** - * This method is used to visit a set of ICVSResources. - */ - public void visit(ICVSFolder root, ICVSResource[] resources) throws CVSException { - localRoot = root; - - // Visit the resources - Set prunableParents = new HashSet(); - for (int i = 0; i < resources.length; i++) { - ICVSResource cvsResource = resources[i]; - // prune the resource and it's children when appropriate - cvsResource.accept(this); - // if the resource doesn't exists, attempt to prune it's parent - if (!cvsResource.exists()) - prunableParents.add(cvsResource.getParent()); - } - for (Iterator iter = prunableParents.iterator(); iter.hasNext();) { - ICVSFolder cvsFolder = (ICVSFolder)iter.next(); - pruneFolderAndParentsIfAppropriate(cvsFolder); - } - } - /** - * @see ICVSResourceVisitor#visitFile(IManagedFile) - */ - public void visitFile(ICVSFile file) throws CVSException { - // nothing to do here - } - - /** - * @see ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder folder) throws CVSException { - // First prune any empty children - folder.acceptChildren(this); - // Then prune the folder if it is empty - pruneFolderIfAppropriate(folder); - } - - private void pruneFolderIfAppropriate(ICVSFolder folder) throws CVSException { - // Only prune managed folders that are not the root of the operation - if (folder.exists() && folder.isManaged() - && ! folder.equals(getLocalRoot()) - && folder.members(ICVSFolder.ALL_EXISTING_MEMBERS).length == 0) { - - // Delete the folder but keep a phantom for local folders - folder.delete(); - } - } - - private ICVSFolder getLocalRoot() { - return localRoot; - } - - /** - * Attemp to prunt the given folder. If the folder is pruned, attempt to prune it's parent. - */ - private void pruneFolderAndParentsIfAppropriate(ICVSFolder folder) throws CVSException { - pruneFolderIfAppropriate(folder); - if (!folder.exists()) { - ICVSFolder parent = folder.getParent(); - pruneFolderAndParentsIfAppropriate(parent); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RTag.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RTag.java deleted file mode 100644 index a83cca00b..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RTag.java +++ /dev/null @@ -1,110 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.TagListener; - -public class RTag extends RemoteCommand { - /*** Local options: specific to tag ***/ - public static final LocalOption CREATE_BRANCH = Tag.CREATE_BRANCH; - public static final LocalOption CLEAR_FROM_REMOVED = new LocalOption("-a", null); //$NON-NLS-1$ - public static final LocalOption FORCE_REASSIGNMENT = new LocalOption("-F", null); //$NON-NLS-1$ - - /*** Default command output listener ***/ - private static final ICommandOutputListener DEFAULT_OUTPUT_LISTENER = new TagListener(); - - /** - * Makes a -r or -D option for a tag. - * Valid for: checkout export history rdiff update - */ - public static LocalOption makeTagOption(CVSTag tag) { - int type = tag.getType(); - switch (type) { - case CVSTag.BRANCH: - case CVSTag.VERSION: - case CVSTag.HEAD: - return new LocalOption("-r", tag.getName()); //$NON-NLS-1$ - case CVSTag.DATE: - return new LocalOption("-D", tag.getName()); //$NON-NLS-1$ - default: - // Unknow tag type!!! - throw new IllegalArgumentException(); - } - } - - protected String getRequestId() { - return "rtag"; //$NON-NLS-1$ - } - - protected ICVSResource[] computeWorkResources(Session session, LocalOption[] localOptions, - String[] arguments) throws CVSException { - if (arguments.length < 2) throw new IllegalArgumentException(); - return super.computeWorkResources(session, localOptions, arguments); - } - - public IStatus execute(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, CVSTag sourceTag, CVSTag tag, String[] arguments, - IProgressMonitor monitor) throws CVSException { - - if(tag.getType() != CVSTag.VERSION && tag.getType() != CVSTag.BRANCH) { - throw new CVSException(new CVSStatus(IStatus.ERROR, Policy.bind("Tag.notVersionOrBranchError"))); //$NON-NLS-1$ - } - - // Add the source tag to the local options - List modifiedLocalOptions = new ArrayList(localOptions.length + 1); - if (sourceTag==null) sourceTag = CVSTag.DEFAULT; - modifiedLocalOptions.addAll(Arrays.asList(localOptions)); - modifiedLocalOptions.add(makeTagOption(sourceTag)); - - // Add the CREATE_BRANCH option for a branch tag - if (tag.getType() == CVSTag.BRANCH) { - if ( ! CREATE_BRANCH.isElementOf(localOptions)) { - modifiedLocalOptions.add(CREATE_BRANCH); - } - } - - // Add the tag name to the start of the arguments - String[] newArguments = new String[arguments.length + 1]; - newArguments[0] = tag.getName(); - System.arraycopy(arguments, 0, newArguments, 1, arguments.length); - - return execute(session, globalOptions, - (LocalOption[]) modifiedLocalOptions.toArray(new LocalOption[modifiedLocalOptions.size()]), - newArguments, null, monitor); - } - - public IStatus execute(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions, - CVSTag sourceTag, CVSTag tag, ICVSRemoteResource[] arguments, IProgressMonitor monitor) - throws CVSException { - - ICVSResource[] resources = (ICVSResource[])Arrays.asList(arguments).toArray(new ICVSResource[arguments.length]); - String[] stringArguments = convertArgumentsForOpenSession(arguments); - - return execute(session, globalOptions, localOptions, sourceTag, tag, stringArguments, monitor); - } - - protected ICommandOutputListener getDefaultCommandOutputListener() { - return DEFAULT_OUTPUT_LISTENER; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemoteCommand.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemoteCommand.java deleted file mode 100644 index f07e4a857..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemoteCommand.java +++ /dev/null @@ -1,50 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -/** - * This class acts as a super class for those CVS commands that do not send up the local file structure - */ -public abstract class RemoteCommand extends Command { - - protected ICVSResource[] computeWorkResources(Session session, LocalOption[] localOptions, - String[] arguments) throws CVSException { - return new ICVSResource[0]; - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - // do nothing - return resources; - } - - protected void sendLocalWorkingDirectory(Session session) throws CVSException { - // do nothing - } - - protected String[] convertArgumentsForOpenSession(ICVSRemoteResource[] arguments) throws CVSException { - // Convert arguments - List stringArguments = new ArrayList(arguments.length); - for (int i = 0; i < arguments.length; i++) { - stringArguments.add(arguments[i].getRepositoryRelativePath()); - } - return (String[]) stringArguments.toArray(new String[stringArguments.size()]); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Remove.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Remove.java deleted file mode 100644 index bec93f4e8..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Remove.java +++ /dev/null @@ -1,36 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -public class Remove extends Command { - /*** Local options: specific to remove ***/ - - protected Remove() { } - protected String getRequestId() { - return "remove"; //$NON-NLS-1$ - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Send all modified files to the server - // XXX Does the command line client send all modified files? - new ModifiedFileSender(session, monitor).visit(session, resources); - return resources; - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemoveEntryHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemoveEntryHandler.java deleted file mode 100644 index 4d8a7ef23..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemoveEntryHandler.java +++ /dev/null @@ -1,55 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; - -/** - * Handles a "Remove-entry" response from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Remove-entry ??? \n - * [...] - * </pre> - * Then - * </p> - */ - -/** - * It removes the file from both the entries of the parent-folder. - * This happen, when the folder has allready been removed locally - * what happens on a checkin that includes a removed file. - */ -class RemoveEntryHandler extends ResponseHandler { - public String getResponseID() { - return "Remove-entry"; //$NON-NLS-1$ - } - - public void handle(Session session, String localDir, - IProgressMonitor monitor) throws CVSException { - // read additional data for the response - String repositoryFile = session.readLine(); - - // Get the local file - String fileName = repositoryFile.substring(repositoryFile.lastIndexOf("/") + 1); //$NON-NLS-1$ - ICVSFolder mParent = session.getLocalRoot().getFolder(localDir); - ICVSFile mFile = mParent.getFile(fileName); - mFile.unmanage(null); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemovedHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemovedHandler.java deleted file mode 100644 index 15ec09e62..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/RemovedHandler.java +++ /dev/null @@ -1,64 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.Policy; - -/** - * Handles a "Removed" response from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Removed ??? \n - * [...] - * </pre> - * Then - * </p> - */ - -/** - * It removes the file from both the entries of the parent-folder - * and from the local filesystem. - */ -class RemovedHandler extends ResponseHandler { - public String getResponseID() { - return "Removed"; //$NON-NLS-1$ - } - - public void handle(Session session, String localDir, IProgressMonitor monitor) throws CVSException { - - // read additional data for the response - String repositoryFile = session.readLine(); - - // Get the local file - String fileName = repositoryFile.substring(repositoryFile.lastIndexOf("/") + 1); //$NON-NLS-1$ - ICVSFolder mParent = session.getLocalRoot().getFolder(localDir); - ICVSFile mFile = mParent.getFile(fileName); - - if ( ! mFile.isManaged()) { - throw new CVSException(Policy.bind("RemovedHandler.invalid", new Path(localDir).append(fileName).toString())); //$NON-NLS-1$ - } - - // delete then unmanage the file - if (mFile.isReadOnly()) mFile.setReadOnly(false); - mFile.delete(); - mFile.unmanage(null); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Request.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Request.java deleted file mode 100644 index 5066ce408..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Request.java +++ /dev/null @@ -1,256 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.MultiStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.IConsoleListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; - -/** - * Abstract base class for requests that are to be sent to the server. - */ -public abstract class Request { - public static final ExpandModules EXPAND_MODULES = new ExpandModules(); - public static final ValidRequests VALID_REQUESTS = new ValidRequests(); - - /*** Response handler map ***/ - private static final Map responseHandlers = new HashMap(); - - private static void initializeHandlerCache() { - synchronized(responseHandlers) { - registerResponseHandler(new CheckedInHandler()); - registerResponseHandler(new CopyHandler()); - registerResponseHandler(new ModTimeHandler()); - registerResponseHandler(new NewEntryHandler()); - registerResponseHandler(new RemovedHandler()); - registerResponseHandler(new RemoveEntryHandler()); - registerResponseHandler(new StaticHandler(true)); - registerResponseHandler(new StaticHandler(false)); - registerResponseHandler(new StickyHandler(true)); - registerResponseHandler(new StickyHandler(false)); - registerResponseHandler(new UpdatedHandler(UpdatedHandler.HANDLE_UPDATED)); - registerResponseHandler(new UpdatedHandler(UpdatedHandler.HANDLE_UPDATE_EXISTING)); - registerResponseHandler(new UpdatedHandler(UpdatedHandler.HANDLE_CREATED)); - registerResponseHandler(new UpdatedHandler(UpdatedHandler.HANDLE_MERGED)); - registerResponseHandler(new ValidRequestsHandler()); - registerResponseHandler(new ModuleExpansionHandler()); - registerResponseHandler(new MTHandler()); - registerResponseHandler(new NotifiedHandler()); - registerResponseHandler(new TemplateHandler()); - } - } - private static void registerResponseHandler(ResponseHandler handler) { - synchronized(responseHandlers) { - responseHandlers.put(handler.getResponseID(), handler); - } - } - - /** - * This method is invoked by Session to get a mutable copy of the - * global list of acceptable response handlers. - * - * @return a map of reponse handlers - */ - protected static Map getReponseHandlerMap() { - synchronized(responseHandlers) { - if (responseHandlers.isEmpty()) { - initializeHandlerCache(); - } - Map copy = new HashMap(); - for (Iterator iter = responseHandlers.values().iterator(); iter.hasNext();) { - ResponseHandler handler = (ResponseHandler) iter.next(); - copy.put(handler.getResponseID(), handler.getInstance()); - - } - return copy; - } - } - /** - * Prevents client code from instantiating us. - */ - protected Request() { } - - /** - * Returns the string used to invoke this request on the server. - * [template method] - * - * @return the request identifier string - */ - protected abstract String getRequestId(); - - /** - * Executes a request and processes the responses. - * - * @param session the open CVS session - * @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 - */ - protected IStatus executeRequest(Session session, ICommandOutputListener listener, - IProgressMonitor monitor) throws CVSException { - // send request - session.sendRequest(getRequestId()); - - // This number can be tweaked if the monitor is judged to move too - // quickly or too slowly. After some experimentation this is a good - // number for both large projects (it doesn't move so quickly as to - // give a false sense of speed) and smaller projects (it actually does - // move some rather than remaining still and then jumping to 100). - final int TOTAL_WORK = 300; - monitor.beginTask(Policy.bind("Command.receivingResponses"), TOTAL_WORK); //$NON-NLS-1$ - int halfWay = TOTAL_WORK / 2; - int currentIncrement = 4; - int nextProgress = currentIncrement; - int worked = 0; - - // If the session is connected to a CVSNT server (1.11.1.1), we'll need to do some special handling for - // some errors. Unfortunately, CVSNT 1.11.1.1 will drop the connection after so some functionality is - // still effected - boolean isCVSNT = session.isCVSNT(); - - List accumulatedStatus = new ArrayList(); - for (;;) { - // update monitor work amount - if (--nextProgress <= 0) { - monitor.worked(1); - worked++; - if (worked >= halfWay) { - // we have passed the current halfway point, so double the - // increment and reset the halfway point. - currentIncrement *= 2; - halfWay += (TOTAL_WORK - halfWay) / 2; - } - // reset the progress counter to another full increment - nextProgress = currentIncrement; - } - Policy.checkCanceled(monitor); - - // retrieve a response line - String response = session.readLine(); - int spacePos = response.indexOf(' '); - String argument; - if (spacePos != -1) { - argument = response.substring(spacePos + 1); - response = response.substring(0, spacePos); - } else argument = ""; //$NON-NLS-1$ - - // handle completion responses - if (response.equals("ok")) { //$NON-NLS-1$ - break; - } else if (response.equals("error") || (isCVSNT && response.equals(""))) { //$NON-NLS-1$ //$NON-NLS-2$ - argument = argument.trim(); - boolean serious = false; - if (argument.length() == 0) { - argument = getServerErrorMessage(); - } else { - argument = Policy.bind("Command.seriousServerError", argument); //$NON-NLS-1$ - if (!accumulatedStatus.isEmpty()) { - accumulatedStatus.add(new CVSStatus(CVSStatus.ERROR, CVSStatus.SERVER_ERROR, argument)); - } - serious = true; - } - - if (accumulatedStatus.isEmpty()) { - accumulatedStatus.add(new CVSStatus(CVSStatus.ERROR, CVSStatus.SERVER_ERROR, Policy.bind("Command.noMoreInfoAvailable")));//$NON-NLS-1$ - } - IStatus status = new MultiStatus(CVSProviderPlugin.ID, CVSStatus.SERVER_ERROR, - (IStatus[]) accumulatedStatus.toArray(new IStatus[accumulatedStatus.size()]), - argument, null); - if (serious) { - throw new CVSServerException(status); - } else { - // look for particularly bad errors in the accumulated statii - for (Iterator iter = accumulatedStatus.iterator(); iter.hasNext();) { - IStatus s = (IStatus) iter.next(); - if (s.getCode() == CVSStatus.PROTOCOL_ERROR) { - throw new CVSServerException(status); - } - } - } - return status; - // handle message responses - } else if (response.equals("MT")) { //$NON-NLS-1$ - // Handle the MT response - MTHandler handler = (MTHandler) session.getResponseHandler(response); - if (handler != null) { - handler.handle(session, argument, monitor); - } else { - throw new CVSException(new org.eclipse.core.runtime.Status(IStatus.ERROR, - CVSProviderPlugin.ID, CVSException.IO_FAILED, - Policy.bind("Command.unsupportedResponse", response, argument), null)); //$NON-NLS-1$ - } - // If a line is available, pass it on to the message listener - // and console as if it were an M response - if (handler.isLineAvailable()) { - String line = handler.getLine(); - IStatus status = listener.messageLine(line, session.getCVSRepositoryLocation(), session.getLocalRoot(), monitor); - if (status != ICommandOutputListener.OK) accumulatedStatus.add(status); - if (session.isOutputToConsole()) { - IConsoleListener consoleListener = CVSProviderPlugin.getPlugin().getConsoleListener(); - if (consoleListener != null) consoleListener.messageLineReceived(line); - } - } - } else if (response.equals("M")) { //$NON-NLS-1$ - IStatus status = listener.messageLine(argument, session.getCVSRepositoryLocation(), session.getLocalRoot(), monitor); - if (status != ICommandOutputListener.OK) accumulatedStatus.add(status); - if (session.isOutputToConsole()) { - IConsoleListener consoleListener = CVSProviderPlugin.getPlugin().getConsoleListener(); - if (consoleListener != null) consoleListener.messageLineReceived(argument); - } - } else if (response.equals("E")) { //$NON-NLS-1$ - IStatus status = listener.errorLine(argument, session.getCVSRepositoryLocation(), session.getLocalRoot(), monitor); - if (status != ICommandOutputListener.OK) accumulatedStatus.add(status); - if (session.isOutputToConsole()) { - IConsoleListener consoleListener = CVSProviderPlugin.getPlugin().getConsoleListener(); - if (consoleListener != null) consoleListener.errorLineReceived(argument); - } - // handle other responses - } else { - ResponseHandler handler = (ResponseHandler) session.getResponseHandler(response); - if (handler != null) { - handler.handle(session, argument, monitor); - } else { - throw new CVSException(new org.eclipse.core.runtime.Status(IStatus.ERROR, - CVSProviderPlugin.ID, CVSException.IO_FAILED, - Policy.bind("Command.unsupportedResponse", response, argument), null)); //$NON-NLS-1$ - } - } - } - if (accumulatedStatus.isEmpty()) { - return ICommandOutputListener.OK; - } else { - return new MultiStatus(CVSProviderPlugin.ID, CVSStatus.INFO, - (IStatus[]) accumulatedStatus.toArray(new IStatus[accumulatedStatus.size()]), - Policy.bind("Command.warnings", Policy.bind("Command." + getRequestId())), null); //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /* - * Provide the message that is used for the status that is generated when the server - * reports as error. - */ - protected String getServerErrorMessage() { - return Policy.bind("Command.serverError", Policy.bind("Command." + getRequestId())); //$NON-NLS-1$ //$NON-NLS-2$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ResponseHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ResponseHandler.java deleted file mode 100644 index e3a00037e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ResponseHandler.java +++ /dev/null @@ -1,187 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResourceStatus; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * Handles server responses that arise as a result of issuing a request - * (usually a command) to a CVS server. The processing of each such - * response is deferred to subclasses. - */ -public abstract class ResponseHandler { - /** - * Returns the text string of the server response handled by this object. - * @return the id - */ - public abstract String getResponseID(); - - /** - * Handles a server response. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Clear-sticky myDirectory \n - * /u/cvsroot/myDirectory \n - * [...] - * </pre> - * Then the <code>handle</code> method of the <code>ResponseHandler</code> - * for <em>Clear-sticky</em> will be invoked with <code>argument</code> - * set to <em>"myDirectory"</em>. It must then read the remaining - * response data from the connection (<em>"/u/cvsroot/myDirectory"</em> - * including the newline) and take any necessary action. - * </p><p> - * Note: The type and quantity of additional data that must be read - * from the connection varies on a per-response basis. - * </p> - * @param session the Session used for CVS communication - * @param argument the argument supplied with the response - * @param monitor the progress monitor for the current CVS command - */ - public abstract void handle(Session session, String argument, - IProgressMonitor monitor) throws CVSException; - - /** - * Creates a new CVS folder. - * @param localDir the local path of the folder relative to root - * @param repositoryDir the remote path of the folder relative to the repository - * @return the new folder - */ - protected static ICVSFolder createFolder( - Session session, - String localDir, - String repositoryDir) throws CVSException { - - ICVSFolder folder = session.getLocalRoot().getFolder(localDir); - if (! folder.exists()) { - try { - folder.mkdir(); - } catch (CVSException original) { - boolean caseInvariant = false; - switch (original.getStatus().getCode()) { - case IResourceStatus.CASE_VARIANT_EXISTS : - // We will try to create the mapped child below. - caseInvariant = true; - break; - - case IResourceStatus.RESOURCE_NOT_FOUND : - // The parent of the folder doesn't exist. It could be due to case invariance. - // Check if there is a case invariant mapping for the folder - String actualLocalDir = session.getUniquePathForCaseSensitivePath(localDir, false); - folder = session.getLocalRoot().getFolder(actualLocalDir); - try { - if (! folder.exists()) folder.mkdir(); - // We succeed in creating the child of a mapped parent - // Since caseInvariant is false, we will fall through - } catch (CVSException ex) { - if (ex.getStatus().getCode() == IResourceStatus.CASE_VARIANT_EXISTS) { - // We will try to create he mapped child below. - caseInvariant = true; - } else { - // The attempt to get the mapped parent failed. - // Throw the original exception - throw original; - } - } - break; - - case IResourceStatus.INVALID_VALUE : - // the folder name is not supported by the platform. Try to compensate. - String validLocalDir = session.getUniquePathForInvalidPath(localDir); - folder = session.getLocalRoot().getFolder(validLocalDir); - try { - if (! folder.exists()) folder.mkdir(); - // We succeed in creating the child of a mapped parent - // Since caseInvariant is false, we will fall through - } catch (CVSException ex) { - // The attempt to get a unique path failed. - // Throw the original exception - throw original; - } - break; - default : - throw original; - - } - if (caseInvariant) { - // Change the name (last segment) of the localDir to a unique name for the case invariant one - String newlocalDir = session.getUniquePathForCaseSensitivePath(localDir, true); - folder = session.getLocalRoot().getFolder(newlocalDir); - if (! folder.exists()) folder.mkdir(); - // Signal to the session that there is a renamed folder. - session.addCaseCollision(localDir, newlocalDir); - } - } - } - if (! folder.isCVSFolder()) { - folder.setFolderSyncInfo(new FolderSyncInfo( - Util.getRelativePath(session.getRepositoryRoot(), repositoryDir), - session.getCVSRepositoryLocation().getLocation(), - null, false)); - } - return folder; - } - - protected ICVSFolder getExistingFolder(Session session, String localDir) - throws CVSException { - ICVSFolder mParent = session.getLocalRoot().getFolder(localDir); - if (! mParent.exists()) { - // First, check if the parent is a phantom - IContainer container = (IContainer)mParent.getIResource(); - if (container != null && container.isPhantom()) { - // Create all the parents as need - recreatePhatomFolders(mParent); - } else { - // It is possible that we have a case variant. - localDir = session.getUniquePathForCaseSensitivePath(localDir, false); - mParent = session.getLocalRoot().getFolder(localDir); - if (!mParent.exists()) { - // It is also possible that the path is invalid for this platform - localDir = session.getUniquePathForInvalidPath(localDir); - mParent = session.getLocalRoot().getFolder(localDir); - Assert.isTrue(mParent.exists()); - } - } - } - return mParent; - } - - /** - * Method recreatePhatomFolders. - * @param mParent - */ - private void recreatePhatomFolders(ICVSFolder folder) throws CVSException { - ICVSFolder parent = folder.getParent(); - if (!parent.exists()) { - recreatePhatomFolders(parent); - } - folder.mkdir(); - } - - /** - * Return as instance that can be used by an open session. Subclasses that contain - * session related state must override this message to return a copy of themselves. - */ - /* package */ ResponseHandler getInstance() { - return this; - } -} - 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 deleted file mode 100644 index 1c6844236..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Session.java +++ /dev/null @@ -1,1141 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.io.ByteArrayInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.Collection; -import java.util.Collections; -import java.util.Comparator; -import java.util.Date; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.zip.GZIPInputStream; -import java.util.zip.GZIPOutputStream; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -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.NullProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -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.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command.GlobalOption; -import org.eclipse.team.internal.ccvs.core.client.Command.QuietOption; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.connection.Connection; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.Util; -import org.eclipse.team.internal.core.streams.CRLFtoLFInputStream; -import org.eclipse.team.internal.core.streams.LFtoCRLFInputStream; -import org.eclipse.team.internal.core.streams.ProgressMonitorInputStream; -import org.eclipse.team.internal.core.streams.SizeConstrainedInputStream; - -/** - * Maintains CVS communication state for the lifetime of a connection - * to a remote repository. This class covers the initialization, use, - * and eventual shutdown of a dialogue between a CVS client and a - * remote server. This dialogue may be monitored through the use of - * a console. - * - * Initially the Session is in a CLOSED state during which communication - * with the server cannot take place. Once OPENED, any number of commands - * may be issued serially to the server, one at a time. When finished, the - * Session MUST be CLOSED once again to prevent eventual local and/or - * remote resource exhaustion. The session can either be discarded, or - * re-opened for use with the same server though no state is persisted from - * previous connections except for console attributes. - * - * CVSExceptions are thrown only as a result of unrecoverable errors. Once - * this happens, commands must no longer be issued to the server. If the - * Session is in the OPEN state, it is still the responsibility of the - * caller to CLOSE it before moving on. - */ -public class Session { - public static final String CURRENT_LOCAL_FOLDER = "."; //$NON-NLS-1$ - public static final String CURRENT_REMOTE_FOLDER = ""; //$NON-NLS-1$ - public static final String SERVER_SEPARATOR = "/"; //$NON-NLS-1$ - - // default file transfer buffer size (in bytes) - private static final int TRANSFER_BUFFER_SIZE = 8192; - // update progress bar in increments of this size (in bytes) - // no incremental progress shown for files smaller than this size - private static final int TRANSFER_PROGRESS_INCREMENT = 32768; - - private static final boolean IS_CRLF_PLATFORM = Arrays.equals( - System.getProperty("line.separator").getBytes(), new byte[] { '\r', '\n' }); //$NON-NLS-1$ - - private CVSRepositoryLocation location; - private ICVSFolder localRoot; - private boolean outputToConsole; - private Connection connection = null; - private String validRequests = null; - private Date modTime = null; - private boolean noLocalChanges = false; - private boolean createBackups = true; - private int compressionLevel = 0; - private List expansions; - private Collection /* of ICVSFile */ textTransferOverrideSet = null; - private Map caseMappings; - - // state need to indicate whether - private boolean ignoringLocalChanges = false; - - // The resource bundle key that provides the file sending message - private String sendFileTitleKey; - private Map responseHandlers; - - /** - * Creates a new CVS session, initially in the CLOSED state. - * By default, command output is directed to the console. - * - * @param location the CVS repository location used for this session - * @param localRoot represents the current working directory of the client - */ - public Session(ICVSRepositoryLocation location, ICVSFolder localRoot) { - this(location, localRoot, true); - } - - /** - * Creates a new CVS session, initially in the CLOSED state. - * - * @param location the CVS repository location used for this session - * @param localRoot represents the current working directory of the client - * @param outputToConsole if true, command output is directed to the console - */ - public Session(ICVSRepositoryLocation location, ICVSFolder localRoot, boolean outputToConsole) { - this.location = (CVSRepositoryLocation) location; - this.localRoot = localRoot; - this.outputToConsole = outputToConsole; - } - - /** - * Register a case collision with the session. - * - * For folders, the desired path is where the folder should be and the actual path - * is where is was put temporarily. If one of the folders involved is pruned, the - * other can be placed properly (see Session#handleCaseCollisions()) - * - * For files, the desired path is where the file should be and the actual path is - * the emtpy path indicating that the resource was not loaded. - * - * This makes sense because the files in a folder are always communicated before the folders - * so a file can only collide with anothe file which can never be pruned so there's no - * point in loading the file in a temporary place. - */ - protected void addCaseCollision(String desiredLocalPath, String actualLocalPath) { - if (caseMappings == null) caseMappings = new HashMap(); - IPath desiredPath = new Path(desiredLocalPath); - IPath actualPath = new Path(actualLocalPath); - Assert.isTrue(actualPath.equals(Path.EMPTY) || (desiredPath.segmentCount() == actualPath.segmentCount())); - caseMappings.put(desiredPath, actualPath); - } - /* - * Add a module expansion receivered from the server. - * This is only used by the ModuleExpansionsHandler - */ - protected void addModuleExpansion(String expansion) { - expansions.add(expansion); - } - - /* - * Add a module expansion receivered from the server. - * This is only used by the ExpandModules command - */ - protected void resetModuleExpansion() { - if (expansions == null) - expansions = new ArrayList(); - else - expansions.clear(); - } - - /** - * Opens, authenticates and initializes a connection to the server specified - * for the remote location. - * - * @param monitor the progress monitor - * @throws IllegalStateException if the Session is not in the CLOSED state - */ - public void open(IProgressMonitor monitor) throws CVSException { - if (connection != null) throw new IllegalStateException(); - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - boolean opened = false; - - try { - connection = location.openConnection(Policy.subMonitorFor(monitor, 50)); - - // If we're connected to a CVSNT server or we don't know the platform, - // accept MT. Otherwise don't. - boolean useMT = ! (location.getServerPlatform() == CVSRepositoryLocation.CVS_SERVER); - if ( ! useMT) { - removeResponseHandler("MT"); //$NON-NLS-1$ - } - - // tell the server the names of the responses we can handle - connection.writeLine("Valid-responses " + makeResponseList()); //$NON-NLS-1$ - - // ask for the set of valid requests - IStatus status = Request.VALID_REQUESTS.execute(this, Policy.subMonitorFor(monitor, 40)); - if (!status.isOK()) { - throw new CVSException(status); - } - - // set the root directory on the server for this connection - connection.writeLine("Root " + getRepositoryRoot()); //$NON-NLS-1$ - - // enable compression - compressionLevel = CVSProviderPlugin.getPlugin().getCompressionLevel(); - if (compressionLevel != 0 && isValidRequest("gzip-file-contents")) { //$NON-NLS-1$ - // Enable the use of CVS 1.8 per-file compression mechanism. - // The newer Gzip-stream request seems to be problematic due to Java's - // GZIPInputStream tendency to block on read() rather than to return a - // partially filled buffer. The latter option would be better since it - // can make more effective use of the code dictionary, if it can be made - // to work... - connection.writeLine("gzip-file-contents " + Integer.toString(compressionLevel)); //$NON-NLS-1$ - } else { - compressionLevel = 0; - } - - // get the server platform if it is unknown - if (CVSProviderPlugin.getPlugin().isDetermineVersionEnabled() && location.getServerPlatform() == CVSRepositoryLocation.UNDETERMINED_PLATFORM) { - Command.VERSION.execute(this, location, Policy.subMonitorFor(monitor, 10)); - } - opened = true; - } finally { - if (connection != null && ! opened) { - try { - close(); - } catch (CVSException ex) { - CVSProviderPlugin.log(ex); - } - } - monitor.done(); - } - } - - /** - * Closes a connection to the server. - * - * @throws IllegalStateException if the Session is not in the OPEN state - */ - public void close() throws CVSException { - if (connection != null) { - connection.close(); - connection = null; - validRequests = null; - } - } - - /** - * Determines if the server supports the specified request. - * - * @param request the request string to verify - * @return true iff the request is supported - */ - public boolean isValidRequest(String request) { - return (validRequests == null) || - (validRequests.indexOf(" " + request + " ") != -1); //$NON-NLS-1$ //$NON-NLS-2$ - } - - public boolean isCVSNT() { - if (location.getServerPlatform() == CVSRepositoryLocation.UNDETERMINED_PLATFORM) { - return location.getRootDirectory().indexOf(':') == 1; - } else { - return location.getServerPlatform() == CVSRepositoryLocation.CVSNT_SERVER; - } - } - - /** - * Return a local path that can be used to uniquely identify a resource - * if the platform does not support case variant names and there is a name collision - */ - protected String getUniquePathForCaseSensitivePath(String localPath, boolean creatingFolder) { - IPath path = new Path(localPath); - IPath existingMapping = null; - if (caseMappings != null) { - // Look for an existing parent path that has already been mapped - for (int i = 0; i < path.segmentCount(); i++) { - IPath key = path.removeLastSegments(i); - existingMapping = (IPath)caseMappings.get(key); - if (existingMapping != null) break; - } - } - if (existingMapping != null) { - if (existingMapping.segmentCount() == path.segmentCount()) { - return existingMapping.toString(); - } - // Convert the path to the mapped path - path = existingMapping.append(path.removeFirstSegments(existingMapping.segmentCount())); - } - if (creatingFolder) { - // Change the name of the folder to a case insensitive one - String folderName = path.lastSegment(); - // XXX We should ensure that each permutation of characters is unique - folderName = getUniqueNameForCaseVariant(folderName); - path = path.removeLastSegments(1).append(folderName); - } - return path.toString(); - } - - /* - * Return a name that is unique for a give case variant. - */ - private String getUniqueNameForCaseVariant(String name) { - char[] buffer = new char[name.length() * 2]; - int position = 0; - for (int i = 0; i < name.length(); i++) { - char c = name.charAt(i); - buffer[position++] = c; - if (Character.isLetter(c)) { - if (Character.isUpperCase(c)) { - buffer[position++] = '-'; - } else { - buffer[position++] = '_'; - } - } - } - return new String(buffer, 0, position); - } - - /** - * Returns the local root folder for this session. - * <p> - * Generally speaking, specifies the "current working directory" at - * the time of invocation of an equivalent CVS command-line client. - * </p> - * - * @return the local root folder - */ - public ICVSFolder getLocalRoot() { - return localRoot; - } - - /** - * Return the list of module expansions communicated from the server. - * - * The modules expansions are typically a directory path of length 1 - * but can be of greater length on occasion. - */ - public String[] getModuleExpansions() { - if (expansions == null) return new String[0]; - return (String[]) expansions.toArray(new String[expansions.size()]); - } - - /** - * Returns the repository root folder for this session. - * <p> - * Specifies the unqualified path to the CVS repository root folder - * on the server. - * </p> - * - * @return the repository root folder - */ - public String getRepositoryRoot() { - return location.getRootDirectory(); - } - - /** - * Returns an object representing the CVS repository location for this session. - * - * @return the CVS repository location - */ - public ICVSRepositoryLocation getCVSRepositoryLocation() { - return location; - } - - private IContainer getIResourceFor(ICVSFolder cvsFolder) throws CoreException, CVSException { - if (cvsFolder.isManaged()) { - return getIResourceFor(cvsFolder.getParent()).getFolder(new Path(cvsFolder.getName())); - } else { - return ResourcesPlugin.getWorkspace().getRoot().getProject(cvsFolder.getName()); - } - } - - protected void handleCaseCollisions() throws CVSException { - // Handle any case variant mappings - Map mappings = caseMappings; - if (mappings == null || mappings.size() == 0) return; - // We need to start at the longest paths and work to the shortest - // in case there are nested case collisions - List sortedCollisions = new ArrayList(); - sortedCollisions.addAll(mappings.keySet()); - Collections.sort(sortedCollisions, new Comparator() { - public int compare(Object arg0, Object arg1) { - int length0 = ((IPath)arg0).segmentCount(); - int length1 = ((IPath)arg1).segmentCount(); - if (length0 == length1) { - return arg0.toString().compareTo(arg1.toString()); - } - return length0 > length1 ? -1 : 1; - } - }); - // For each mapping, we need to see if one of the culprits was pruned - List unhandledMappings = new ArrayList(); - Iterator iterator = sortedCollisions.iterator(); - while (iterator.hasNext()) { - IPath desiredPath = (IPath)iterator.next(); - IPath actualPath = (IPath)mappings.get(desiredPath); - // Check for the empty path (i.e. unloaded file) - if (actualPath.equals(Path.EMPTY)) { - unhandledMappings.add(desiredPath); - continue; - } - // Check if the actualPath still exists (it may have been pruned) - ICVSFolder actualFolder = getLocalRoot().getFolder(actualPath.toString()); - if ( ! actualFolder.exists()) continue; - // Check if the desiredPath exists (we can only do this by trying to create it - ICVSFolder desiredFolder = getLocalRoot().getFolder(desiredPath.toString()); - try { - desiredFolder.mkdir(); - desiredFolder.delete(); - } catch (CVSException e) { - // Must still exists. Delete the collision - actualFolder.delete(); - actualFolder.unmanage(null); - unhandledMappings.add(desiredPath); - continue; - } - // The desired location is open (probably due to pruning) - try { - // We need to get the IResource for the actual and desired locations - IResource actualResource = getIResourceFor(actualFolder); - IResource desiredResource = actualResource.getParent().getFolder(new Path(desiredFolder.getName())); - // Move the actual to the desired location - actualResource.move(desiredResource.getFullPath(), false, null); - // We need to also move the sync info. Since sync info is a session property - // of the object, we can simpy reset the info for each moved resource - desiredFolder.accept(new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - file.setSyncBytes(file.getSyncBytes(), ICVSFile.UNKNOWN); - } - public void visitFolder(ICVSFolder folder) throws CVSException { - folder.setFolderSyncInfo(folder.getFolderSyncInfo()); - folder.acceptChildren(this); - } - }); - // Unmanage the old location in order to remove the entry from the parent - actualFolder.unmanage(null); - } catch (CoreException e) { - CVSProviderPlugin.log(e); - unhandledMappings.add(desiredPath); - } - } - - if (unhandledMappings.size() > 0) { - MultiStatus status = new MultiStatus(CVSProviderPlugin.ID, CVSStatus.CASE_VARIANT_EXISTS, Policy.bind("PruneFolderVisitor.caseVariantsExist"), null);//$NON-NLS-1$ - Iterator iter = unhandledMappings.iterator(); - while (iter.hasNext()) { - IPath desiredPath = (IPath) iter.next(); - IPath actualPath = (IPath)mappings.get(desiredPath); - status.add(new CVSStatus(IStatus.ERROR, CVSStatus.CASE_VARIANT_EXISTS, - Policy.bind("PruneFolderVisitor.caseVariantExists", desiredPath.toString())));//$NON-NLS-1$ - } - if (status.getChildren().length == 1) { - throw new CVSException(status.getChildren()[0]); - } else { - throw new CVSException(status); - } - } - } - - /** - * Receives a line of text minus the newline from the server. - * - * @return the line of text - */ - public String readLine() throws CVSException { - return connection.readLine(); - } - - /** - * Sends a line of text followed by a newline to the server. - * - * @param line the line of text - */ - public void writeLine(String line) throws CVSException { - connection.writeLine(line); - } - - /** - * Sends an argument to the server. - * <p>e.g. sendArgument("Hello\nWorld\n Hello World") sends: - * <pre> - * Argument Hello \n - * Argumentx World \n - * Argumentx Hello World \n - * </pre></p> - * - * @param arg the argument to send - */ - public void sendArgument(String arg) throws CVSException { - connection.write("Argument "); //$NON-NLS-1$ - int oldPos = 0; - for (;;) { - int pos = arg.indexOf('\n', oldPos); - if (pos == -1) break; - connection.writeLine(arg.substring(oldPos, pos)); - connection.write("Argumentx "); //$NON-NLS-1$ - oldPos = pos + 1; - } - connection.writeLine(arg.substring(oldPos)); - } - - /** - * Sends a request to the server and flushes any output buffers. - * - * @param requestId the string associated with the request to be executed - */ - public void sendRequest(String requestId) throws CVSException { - connection.writeLine(requestId); - connection.flush(); - } - - /** - * Sends an Is-modified request to the server without the file contents. - * <p>e.g. if a file called "local_file" was modified, sends: - * <pre> - * Is-modified local_file \n - * </pre></p><p> - * This request is an optimized form of the Modified request and may not - * be supported by all servers. Hence, if it is not supported, a Modified - * request is sent instead along with the file's contents. According to - * the CVS protocol specification, this request is only safe for use with - * some forms of: admin, annotate, diff, editors, log, watch-add, watch-off, - * watch-on, watch-remove, and watchers.<br> - * It may be possible to use this for: add, export, remove and status.<br> - * Do not use with co, ci, history, init, import, release, rdiff, rtag, or update. - * </p><p> - * Note: The most recent Directory request must have specified the file's - * parent folder. - * </p> - * - * @param file the file that was modified - * @see #sendModified - */ - public void sendIsModified(ICVSFile file, boolean isBinary, IProgressMonitor monitor) - throws CVSException { - if (isValidRequest("Is-modified")) { //$NON-NLS-1$ - connection.writeLine("Is-modified " + file.getName()); //$NON-NLS-1$ - } else { - sendModified(file, isBinary, monitor); - } - } - - /** - * Sends a Static-directory request to the server. - * <p> - * Indicates that the directory specified in the most recent Directory request - * is static. No new files will be checked out into this directory unless - * explicitly requested. - * </p> - */ - public void sendStaticDirectory() throws CVSException { - connection.writeLine("Static-directory"); //$NON-NLS-1$ - } - - /** - * Sends a Directory request to the server with a constructed path. - * <p> - * It may be necessary at times to guess the remote path of a directory since - * it does not exist yet. In this case we construct a remote path based on the - * local path by prepending the local path with the repository root. This may - * not work in the presence of modules, so only use it for creating new projects. - * </p><p> - * Note: A CVS repository root can end with a trailing slash. The CVS server - * expects that the repository root sent contain this extra slash. Including - * the foward slash in addition to the absolute remote path makes for a string - * containing two consecutive slashes (e.g. /home/cvs/repo//projecta/a.txt). - * This is valid in the CVS protocol. - * </p> - */ - public void sendConstructedDirectory(String localDir) throws CVSException { - sendDirectory(localDir, getRepositoryRoot() + "/" + localDir); //$NON-NLS-1$ - } - - /** - * Sends a Directory request to the server. - * <p>e.g. sendDirectory("local_dir", "remote_dir") sends: - * <pre> - * Directory local_dir - * repository_root/remote_dir - * </pre></p> - * - * @param localDir the path of the local directory relative to localRoot - * @param remoteDir the path of the remote directory relative to repositoryRoot - */ - public void sendDirectory(String localDir, String remoteDir) throws CVSException { - if (localDir.length() == 0) localDir = "."; //$NON-NLS-1$ - connection.writeLine("Directory " + localDir); //$NON-NLS-1$ - connection.writeLine(remoteDir); - } - - /** - * Sends a Directory request for the localRoot. - */ - public void sendLocalRootDirectory() throws CVSException { - sendDirectory(".", localRoot.getRemoteLocation(localRoot)); //$NON-NLS-1$ - } - - /** - * Sends a Directory request for the localRoot with a constructed path. - * <p> - * Use this when creating a new project that does not exist in the repository. - * </p> - * @see #sendConstructedDirectory - */ - public void sendConstructedRootDirectory() throws CVSException { - sendConstructedDirectory(""); //$NON-NLS-1$ - } - - /** - * Sends an Entry request to the server. - * <p> - * Indicates that a file is managed (but it may not exist locally). Sends - * the file's entry line to the server to indicate the version that was - * previously checked out. - * </p><p> - * Note: The most recent Directory request must have specified the file's - * parent folder. - * </p> - * - * @param entryLine the formatted entry line of the managed file. - */ - public void sendEntry(byte[] syncBytes, String serverTimestamp) throws CVSException { - connection.write("Entry "); //$NON-NLS-1$ - if (serverTimestamp == null) { - serverTimestamp = ""; //$NON-NLS-1$ - } - int start = Util.getOffsetOfDelimeter(syncBytes, (byte)'/', 0, 3); - if (start == -1) { - // something is wrong with the entry line so just send it as is - // and let the server report the error. - connection.writeLine(syncBytes, 0, syncBytes.length); - return; - } - int end = Util.getOffsetOfDelimeter(syncBytes, (byte)'/', start + 1, 1); - if (end == -1) { - // something is wrong with the entry line so just send it as is - // and let the server report the error. - connection.writeLine(syncBytes, 0, syncBytes.length); - return; - } - connection.write(syncBytes, 0, start + 1); - connection.write(serverTimestamp); - connection.writeLine(syncBytes, end, syncBytes.length - end); - } - - /** - * Sends a global options to the server. - * <p>e.g. sendGlobalOption("-n") sends: - * <pre> - * Global_option -n \n - * </pre></p> - * - * @param option the global option to send - */ - public void sendGlobalOption(String option) throws CVSException { - connection.writeLine("Global_option " + option); //$NON-NLS-1$ - } - - /** - * Sends an Unchanged request to the server. - * <p>e.g. if a file called "local_file" was not modified, sends: - * <pre> - * Unchanged local_file \n - * </pre></p><p> - * Note: The most recent Directory request must have specified the file's - * parent folder. - * </p> - * - * @param file the file that was not modified - */ - public void sendUnchanged(ICVSFile file) throws CVSException { - connection.writeLine("Unchanged " + file.getName()); //$NON-NLS-1$ - } - - /** - * Sends the Notify request to the server - */ - public void sendNotify(ICVSFolder parent, NotifyInfo info) - throws CVSException { - - String filename = info.getName(); - connection.writeLine("Notify " + filename); //$NON-NLS-1$ - connection.writeLine(info.getServerLine(parent)); - } - - /** - * Sends a Questionable request to the server. - * <p> - * Indicates that a file exists locally but is unmanaged. Asks the server - * whether or not the file should be ignored in subsequent CVS operations. - * The reply to the request occurs in the form of special M-type message - * responses prefixed with '?' when the next command is executed. - * </p><p> - * Note: The most recent Directory request must have specified the file's - * parent folder. - * </p> - * - * @param resource the local file or folder - */ - public void sendQuestionable(ICVSResource resource) throws CVSException { - connection.writeLine("Questionable " + resource.getName()); //$NON-NLS-1$ - } - - /** - * Sends a Sticky tag request to the server. - * <p> - * Indicates that the directory specified in the most recent Directory request - * has a sticky tag or date, and sends the tag's contents. - * </p> - * - * @param tag the sticky tag associated with the directory - */ - public void sendSticky(String tag) throws CVSException { - connection.writeLine("Sticky " + tag); //$NON-NLS-1$ - } - - /** - * Sends a Modified request to the server along with the file contents. - * <p>e.g. if a file called "local_file" was modified, sends: - * <pre> - * Modified local_file \n - * file_permissions \n - * file_size \n - * [... file_contents ...] - * </pre></p><p> - * Under some circumstances, Is-modified may be used in place of this request.<br> - * Do not use with history, init, import, rdiff, release, rtag, or update. - * </p><p> - * Note: The most recent Directory request must have specified the file's - * parent folder. - * </p> - * - * @param file the file that was modified - * @param isBinary if true the file is sent without translating line delimiters - * @param monitor the progress monitor - * @see #sendIsModified - */ - public void sendModified(ICVSFile file, boolean isBinary, IProgressMonitor monitor) - throws CVSException { - sendModified(file, isBinary, true, monitor); - } - - public void sendModified(ICVSFile file, boolean isBinary, boolean sendBinary, IProgressMonitor monitor) - throws CVSException { - - String filename = file.getName(); - connection.writeLine("Modified " + filename); //$NON-NLS-1$ - // send the default permissions for now - connection.writeLine(ResourceSyncInfo.getDefaultPermissions()); - sendFile(file, isBinary, sendBinary, monitor); - } - - /** - * Sends a file to the remote CVS server, possibly translating line delimiters. - * <p> - * Line termination sequences are automatically converted to linefeeds only - * (required by the CVS specification) when sending non-binary files. This - * may alter the actual size and contents of the file that is sent. - * </p><p> - * Note: Non-binary files must be small enough to fit in available memory. - * </p> - * @param file the file to be sent - * @param isBinary is true if the file should be sent without translation - * @param monitor the progress monitor - */ - public void sendFile(ICVSFile file, boolean isBinary, IProgressMonitor monitor) throws CVSException { - sendFile(file, isBinary, true, monitor); - } - - public void sendFile(ICVSFile file, boolean isBinary, boolean sendBinary, IProgressMonitor monitor) throws CVSException { - // check overrides - if (textTransferOverrideSet != null && - textTransferOverrideSet.contains(file)) isBinary = false; - - // update progress monitor - final String title = Policy.bind(getSendFileTitleKey(), new Object[]{ Util.toTruncatedPath(file, localRoot, 3) }); //$NON-NLS-1$ - monitor.subTask(Policy.bind("Session.transferNoSize", title)); //$NON-NLS-1$ - try { - InputStream in = null; - long length; - try { - if (isBinary && !sendBinary) { - byte[] bytes = "hello".getBytes(); //$NON-NLS-1$ - sendUncompressedBytes(new ByteArrayInputStream(bytes), bytes.length); - return; - } - - if (compressionLevel == 0) { - in = file.getContents(); - if (!isBinary && IS_CRLF_PLATFORM){ - // uncompressed text - byte[] buffer = new byte[TRANSFER_BUFFER_SIZE]; - in = new CRLFtoLFInputStream(in); - ByteCountOutputStream counter = new ByteCountOutputStream(); - try { - for (int count; (count = in.read(buffer)) != -1;) counter.write(buffer, 0, count); - } finally { - counter.close(); - } - in.close(); - length = counter.getSize(); - in = new CRLFtoLFInputStream(file.getContents()); - } else { - // uncompressed binary - length = file.getSize(); - } - in = new ProgressMonitorInputStream(in, length, TRANSFER_PROGRESS_INCREMENT, monitor) { - protected void updateMonitor(long bytesRead, long bytesTotal, IProgressMonitor monitor) { - if (bytesRead == 0) return; - Assert.isTrue(bytesRead <= bytesTotal); - monitor.subTask(Policy.bind("Session.transfer", //$NON-NLS-1$ - new Object[] { title, Long.toString(bytesRead >> 10), Long.toString(bytesTotal >> 10) })); - } - }; - sendUncompressedBytes(in, length); - } else { - monitor.subTask(Policy.bind("Session.calculatingCompressedSize", Util.toTruncatedPath(file, localRoot, 3))); //$NON-NLS-1$ - in = file.getContents(); - byte[] buffer = new byte[TRANSFER_BUFFER_SIZE]; - ByteCountOutputStream counter = new ByteCountOutputStream(); - OutputStream zout = new GZIPOutputStream(counter); - if (!isBinary && IS_CRLF_PLATFORM) in = new CRLFtoLFInputStream(in); - try { - for (int count; (count = in.read(buffer)) != -1;) zout.write(buffer, 0, count); - } finally { - zout.close(); - } - in.close(); - in = file.getContents(); - in = new ProgressMonitorInputStream(in, file.getSize(), TRANSFER_PROGRESS_INCREMENT, monitor) { - protected void updateMonitor(long bytesRead, long bytesTotal, IProgressMonitor monitor) { - if (bytesRead == 0) return; - Assert.isTrue(bytesRead <= bytesTotal); - monitor.subTask(Policy.bind("Session.transfer", //$NON-NLS-1$ - new Object[] { title, Long.toString(bytesRead >> 10), Long.toString(bytesTotal >> 10) })); - } - }; - if (!isBinary && IS_CRLF_PLATFORM) in = new CRLFtoLFInputStream(in); - sendCompressedBytes(in, counter.getSize()); - } - } finally { - if (in != null) in.close(); - } - } catch (IOException e) { - throw CVSException.wrapException(e); - } - } - - /* - * Send the contents of the input stream to CVS. - * Length must equal the number of bytes that will be transferred - * across the wire, that is, the compressed file size. - */ - private void sendCompressedBytes(InputStream in, long length) throws IOException, CVSException { - String sizeLine = "z" + Long.toString(length); //$NON-NLS-1$ - writeLine(sizeLine); - OutputStream out = connection.getOutputStream(); - GZIPOutputStream zo = new GZIPOutputStream(out); - byte[] buffer = new byte[TRANSFER_BUFFER_SIZE]; - for (int count; - (count = in.read(buffer)) != -1;) - zo.write(buffer, 0, count); - zo.finish(); - } - - /* - * Send the contents of the input stream to CVS. - * Length must equal the number of bytes that will be transferred - * across the wire. - */ - private void sendUncompressedBytes(InputStream in, long length) throws IOException, CVSException { - OutputStream out = connection.getOutputStream(); - String sizeLine = Long.toString(length); - writeLine(sizeLine); - byte[] buffer = new byte[TRANSFER_BUFFER_SIZE]; - for (int count; (count = in.read(buffer)) != -1;) out.write(buffer, 0, count); - } - - - - - /** - * Receives a file from the remote CVS server, possibly translating line delimiters. - * <p> - * Line termination sequences are automatically converted to platform format - * only when receiving non-binary files. This may alter the actual size and - * contents of the file that is received. - * </p><p> - * Translation is performed on-the-fly, so the file need not fit in available memory. - * </p> - * @param file the file to be received - * @param isBinary is true if the file should be received without translation - * @param responseType one of the ICVSFile updated types (UPDATED, CREATED, MERGED, UPDATE_EXISTING) - * indicating what repsonse type provided the file contents - * @param monitor the progress monitor - */ - public void receiveFile(ICVSFile file, boolean isBinary, int responseType, IProgressMonitor monitor) - throws CVSException { - // check overrides - if (textTransferOverrideSet != null && - textTransferOverrideSet.contains(file)) isBinary = false; - - // update progress monitor - final String title = Policy.bind("Session.receiving", new Object[]{ Util.toTruncatedPath(file, localRoot, 3) }); //$NON-NLS-1$ - monitor.subTask(Policy.bind("Session.transferNoSize", title)); //$NON-NLS-1$ - // get the file size from the server - long size; - boolean compressed = false; - try { - String sizeLine = readLine(); - if (sizeLine.charAt(0) == 'z') { - compressed = true; - sizeLine = sizeLine.substring(1); - } - size = Long.parseLong(sizeLine, 10); - } catch (NumberFormatException e) { - throw new CVSException(Policy.bind("Session.badInt"), e); //$NON-NLS-1$ - } - // create an input stream that spans the next 'size' bytes from the connection - InputStream in = new SizeConstrainedInputStream(connection.getInputStream(), size, true /*discardOnClose*/); - // setup progress monitoring - in = new ProgressMonitorInputStream(in, size, TRANSFER_PROGRESS_INCREMENT, monitor) { - protected void updateMonitor(long bytesRead, long bytesTotal, IProgressMonitor monitor) { - if (bytesRead == 0) return; - monitor.subTask(Policy.bind("Session.transfer", //$NON-NLS-1$ - new Object[] { title, Long.toString(bytesRead >> 10), Long.toString(bytesTotal >> 10) })); - } - }; - // if compression enabled, decompress on the fly - if (compressed) { - try { - in = new GZIPInputStream(in); - } catch (IOException e) { - throw CVSException.wrapException(e); - } - } - // if not binary, translate line delimiters on the fly - if (! isBinary) { - // always auto-correct for CRLF line-ends that come from the server - in = new CRLFtoLFInputStream(in); - // switch from LF to CRLF if appropriate - if (IS_CRLF_PLATFORM) in = new LFtoCRLFInputStream(in); - } - // write the file locally - file.setContents(in, responseType, true, new NullProgressMonitor()); - } - - /** - * Stores the value of the last Mod-time response encountered. - * Valid only for the duration of a single CVS command. - */ - void setModTime(Date modTime) { - this.modTime = modTime; - } - - /** - * Returns the stored value of the last Mod-time response, - * or null if there was none while processing the current command. - */ - Date getModTime() { - return modTime; - } - - /** - * Stores true if the -n global option was specified for the current command. - * Valid only for the duration of a single CVS command. - */ - void setNoLocalChanges(boolean noLocalChanges) { - this.noLocalChanges = noLocalChanges; - } - - /** - * Returns true if the -n global option was specified for the current command, - * false otherwise. - */ - boolean isNoLocalChanges() { - return noLocalChanges; - } - - /** - * Callback hook for the ValidRequestsHandler to specify the set of valid - * requests for this session. - */ - void setValidRequests(String validRequests) { - this.validRequests = " " + validRequests + " "; //$NON-NLS-1$ //$NON-NLS-2$ - } - - boolean isOutputToConsole() { - return outputToConsole; - } - - /** - * Stores a flag as to whether .# files will be created. (Default is true) - * @param createBackups if true, creates .# files at the server's request - */ - void setCreateBackups(boolean createBackups) { - this.createBackups = createBackups; - } - - /** - * Returns a flag as to whether .# files will be created. - */ - boolean isCreateBackups() { - return createBackups; - } - - /** - * Gets the sendFileTitleKey. - * @return Returns a String - */ - String getSendFileTitleKey() { - if (sendFileTitleKey == null) - return "Session.sending"; //$NON-NLS-1$ - return sendFileTitleKey; - } - - /** - * Sets the sendFileTitleKey. - * @param sendFileTitleKey The sendFileTitleKey to set - */ - public void setSendFileTitleKey(String sendFileTitleKey) { - this.sendFileTitleKey = sendFileTitleKey; - } - - /** - * Remembers a set of files that must be transferred as 'text' - * regardless of what the isBinary parameter to sendFile() is. - * - * @param textTransferOverrideSet the set of ICVSFiles to override, or null if none - */ - public void setTextTransferOverride(Collection textTransferOverrideSet) { - this.textTransferOverrideSet = textTransferOverrideSet; - } - - /** - * Filter the provided global options using parameters set on this session - * or globally. The session may add global options that correspond to user - * preferences or remove those that contradict requirements for this - * particular session. - * - * @param globalOptions the global options, read-only - * @return the filtered global options - */ - protected GlobalOption[] filterGlobalOptions(GlobalOption[] globalOptions) { - if (! Command.DO_NOT_CHANGE.isElementOf(globalOptions)) { - // Get the user preference for verbosity - QuietOption quietOption = CVSProviderPlugin.getPlugin().getQuietness(); - if (quietOption != null) { - globalOptions = quietOption.addToEnd(globalOptions); - } - // Get the user preference for read-only - if (CVSProviderPlugin.getPlugin().getPluginPreferences().getBoolean(CVSProviderPlugin.READ_ONLY)) { - if (!Command.MAKE_READ_ONLY.isElementOf(globalOptions)) { - globalOptions = Command.MAKE_READ_ONLY.addToEnd(globalOptions); - } - } - } - return globalOptions; - } - /** - * Method setIgnoringLocalChanges. - * @param b - */ - protected void setIgnoringLocalChanges(boolean b) { - ignoringLocalChanges = b; - } - /** - * Returns the ignoringLocalChanges. - * @return boolean - */ - protected boolean isIgnoringLocalChanges() { - return ignoringLocalChanges; - } - - /** - * Method getUniquePathForInvalidPath. - * @param localDir - * @return String - */ - public String getUniquePathForInvalidPath(String localDir) { - IPath oldPath = new Path(localDir); - int count = oldPath.segmentCount(); - for (int i = 0; i < count; i++) { - String segment = oldPath.segment(i); - if (segment.endsWith(".")) { //$NON-NLS-1$ - segment = segment + Policy.bind("Session.dot_2"); //$NON-NLS-1$ - oldPath = oldPath.removeLastSegments(count - i).append(segment).append(oldPath.removeFirstSegments(i + 1)); - } - } - return oldPath.toString(); - } - - /* - * Get the response handler map to be used for this session. The map is created by making a copy of the global - * reponse handler map. - */ - protected Map getReponseHandlers() { - if (responseHandlers == null) { - responseHandlers = Request.getReponseHandlerMap(); - } - return responseHandlers; - } - - /* - * Makes a list of all valid responses; for initializing a session. - * @return a space-delimited list of all valid response strings - */ - private String makeResponseList() { - StringBuffer result = new StringBuffer("ok error M E"); //$NON-NLS-1$ - Iterator elements = getReponseHandlers().keySet().iterator(); - while (elements.hasNext()) { - result.append(' '); - result.append((String) elements.next()); - } - - return result.toString(); - } - protected void registerResponseHandler(ResponseHandler handler) { - getReponseHandlers().put(handler.getResponseID(), handler); - } - - protected void removeResponseHandler(String responseID) { - getReponseHandlers().remove(responseID); - } - - protected ResponseHandler getResponseHandler(String responseID) { - return (ResponseHandler)getReponseHandlers().get(responseID); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/StaticHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/StaticHandler.java deleted file mode 100644 index 2c6d46e98..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/StaticHandler.java +++ /dev/null @@ -1,70 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Handles any "Set-static-directory" and "Clear-static-directory" responses - * from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Set-static-directory myproject/ \n - * /u/cvsroot/myproject/ \n - * [...] - * </pre> - * Then we set or clear the static flag of the folder "myproject", - * automatically creating it if it does not exist locally, - * </p> - */ -class StaticHandler extends ResponseHandler { - private final boolean setStaticDirectory; - - public StaticHandler(boolean setStaticDirectory) { - this.setStaticDirectory = setStaticDirectory; - } - - public String getResponseID() { - if (setStaticDirectory) { - return "Set-static-directory"; //$NON-NLS-1$ - } else { - return "Clear-static-directory"; //$NON-NLS-1$ - } - } - - public void handle(Session session, String localDir, - IProgressMonitor monitor) throws CVSException { - // read additional data for the response - String repositoryDir = session.readLine(); - - // create the directory then set or clear the static flag - Assert.isTrue(repositoryDir.endsWith("/")); //$NON-NLS-1$ - repositoryDir = repositoryDir.substring(0, repositoryDir.length() - 1); - ICVSFolder folder = createFolder(session, localDir, repositoryDir); - FolderSyncInfo syncInfo = folder.getFolderSyncInfo(); - // Added to ignore sync info for workspace root - if (syncInfo == null) return; - FolderSyncInfo newInfo = new FolderSyncInfo(syncInfo.getRepository(), - syncInfo.getRoot(), syncInfo.getTag(), setStaticDirectory); - // only set the sync info if it has changed - if (!syncInfo.equals(newInfo)) - folder.setFolderSyncInfo(newInfo); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Status.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Status.java deleted file mode 100644 index 31b2d5a63..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Status.java +++ /dev/null @@ -1,21 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -public class Status extends AbstractMessageCommand { - /*** Local options: specific to status ***/ - - protected Status() { } - protected String getRequestId() { - return "status"; //$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/StickyHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/StickyHandler.java deleted file mode 100644 index 6364f84ca..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/StickyHandler.java +++ /dev/null @@ -1,77 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.resources.CVSEntryLineTag; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Handles any "Set-sticky" and "Clear-stick" responses from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Set-sticky myproject/ \n - * /u/cvsroot/myproject/ \n - * Tsometag \n - * [...] - * </pre> - * Then we set or clear the sticky tag property of the folder "myproject", - * automatically creating it if it does not exist locally, - * </p> - */ -class StickyHandler extends ResponseHandler { - private final boolean setSticky; - - public StickyHandler(boolean setSticky) { - this.setSticky = setSticky; - } - - public String getResponseID() { - if (setSticky) { - return "Set-sticky"; //$NON-NLS-1$ - } else { - return "Clear-sticky"; //$NON-NLS-1$ - } - } - - public void handle(Session session, String localDir, - IProgressMonitor monitor) throws CVSException { - // read additional data for the response - String repositoryDir = session.readLine(); - String tag = null; - if (setSticky) { - tag = session.readLine(); - if (tag.length() == 0) tag = null; // FIXME: is this correct - } - - // create the directory then set or clear the sticky tag - Assert.isTrue(repositoryDir.endsWith("/")); //$NON-NLS-1$ - repositoryDir = repositoryDir.substring(0, repositoryDir.length() - 1); - ICVSFolder folder = createFolder(session, localDir, repositoryDir); - FolderSyncInfo syncInfo = folder.getFolderSyncInfo(); - // Added to ignore sync info for workspace root - if (syncInfo == null) return; - FolderSyncInfo newInfo = new FolderSyncInfo(syncInfo.getRepository(), - syncInfo.getRoot(), tag != null ? new CVSEntryLineTag(tag) : null, - syncInfo.getIsStatic()); - // only set the sync info if it has changed - if (!syncInfo.equals(newInfo)) - folder.setFolderSyncInfo(newInfo); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/SyncUpdate.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/SyncUpdate.java deleted file mode 100644 index f0020f106..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/SyncUpdate.java +++ /dev/null @@ -1,31 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -public class SyncUpdate extends Update { - - public SyncUpdate() { }; - - /* - * @see Command#sendFileStructure(ICVSResource,IProgressMonitor,boolean,boolean,boolean) - */ - protected void sendFileStructure(Session session, ICVSResource[] resources, - boolean emptyFolders, IProgressMonitor monitor) throws CVSException { - - checkResourcesManaged(resources); - new FileStructureVisitor(session, emptyFolders, true, false, monitor).visit(session, resources); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Tag.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Tag.java deleted file mode 100644 index e7dba043e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Tag.java +++ /dev/null @@ -1,107 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.TagListener; - -public class Tag extends Command { - /*** Local options: specific to tag ***/ - public static final LocalOption CREATE_BRANCH = new LocalOption("-b", null); //$NON-NLS-1$ - public static final LocalOption FORCE_REASSIGNMENT = new LocalOption("-F", null); //$NON-NLS-1$ - - /*** Default command output listener ***/ - private static final ICommandOutputListener DEFAULT_OUTPUT_LISTENER = new TagListener(); - - // handle added and removed resources in a special way - private boolean customBehaviorEnabled; - - protected Tag(boolean customBehaviorEnabled) { - this.customBehaviorEnabled = customBehaviorEnabled; - } - - protected Tag() { - this(false); - } - - protected String getRequestId() { - return "tag"; //$NON-NLS-1$ - } - - protected ICVSResource[] computeWorkResources(Session session, LocalOption[] localOptions, - String[] arguments) throws CVSException { - - if (arguments.length < 1) throw new IllegalArgumentException(); - String[] allButFirst = new String[arguments.length - 1]; - System.arraycopy(arguments, 1, allButFirst, 0, arguments.length - 1); - return super.computeWorkResources(session, localOptions, allButFirst); - } - - public IStatus execute(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, CVSTag tag, String[] arguments, ICommandOutputListener listener, - IProgressMonitor monitor) throws CVSException { - - if(tag.getType() != CVSTag.VERSION && tag.getType() != CVSTag.BRANCH) { - throw new CVSException(new CVSStatus(IStatus.ERROR, Policy.bind("Tag.notVersionOrBranchError"))); //$NON-NLS-1$ - } - - // Add the CREATE_BRANCH option for a branch tag - if (tag.getType() == CVSTag.BRANCH) { - if ( ! CREATE_BRANCH.isElementOf(localOptions)) { - LocalOption[] newLocalOptions = new LocalOption[localOptions.length + 1]; - System.arraycopy(localOptions, 0, newLocalOptions, 0, localOptions.length); - newLocalOptions[newLocalOptions.length - 1] = CREATE_BRANCH; - localOptions = newLocalOptions; - } - } - - // Add the tag name to the start of the arguments - String[] newArguments = new String[arguments.length + 1]; - newArguments[0] = tag.getName(); - System.arraycopy(arguments, 0, newArguments, 1, arguments.length); - - return execute(session, globalOptions, localOptions, newArguments, listener, monitor); - } - - public IStatus execute(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions, - CVSTag tag, ICVSResource[] arguments, ICommandOutputListener listener, IProgressMonitor monitor) - throws CVSException { - - String[] stringArguments = convertArgumentsForOpenSession(arguments, session); - - return execute(session, globalOptions, localOptions, tag, stringArguments, listener, monitor); - } - - protected ICommandOutputListener getDefaultCommandOutputListener() { - return DEFAULT_OUTPUT_LISTENER; - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Send all folders that are already managed to the server - if (customBehaviorEnabled) { - new TagFileSender(session, monitor).visit(session, resources); - } else { - new FileStructureVisitor(session, false, false, monitor).visit(session, resources); - } - return resources; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/TagFileSender.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/TagFileSender.java deleted file mode 100644 index 9bf0555f3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/TagFileSender.java +++ /dev/null @@ -1,51 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * Special visitor which handles added and removed files in a special way. - * Added resources are skipped. Deleted resources are sent as if they were not deleted. - */ -class TagFileSender extends FileStructureVisitor { - - public TagFileSender(Session session, IProgressMonitor monitor) { - super(session, false, false, monitor); - } - - /** - * Override sendFile to provide custom handling of added and deleted resources. - * Added resources are skipped. Deleted resources are sent as if they were not deleted. - */ - protected void sendFile(ICVSFile mFile) throws CVSException { - Policy.checkCanceled(monitor); - byte[] syncBytes = mFile.getSyncBytes(); - if (syncBytes != null) { - // Send the parent folder if it hasn't been sent already - sendFolder(mFile.getParent()); - // Send the file if appropriate - if (ResourceSyncInfo.isDeletion(syncBytes)) { - // makes this resource sync undeleted - syncBytes = ResourceSyncInfo.convertFromDeletion(syncBytes); - } - if (!ResourceSyncInfo.isAddition(syncBytes)) { - session.sendEntry(syncBytes, ResourceSyncInfo.getTimestampToServer(syncBytes, mFile.getTimeStamp())); - session.sendIsModified(mFile, ResourceSyncInfo.isBinary(syncBytes), monitor); - } - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/TemplateHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/TemplateHandler.java deleted file mode 100644 index 1fa7c1fe3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/TemplateHandler.java +++ /dev/null @@ -1,50 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.util.SyncFileWriter; - -/** - * @author Administrator - * - * To change this generated comment edit the template variable "typecomment": - * Window>Preferences>Java>Templates. - * To enable and disable the creation of type comments go to - * Window>Preferences>Java>Code Generation. - */ -public class TemplateHandler extends ResponseHandler { - - /** - * @see org.eclipse.team.internal.ccvs.core.client.ResponseHandler#getResponseID() - */ - public String getResponseID() { - return "Template"; //$NON-NLS-1$ - } - - /** - * @see org.eclipse.team.internal.ccvs.core.client.ResponseHandler#handle(org.eclipse.team.internal.ccvs.core.client.Session, java.lang.String, org.eclipse.core.runtime.IProgressMonitor) - */ - public void handle(Session session, String localDir, IProgressMonitor monitor) throws CVSException { - String remoteDir = session.readLine(); - ICVSFolder localFolder = getExistingFolder(session, localDir); - IContainer container = (IContainer)localFolder.getIResource(); - if (container == null) return; - ICVSFile templateFile = CVSWorkspaceRoot.getCVSFileFor(SyncFileWriter.getTemplateFile(container)); - session.receiveFile(templateFile, false, UpdatedHandler.HANDLE_UPDATED, monitor); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Update.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Update.java deleted file mode 100644 index d685e99ce..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Update.java +++ /dev/null @@ -1,213 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; - -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.CVSTeamProvider; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.UpdateListener; - -public class Update extends Command { - /*** Local options: specific to update ***/ - public static final LocalOption CLEAR_STICKY = new LocalOption("-A"); //$NON-NLS-1$ - public static final LocalOption IGNORE_LOCAL_CHANGES = new LocalOption("-C"); //$NON-NLS-1$ - public static final LocalOption RETRIEVE_ABSENT_DIRECTORIES = new LocalOption("-d"); //$NON-NLS-1$ - public static final LocalOption JOIN = new LocalOption("-j"); //$NON-NLS-1$ - - /*** Default command output listener ***/ - private static final ICommandOutputListener DEFAULT_OUTPUT_LISTENER = new UpdateListener(null); - - /*** File information status returned from update ***/ - public static final int STATE_NONE = 0; // no state information available - public static final int STATE_ADDED_LOCAL = 1; // new file locally that was added but not comitted to server yet - public static final int STATE_UNKOWN = 2; // new file locally but not added to server - public static final int STATE_REMOTE_CHANGES = 3; // remote changes to an unmodified local file - public static final int STATE_DELETED = 4; // removed locally but still exists on the server - public static final int STATE_MODIFIED = 5; // modified locally - public static final int STATE_CONFLICT = 6; // modified locally and on the server but cannot be auto-merged - public static final int STATE_MERGEABLE_CONFLICT = 7; // modified locally and on the server but can be auto-merged - - /** - * Makes a -r or -D or -A option for a tag. - * Valid for: checkout export history rdiff update - */ - public static LocalOption makeTagOption(CVSTag tag) { - int type = tag.getType(); - switch (type) { - case CVSTag.HEAD: - return CLEAR_STICKY; - default: - return Command.makeTagOption(tag); - } - } - - protected Update() { } - protected String getRequestId() { - return "update"; //$NON-NLS-1$ - } - - protected ICommandOutputListener getDefaultCommandOutputListener() { - return DEFAULT_OUTPUT_LISTENER; - } - - protected ICVSResource[] sendLocalResourceState(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor) - throws CVSException { - - // Send all folders that are already managed to the server - // even folders that are empty - sendFileStructure(session, resources, true, monitor); - return resources; - } - - /** - * Convenience method that allows the creation of .# files to be disabled. - * @param createBackups if true, creates .# files - * @see Command.execute - */ - public final IStatus execute(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, String[] arguments, ICommandOutputListener listener, - IProgressMonitor pm, boolean createBackups) throws CVSException { - session.setCreateBackups(createBackups); - try { - return super.execute(session, globalOptions, localOptions, arguments, listener, pm); - } finally { - session.setCreateBackups(true); - } - } - - /** - * On successful finish, prune empty directories if the -P or -D option was specified. - */ - protected IStatus commandFinished(Session session, GlobalOption[] globalOptions, - LocalOption[] localOptions, ICVSResource[] resources, IProgressMonitor monitor, - IStatus status) throws CVSException { - // If we didn't succeed, don't do any post processing - if (status.getCode() == CVSStatus.SERVER_ERROR) { - return status; - } - - // If we are pruning (-P) or getting a sticky copy using -D, then prune empty directories - if (PRUNE_EMPTY_DIRECTORIES.isElementOf(localOptions) || - findOption(localOptions, "-D") != null) { //$NON-NLS-1$ - // Delete empty directories - new PruneFolderVisitor().visit(session, resources); - - } - session.handleCaseCollisions(); - return status; - } - - protected LocalOption[] filterLocalOptions(Session session, GlobalOption[] globalOptions, LocalOption[] localOptions) { - List newOptions = new ArrayList(Arrays.asList(localOptions)); - - // Look for absent directories if enabled and the option is not already included - ICVSFolder sessionRoot = session.getLocalRoot(); - IResource resource = null; - RepositoryProvider provider = null; - // If there is a provider, use the providers setting - try { - resource = session.getLocalRoot().getIResource(); - if (resource != null) { - provider = RepositoryProvider.getProvider(resource.getProject(), CVSProviderPlugin.getTypeId()); - if (provider != null) { - if (((CVSTeamProvider)provider).getFetchAbsentDirectories() && ! RETRIEVE_ABSENT_DIRECTORIES.isElementOf(localOptions)) { - newOptions.add(Update.RETRIEVE_ABSENT_DIRECTORIES); - } - } - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - // If there is no provider, use the global setting - if (provider == null) { - if (CVSProviderPlugin.getPlugin().getFetchAbsentDirectories() && ! RETRIEVE_ABSENT_DIRECTORIES.isElementOf(localOptions)) { - newOptions.add(Update.RETRIEVE_ABSENT_DIRECTORIES); - } - } - - // Prune empty directories if pruning is enabled and the command in not being run in non-update mode - if (CVSProviderPlugin.getPlugin().getPruneEmptyDirectories() && ! PRUNE_EMPTY_DIRECTORIES.isElementOf(localOptions)) { - if (! DO_NOT_CHANGE.isElementOf(globalOptions)) { - newOptions.add(Update.PRUNE_EMPTY_DIRECTORIES); - } - } - localOptions = (LocalOption[]) newOptions.toArray(new LocalOption[newOptions.size()]); - return super.filterLocalOptions(session, globalOptions, localOptions); - } - - /** - * We allow unmanaged resources as long as there parents are managed. - * - * @see Command#checkResourcesManaged(ICVSResource[]) - */ - protected void checkResourcesManaged(ICVSResource[] resources) throws CVSException { - for (int i = 0; i < resources.length; ++i) { - ICVSFolder folder; - if (resources[i].isFolder()) { - if (((ICVSFolder)resources[i]).isCVSFolder()) { - folder = (ICVSFolder)resources[i]; - } else { - folder = resources[i].getParent(); - } - } - else { - folder = resources[i].getParent(); - } - if (folder==null || (!folder.isCVSFolder() && folder.exists())) { - throw new CVSException(Policy.bind("Command.argumentNotManaged", folder.getName()));//$NON-NLS-1$ - } - } - } - - /** - * @see org.eclipse.team.internal.ccvs.core.client.Command#doExecute(org.eclipse.team.internal.ccvs.core.client.Session, org.eclipse.team.internal.ccvs.core.client.Command.GlobalOption, org.eclipse.team.internal.ccvs.core.client.Command.LocalOption, java.lang.String, org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener, org.eclipse.core.runtime.IProgressMonitor) - */ - protected IStatus doExecute( - Session session, - GlobalOption[] globalOptions, - LocalOption[] localOptions, - String[] arguments, - ICommandOutputListener listener, - IProgressMonitor monitor) - throws CVSException { - - session.setIgnoringLocalChanges(IGNORE_LOCAL_CHANGES.isElementOf(localOptions)); - try { - return super.doExecute( - session, - globalOptions, - localOptions, - arguments, - listener, - monitor); - } finally { - session.setIgnoringLocalChanges(false); - } - - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/UpdateMergableOnly.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/UpdateMergableOnly.java deleted file mode 100644 index 84b28180d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/UpdateMergableOnly.java +++ /dev/null @@ -1,113 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.util.ArrayList; -import java.util.Date; -import java.util.List; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * This custom update command will only update files that - * are either incoming changes (Update-existing) or auto-mergable - * (Merged with no "+=" in entry line). - */ -public class UpdateMergableOnly extends Update { - - List skippedFiles = new ArrayList(); - - public class MergableOnlyUpdatedHandler extends UpdatedHandler { - - public MergableOnlyUpdatedHandler() { - // handle "Merged" responses - super(UpdatedHandler.HANDLE_MERGED); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.client.UpdatedHandler#getTargetFile(org.eclipse.team.internal.ccvs.core.ICVSFolder, java.lang.String, byte[]) - */ - protected ICVSFile getTargetFile(ICVSFolder mParent, String fileName, byte[] entryBytes) throws CVSException { - String adjustedFileName = fileName; - if (ResourceSyncInfo.isMergedWithConflicts(entryBytes)) { - // for merged-with-conflict, return a temp file - adjustedFileName = ".##" + adjustedFileName; //$NON-NLS-1$ - skippedFiles.add(((IContainer)mParent.getIResource()).getFile(new Path(fileName))); - } - return super.getTargetFile(mParent, adjustedFileName, entryBytes); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.client.UpdatedHandler#receiveTargetFile(org.eclipse.team.internal.ccvs.core.client.Session, org.eclipse.team.internal.ccvs.core.ICVSFile, java.lang.String, java.util.Date, boolean, boolean, org.eclipse.core.runtime.IProgressMonitor) - */ - protected void receiveTargetFile( - Session session, - ICVSFile mFile, - String entryLine, - Date modTime, - boolean binary, - boolean readOnly, - IProgressMonitor monitor) - throws CVSException { - - if (ResourceSyncInfo.isMergedWithConflicts(entryLine.getBytes())) { - // For merged-with-conflict, just recieve the file contents. - // Use the Updated handler type so that the file will be created or - // updated. - session.receiveFile(mFile, binary, UpdatedHandler.HANDLE_UPDATED, monitor); - } else { - super.receiveTargetFile(session, mFile, entryLine, modTime, binary, readOnly, monitor); - } - } - } - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.client.Command#doExecute(org.eclipse.team.internal.ccvs.core.client.Session, org.eclipse.team.internal.ccvs.core.client.Command.GlobalOption[], org.eclipse.team.internal.ccvs.core.client.Command.LocalOption[], java.lang.String[], org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener, org.eclipse.core.runtime.IProgressMonitor) - */ - protected IStatus doExecute( - Session session, - GlobalOption[] globalOptions, - LocalOption[] localOptions, - String[] arguments, - ICommandOutputListener listener, - IProgressMonitor monitor) - throws CVSException { - - MergableOnlyUpdatedHandler newHandler = new MergableOnlyUpdatedHandler(); - ResponseHandler oldHandler = session.getResponseHandler(newHandler.getResponseID()); - skippedFiles.clear(); - try { - session.registerResponseHandler(newHandler); - return super.doExecute( - session, - globalOptions, - localOptions, - arguments, - listener, - monitor); - } finally { - session.registerResponseHandler(oldHandler); - } - } - - public IFile[] getSkippedFiles() { - return (IFile[]) skippedFiles.toArray(new IFile[skippedFiles.size()]); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/UpdatedHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/UpdatedHandler.java deleted file mode 100644 index 5585fa90d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/UpdatedHandler.java +++ /dev/null @@ -1,140 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import java.util.Date; - -import org.eclipse.core.resources.IResourceStatus; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * Handles any "Updated" and "Merged" responses - * from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Updated ???\n - * [...] - * </pre> - * Then - * </p> - */ - -/** - * Does get information about the file that is updated - * and the file-content itself and puts it on the fileSystem. - * - * The difference beetween the "Updated" and the "Merged" is, that - * an "Merged" file is not going to be up-to-date after the operation. - * - * Requiers a exisiting parent-folder. - */ -class UpdatedHandler extends ResponseHandler { - - private int handlerType; - - protected static final int HANDLE_UPDATED = ICVSFile.UPDATED; - protected static final int HANDLE_MERGED = ICVSFile.MERGED; - protected static final int HANDLE_UPDATE_EXISTING = ICVSFile.UPDATE_EXISTING; - protected static final int HANDLE_CREATED = ICVSFile.CREATED; - - private static final String READ_ONLY_FLAG = "u=rw"; //$NON-NLS-1$ - - public UpdatedHandler(int handlerType) { - this.handlerType = handlerType; - } - - public String getResponseID() { - switch (handlerType) { - case HANDLE_UPDATED: return "Updated"; //$NON-NLS-1$ - case HANDLE_MERGED: return "Merged"; //$NON-NLS-1$ - case HANDLE_UPDATE_EXISTING: return "Update-existing"; //$NON-NLS-1$ - case HANDLE_CREATED: return "Created"; //$NON-NLS-1$ - } - return null; - } - - public void handle(Session session, String localDir, IProgressMonitor monitor) throws CVSException { - // read additional data for the response - String repositoryFile = session.readLine(); - String entryLine = session.readLine(); - byte[] entryBytes = entryLine.getBytes(); - String permissionsLine = session.readLine(); - - // clear file update modifiers - Date modTime = session.getModTime(); - session.setModTime(null); - - // Get the local file - String fileName = repositoryFile.substring(repositoryFile.lastIndexOf("/") + 1); //$NON-NLS-1$ - ICVSFolder mParent = getExistingFolder(session, localDir); - ICVSFile mFile = getTargetFile(mParent, fileName, entryBytes); - - boolean binary = ResourceSyncInfo.isBinary(entryBytes); - boolean readOnly = permissionsLine.indexOf(READ_ONLY_FLAG) == -1; - - // The file may have been set as read-only by a previous checkout/update - if (mFile.isReadOnly()) mFile.setReadOnly(false); - - try { - receiveTargetFile(session, mFile, entryLine, modTime, binary, readOnly, monitor); - } catch (CVSException e) { - if (e.getStatus().getCode() == IResourceStatus.CASE_VARIANT_EXISTS) { - // Record that we have a case collision and continue; - session.addCaseCollision(new Path(localDir).append(fileName).toString(), Path.EMPTY.toString()); - return; - } else { - throw e; - } - } - } - - protected ICVSFile getTargetFile(ICVSFolder mParent, String fileName, byte[] entryBytes) throws CVSException { - return mParent.getFile(fileName); - } - - protected void receiveTargetFile(Session session, ICVSFile mFile, String entryLine, Date modTime, boolean binary, boolean readOnly, IProgressMonitor monitor) throws CVSException { - - // receive the file contents from the server - session.receiveFile(mFile, binary, handlerType, monitor); - - // Set the timestamp in the file and get it again so that we use the *real* timestamp - // in the sync info. The os may not actually set the time we provided :) - mFile.setTimeStamp(modTime); - modTime = mFile.getTimeStamp(); - ResourceSyncInfo info = new ResourceSyncInfo(entryLine, null, null); - MutableResourceSyncInfo newInfoWithTimestamp = info.cloneMutable(); - newInfoWithTimestamp.setTimeStamp(modTime); - int modificationState = ICVSFile.UNKNOWN; - if(handlerType==HANDLE_MERGED) { - newInfoWithTimestamp.setMerged(); - } else if (!session.isIgnoringLocalChanges() - && !info.isAdded() /* could be an added entry during a merge in which case it is dirty */ - && (handlerType==HANDLE_UPDATE_EXISTING || handlerType==HANDLE_CREATED)) { - // both these cases result in an unmodified file. - // reporting is handled by the FileModificationManager - modificationState = ICVSFile.CLEAN; - CVSProviderPlugin.getPlugin().getFileModificationManager().updated(mFile); - } - mFile.setSyncInfo(newInfoWithTimestamp, modificationState); - if (readOnly) mFile.setReadOnly(true); - } - -}
\ No newline at end of file diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ValidRequests.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ValidRequests.java deleted file mode 100644 index 4272e132a..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ValidRequests.java +++ /dev/null @@ -1,28 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; - -class ValidRequests extends Request { - - protected ValidRequests() { } - - protected String getRequestId() { - return "valid-requests"; //$NON-NLS-1$ - } - - public IStatus execute(Session session, IProgressMonitor monitor) throws CVSException { - return executeRequest(session, Command.DEFAULT_OUTPUT_LISTENER, monitor); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ValidRequestsHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ValidRequestsHandler.java deleted file mode 100644 index 965ce9fd7..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/ValidRequestsHandler.java +++ /dev/null @@ -1,43 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.client.Session; - -/** - * Handles a "Valid-requests" response from the CVS server. - * <p> - * Suppose as a result of performing a command the CVS server responds - * as follows:<br> - * <pre> - * [...] - * Valid-requests ci co update Root Directory Valid-responses Argument ...\n - * [...] - * </pre> - * Then we remember the set of valid requests for this session in - * preparation for isValidRequests queries. - * </p> - */ -class ValidRequestsHandler extends ResponseHandler { - public String getResponseID() { - return "Valid-requests"; //$NON-NLS-1$ - } - - public void handle(Session session, String validRequests, - IProgressMonitor monitor) throws CVSException { - // remember the set of valid requests for this session - session.setValidRequests(validRequests); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Version.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Version.java deleted file mode 100644 index abb426e3f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/Version.java +++ /dev/null @@ -1,87 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; - -/** - * Here are some of the output formats we know about: - * - * Concurrent Versions System (CVS) 1.11.1p1 (client/server) - * Concurrent Versions System (CVS) NT 1.11.1.1 (Build 27) - * Concurrent Versions System (CVSNT) 1.11.1.3 (Build 57a) (client/server) - */ -public class Version extends RemoteCommand { - - private static final String CVS_NT_PREFIX_1 = "Concurrent Versions System (CVS) NT "; //$NON-NLS-1$ - private static final String CVS_NT_PREFIX_2 = "Concurrent Versions System (CVSNT) "; //$NON-NLS-1$ - private static final String CVS_PREFIX = "Concurrent Versions System (CVS) "; //$NON-NLS-1$ - /** - * @see Request#getRequestId() - */ - protected String getRequestId() { - return "version"; //$NON-NLS-1$ - } - - public IStatus execute(Session session, final ICVSRepositoryLocation location, IProgressMonitor monitor) throws CVSException { - - // The server may not support the version request - if ( ! session.isValidRequest(getRequestId())) { - IStatus status = new CVSStatus(IStatus.WARNING, CVSStatus.SERVER_IS_UNKNOWN, Policy.bind("Version.versionNotValidRequest", location.getHost()));//$NON-NLS-1$ - ((CVSRepositoryLocation)location).setServerPlaform(status); - CVSProviderPlugin.log(status); - return status; - } - - ICommandOutputListener listener = new ICommandOutputListener() { - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - String knownPrefix = null; - boolean isCVSNT = false; - if (line.startsWith(CVS_NT_PREFIX_1)) { - isCVSNT = true; - knownPrefix = CVS_NT_PREFIX_1; - } else if (line.startsWith(CVS_NT_PREFIX_2)) { - isCVSNT = true; - knownPrefix = CVS_NT_PREFIX_2; - } else if (line.startsWith(CVS_PREFIX)) { - knownPrefix = CVS_PREFIX; - } - IStatus status = OK; - if (knownPrefix != null) { - String versionNumber = line.substring(knownPrefix.length(), line.indexOf(' ', knownPrefix.length() + 1)); - if (versionNumber.startsWith("1.10") || versionNumber.equals("1.11") || versionNumber.equals("1.11.1")) { //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ - status = new CVSStatus(IStatus.ERROR, CVSStatus.UNSUPPORTED_SERVER_VERSION, Policy.bind("Version.unsupportedVersion", location.getHost(), versionNumber));//$NON-NLS-1$ - } else if (isCVSNT) { - status = new CVSStatus(IStatus.WARNING, CVSStatus.SERVER_IS_CVSNT, Policy.bind("Version.unsupportedCVSNT", location.getHost(), versionNumber));//$NON-NLS-1$ - } - } else { - status = new CVSStatus(IStatus.INFO, CVSStatus.SERVER_IS_UNKNOWN, Policy.bind("Version.unknownVersionFormat", location.getHost(), line));//$NON-NLS-1$ - } - ((CVSRepositoryLocation)location).setServerPlaform(status); - return status; - } - public IStatus errorLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - return new CVSStatus(IStatus.ERROR, CVSStatus.ERROR_LINE, line); - } - }; - - return execute(session, NO_GLOBAL_OPTIONS, NO_LOCAL_OPTIONS, new String[] {}, listener, monitor); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/AdminKSubstListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/AdminKSubstListener.java deleted file mode 100644 index 386841dc7..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/AdminKSubstListener.java +++ /dev/null @@ -1,91 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.Command.KSubstOption; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * Used with 'admin -ksubst' to capture lines of text that are issued - * as confirmation that the remote keyword substitution mode has been - * changed. When encountered, updates the local ResourceSyncInfo for - * the file in question to reflect - * - * e.g. - * RCS file: path/filename,v - * done - * - * We don't expect to see anything special on stderr if the command succeeds. - */ -public class AdminKSubstListener extends CommandOutputListener { - private KSubstOption ksubstMode; - - public AdminKSubstListener(KSubstOption ksubstMode) { - this.ksubstMode = ksubstMode; - } - - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, - IProgressMonitor monitor) { - if (line.startsWith("RCS file:")) { //$NON-NLS-1$ - String rcsFile = line.substring(10).trim(); - if (! rcsFile.endsWith(",v")) { //$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, - Policy.bind("AdminKSubstListener.expectedRCSFile", rcsFile)); //$NON-NLS-1$ - } - String remoteRootLocation = null; - try { - FolderSyncInfo info = commandRoot.getFolderSyncInfo(); - remoteRootLocation = info.getRemoteLocation(); - } catch (CVSException e) { - return e.getStatus(); - } - if (remoteRootLocation == null) { - return new CVSStatus(CVSStatus.ERROR, - Policy.bind("AdminKSubstListener.commandRootNotManaged")); //$NON-NLS-1$ - } - IPath rcsFilePath = new Path(rcsFile.substring(0, rcsFile.length() - 2)); - IPath remoteRootPath = new Path(remoteRootLocation); - if (! remoteRootPath.isPrefixOf(rcsFilePath)) { - return new CVSStatus(CVSStatus.ERROR, - Policy.bind("AdminKSubstListener.expectedChildOfCommandRoot", //$NON-NLS-1$ - rcsFilePath.toString(), remoteRootPath.toString())); - } - rcsFilePath = rcsFilePath.removeFirstSegments(remoteRootPath.segmentCount()); - try { - ICVSFile file = commandRoot.getFile(rcsFilePath.toString()); - //ResourceSyncInfo info = file.getSyncInfo(); - byte[] syncBytes = file.getSyncBytes(); - if (syncBytes != null) { - // only update sync info if we have it locally - file.setSyncBytes(ResourceSyncInfo.setKeywordMode(syncBytes, ksubstMode), ICVSFile.UNKNOWN); - } - } catch (CVSException e) { - return new CVSStatus(CVSStatus.ERROR, - Policy.bind("AdminKSubstListener.couldNotSetResourceSyncInfo", //$NON-NLS-1$ - rcsFilePath.toString(), e.toString())); - } - } - return OK; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/AnnotateListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/AnnotateListener.java deleted file mode 100644 index 8d0977c78..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/AnnotateListener.java +++ /dev/null @@ -1,99 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSAnnotateBlock; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; - -public class AnnotateListener extends CommandOutputListener { - -/** - * Handle output from the CVS Annotate command. - */ - ByteArrayOutputStream aStream = new ByteArrayOutputStream(); - List blocks = new ArrayList(); - int lineNumber; - String error; - - /** - * @return - */ - public String getError() { - return error; - } - - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - - CVSAnnotateBlock aBlock = new CVSAnnotateBlock(line, lineNumber++); - if (!aBlock.isValid()) { - error = line; - } - - /** - * Make sure all lines have a line terminator. - */ - try { - aStream.write(line.substring(aBlock.getSourceOffset()).getBytes()); - if (!(line.endsWith("\r") || line.endsWith("\r\n"))) { - aStream.write(System.getProperty("line.separator").getBytes()); - } - } catch (IOException e) { - } - add(aBlock); - return OK; - } - - public InputStream getContents() { - return new ByteArrayInputStream(aStream.toByteArray()); - } - - public List getCvsAnnotateBlocks() { - return blocks; - } - /** - * Add an annotate block to the receiver merging this block with the - * previous block if it is part of the same change. - * @param aBlock - */ - private void add(CVSAnnotateBlock aBlock) { - - int size = blocks.size(); - if (size == 0) { - blocks.add(aBlock); - } else { - CVSAnnotateBlock lastBlock = (CVSAnnotateBlock) blocks.get(size - 1); - if (lastBlock.getRevision().equals(aBlock.getRevision())) { - lastBlock.setEndLine(aBlock.getStartLine()); - } else { - blocks.add(aBlock); - } - } - } - - /** - * @return - */ - public boolean hasError() { - return (error != null); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/DiffListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/DiffListener.java deleted file mode 100644 index a9d0765f5..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/DiffListener.java +++ /dev/null @@ -1,58 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import java.io.PrintStream; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; - -public class DiffListener extends CommandOutputListener { - PrintStream patchStream; - - public DiffListener(PrintStream patchStream) { - this.patchStream = patchStream; - } - - public IStatus messageLine( - String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor) { - // ignore any server messages - if (getServerMessage(line, location) == null) { - // Ensure that the line doesn't end with a CR. - // This can happen if the remote file has CR/LF in it. - if (line.length() > 0 && line.charAt(line.length() - 1) == '\r') { - line = line.substring(0, line.length() - 1); - } - patchStream.println(line); - } - return OK; - } - - public IStatus errorLine( - String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor) { - // ignore server messages for now - this is used only with the diff - // request and the errors can be safely ignored. - if (getServerMessage(line, location) != null) { - return OK; - } - return super.errorLine(line, location, commandRoot, monitor); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/EditorsListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/EditorsListener.java deleted file mode 100644 index 096684f15..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/EditorsListener.java +++ /dev/null @@ -1,103 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2003 CSC SoftwareConsult GmbH & Co. OHG, Germany and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * CSC - Intial implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import java.util.LinkedList; -import java.util.List; -import java.util.StringTokenizer; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.EditorsInfo; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; - - -/** - * - * - * Listener for the Editors command - * - * @author <a href="mailto:kohlwes@gmx.net">Gregor Kohlwes</a> - * - */ -public class EditorsListener extends CommandOutputListener { - /** - * List to store the EditorsInfos - */ - private List infos = new LinkedList(); - - /** - * Name of the current file - */ - private String fileName; - - /** - * Constructor EditorsListener. - */ - public EditorsListener() { - } - - /** - * @see org.eclipse.team.internal.ccvs.core.client.listeners.ICommandOutputListener#messageLine(java.lang.String, org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation, org.eclipse.team.internal.ccvs.core.ICVSFolder, org.eclipse.core.runtime.IProgressMonitor) - */ - public IStatus messageLine( - String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor) { - - // If there is a file with multiple editors - // then cvs will write the filename only - // in the first line and the following - // line will start with a Tab - if (line.startsWith("\t")) { //$NON-NLS-1$ - line = fileName + line; - } - EditorsInfo info = new EditorsInfo(); - StringTokenizer tokenizer = new StringTokenizer(line,"\t"); //$NON-NLS-1$ - int i = 0; - while(tokenizer.hasMoreTokens()) { - String token = tokenizer.nextToken(); - switch (i) { - case 0: - info.setFileName(token); - fileName = token; - break; - case 1: - info.setUserName(token); - break; - case 2: - info.setDateString(token); - break; - case 3: - info.setComputerName(token); - break; - default : - break; - } - i++; - } - - infos.add(info); - return OK; - - } - /** - * Method getEditorsInfos. - * @return IEditorsInfo[] - */ - public EditorsInfo[] getEditorsInfos() { - return (EditorsInfo[]) infos.toArray(new EditorsInfo[infos.size()]); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ICommandOutputListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ICommandOutputListener.java deleted file mode 100644 index 58281d8ae..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ICommandOutputListener.java +++ /dev/null @@ -1,72 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.Policy; - -/** - * Instances of this interface can be passed to the <code>Command#execute</code> methods - * and will receive notification when M or E messages are received from the server. - */ -public interface ICommandOutputListener { - - /*** Status to be returned when no error or warning occured ***/ - public static final IStatus OK = new CVSStatus(CVSStatus.OK, Policy.bind("ok")); //$NON-NLS-1$ - - public static final String SERVER_PREFIX = "server: "; //$NON-NLS-1$ - public static final String SERVER_ABORTED_PREFIX = "[server aborted]: "; //$NON-NLS-1$ - public static final String RTAG_PREFIX = "rtag: "; //$NON-NLS-1$ - - /** - * Invoked when a message line is received from the server. - * <p> - * Any status other than ICommandOutputListener.OK will be accumulated - * by the command and returned. The severity of the status matches those of - * IStatus and must indicate whether this is a warning, error, or informational - * text.while the code should be one of the codes provided by CVSStatus. - * The status code must not be CVSStatus.SERVER_ERROR. - * </p> - * - * @param line the line of message text sent by the server - * @param commandRoot the root directory of the command - * @param monitor the progress monitor - * @return a status indicating success or failure based on the text - */ - public IStatus messageLine(String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor); - - /** - * Invoked when an error line is received from the server. - * <p> - * Any status other than ICommandOutputListener.OK will be accumulated - * by the command and returned. The severity of the status matches those of - * IStatus and must indicate whether this is a warning, error, or informational - * text.while the code should be one of the codes provided by CVSStatus. - * The status code must not be CVSStatus.SERVER_ERROR. - * </p> - * - * @param line the line of error text sent by the server - * @param commandRoot the root directory of the command - * @param monitor the progress monitor - * @return a status indicating success or failure based on the text - */ - public IStatus errorLine(String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IConsoleListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IConsoleListener.java deleted file mode 100644 index ec5aa2c8b..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IConsoleListener.java +++ /dev/null @@ -1,40 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import org.eclipse.core.runtime.IStatus; - -public interface IConsoleListener { - /** - * Called when a command is invoked. - * @param line the command invocation string - */ - public void commandInvoked(String line); - - /** - * Called when a line of message text has been received. - * @param line the line of text - */ - public void messageLineReceived(String line); - - /** - * Called when a line of error text has been received. - * @param line the line of text - */ - public void errorLineReceived(String line); - - /** - * Called when a command has been completed. - * @param status the status code, or null if not applicable - * @param exception an exception, or null if not applicable - */ - public void commandCompleted(IStatus status, Exception exception); -} 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 deleted file mode 100644 index b7744fcab..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IStatusListener.java +++ /dev/null @@ -1,27 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import org.eclipse.team.internal.ccvs.core.ICVSFolder; - -public interface IStatusListener { - - public static final String FOLDER_REVISION = ""; //$NON-NLS-1$ - - /** - * Provides access to the revision of a file through the use of the Status command. - * - * @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(ICVSFolder commandRoot, String 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 deleted file mode 100644 index 67874f531..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/IUpdateMessageListener.java +++ /dev/null @@ -1,51 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import org.eclipse.team.internal.ccvs.core.ICVSFolder; - -/** - * This listener is used by RemoteFolder to listener for E and M messages - * from the CVS server in order to determine the files and folders contained in a parent folder. - */ -public interface IUpdateMessageListener { - /** - * 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, String 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 directoryInformation(ICVSFolder commandRoot, String path, boolean newDirectory); - /** - * 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 fileInformation(int type, ICVSFolder parent, String filename); - /** - * 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 fileDoesNotExist(ICVSFolder parent, String filename); -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/LogEntry.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/LogEntry.java deleted file mode 100644 index 1d5e49960..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/LogEntry.java +++ /dev/null @@ -1,99 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import java.util.Date; - -import org.eclipse.core.runtime.PlatformObject; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFile; -import org.eclipse.team.internal.ccvs.core.ILogEntry; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFile; - -public class LogEntry extends PlatformObject implements ILogEntry { - - private RemoteFile file; - private String author; - private Date date; - private String comment; - private String state; - private CVSTag[] tags; - - public LogEntry(RemoteFile file, String revision, String author, Date date, String comment, String state, CVSTag[] tags) { - this.file = file.toRevision(revision); - this.author = author; - this.date = date; - this.comment = comment; - this.state = state; - this.tags = tags; - } - - /** - * @see ILogEntry#getRevision() - */ - public String getRevision() { - return file.getRevision(); - } - - /** - * @see ILogEntry#getAuthor() - */ - public String getAuthor() { - return author; - } - - /** - * @see ILogEntry#getDate() - */ - public Date getDate() { - return date; - } - - /** - * @see ILogEntry#getComment() - */ - public String getComment() { - return comment; - } - - /** - * @see ILogEntry#getState() - */ - public String getState() { - return state; - } - - /** - * @see ILogEntry#getTags() - */ - public CVSTag[] getTags() { - CVSTag[] result = new CVSTag[tags.length]; - System.arraycopy(tags, 0, result, 0, tags.length); - return result; - } - - /** - * @see ILogEntry#getRemoteFile() - */ - public ICVSRemoteFile getRemoteFile() { - return file; - } - - /** - * @see ILogEntry#isDeletion() - */ - public boolean isDeletion() { - return getState().equals("dead"); //$NON-NLS-1$ - } - -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/LogListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/LogListener.java deleted file mode 100644 index 6d692b1da..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/LogListener.java +++ /dev/null @@ -1,172 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import java.util.ArrayList; -import java.util.Date; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.DateUtil; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFile; - -public class LogListener extends CommandOutputListener { - private List entries; - private RemoteFile file; - - // state - private final int BEGIN = 0, SYMBOLIC_NAMES = 1, REVISION = 2, COMMENT = 3, DONE = 4; - private List tagNames = new ArrayList(5); - private List tagRevisions = new ArrayList(5); - private int state = BEGIN; // current state - private String creationDate; - private String author; - private String revision; // revision number - private String fileState; // - private StringBuffer comment; // comment - - private static final String NOTHING_KNOWN_ABOUT = "nothing known about "; //$NON-NLS-1$ - - public LogListener(RemoteFile file, List entries) { - this.file = file; - this.entries = entries; - } - - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, - IProgressMonitor monitor) { - // Fields we will find in the log for a file - // keys = String (tag name), values = String (tag revision number) */ - switch (state) { - case BEGIN: - if (line.startsWith("symbolic names:")) { //$NON-NLS-1$ - state = SYMBOLIC_NAMES; - } else if (line.startsWith("revision ")) { //$NON-NLS-1$ - revision = line.substring(9); - state = REVISION; - } - break; - case SYMBOLIC_NAMES: - if (line.startsWith("keyword substitution:")) { //$NON-NLS-1$ - state = BEGIN; - } else { - int firstColon = line.indexOf(':'); - String tagName = line.substring(1, firstColon); - String tagRevision = line.substring(firstColon + 2); - tagNames.add(tagName); - tagRevisions.add(tagRevision); - } - break; - case REVISION: - // date: 2000/06/19 04:56:21; author: somebody; state: Exp; lines: +114 -45 - // get the creation date - int endOfDateIndex = line.indexOf(';', 6); - creationDate = line.substring(6, endOfDateIndex) + " GMT"; //$NON-NLS-1$ - - // get the author name - int endOfAuthorIndex = line.indexOf(';', endOfDateIndex + 1); - author = line.substring(endOfDateIndex + 11, endOfAuthorIndex); - - // get the file state (because this revision might be "dead") - fileState = line.substring(endOfAuthorIndex + 10, line.indexOf(';', endOfAuthorIndex + 1)); - comment = new StringBuffer(); - state = COMMENT; - break; - case COMMENT: - // skip next line (info about branches) if it exists, if not then it is a comment line. - if (line.startsWith("branches:")) break; //$NON-NLS-1$ - if (line.equals("=============================================================================") //$NON-NLS-1$ - || line.equals("----------------------------")) { //$NON-NLS-1$ - state = DONE; - break; - } - if (comment.length() != 0) comment.append('\n'); - comment.append(line); - break; - } - if (state == DONE) { - // we are only interested in tag names for this revision, remove all others. - List thisRevisionTags = new ArrayList(3); - for (int i = 0; i < tagNames.size(); i++) { - String tagName = (String) tagNames.get(i); - String tagRevision = (String) tagRevisions.get(i); - // If this is a branch tag then only include this tag with the revision - // that is the root of this branch (e.g. 1.1 is root of branch 1.1.2). - boolean isBranch = isBranchTag(tagRevision); - if (isBranch) { - int lastDot = tagRevision.lastIndexOf('.'); - if (lastDot == -1) { - CVSProviderPlugin.log(IStatus.ERROR, - Policy.bind("LogListener.invalidRevisionFormat", tagName, tagRevision), null); //$NON-NLS-1$ - } else { - if (tagRevision.charAt(lastDot - 1) == '0' && tagRevision.charAt(lastDot - 2) == '.') { - lastDot = lastDot - 2; - } - tagRevision = tagRevision.substring(0, lastDot); - } - } - if (tagRevision.equals(revision)) { - int type = isBranch ? CVSTag.BRANCH : CVSTag.VERSION; - thisRevisionTags.add(new CVSTag(tagName, type)); - } - } - Date date = DateUtil.convertFromLogTime(creationDate); - LogEntry entry = new LogEntry(file, revision, author, date, - comment.toString(), fileState, (CVSTag[]) thisRevisionTags.toArray(new CVSTag[0])); - entries.add(entry); - state = BEGIN; - // XXX should we reset the tagNames and tagRevisions stuff? - } - return OK; - } - - public IStatus errorLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - String serverMessage = getServerMessage(line, location); - if (serverMessage != null) { - // look for the following condition - // E cvs server: nothing known about .vcm_meta - if (serverMessage.startsWith(NOTHING_KNOWN_ABOUT)) { - String filename = serverMessage.substring(NOTHING_KNOWN_ABOUT.length()); - return new CVSStatus(IStatus.ERROR, CVSStatus.DOES_NOT_EXIST, commandRoot, line); - } - } - return OK; - } - - /** branch tags have odd number of segments or have - * an even number with a zero as the second last segment - * e.g: 1.1.1, 1.26.0.2 are branch revision numbers */ - protected boolean isBranchTag(String tagName) { - // First check if we have an odd number of segments (i.e. even number of dots) - int numberOfDots = 0; - int lastDot = 0; - for (int i = 0; i < tagName.length(); i++) { - if (tagName.charAt(i) == '.') { - numberOfDots++; - lastDot = i; - } - } - if ((numberOfDots % 2) == 0) return true; - if (numberOfDots == 1) return false; - - // If not, check if the second lat segment is a zero - if (tagName.charAt(lastDot - 1) == '0' && tagName.charAt(lastDot - 2) == '.') return true; - return false; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ModuleDefinitionsListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ModuleDefinitionsListener.java deleted file mode 100644 index 4de19a23b..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ModuleDefinitionsListener.java +++ /dev/null @@ -1,71 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import java.util.HashMap; -import java.util.Map; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; - -/* - * This class pares the output of the "cvs checkout -c" command which returns the list of modules - * defined in the CVSROOT/modules file. - */ -public class ModuleDefinitionsListener extends CommandOutputListener { - - // the last line read from the context (used to accumulate multi-line definitions) - private String lastLine = ""; //$NON-NLS-1$ - - private Map moduleMap; - - public ModuleDefinitionsListener() { - reset(); - } - - /* - * @see ICommandOutputListener#messageLine(String, ICVSFolder, IProgressMonitor) - */ - public IStatus messageLine( - String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor) { - - // Lines that start with a space indicate a multi line entry - if( line.charAt(0) == ' ' ) { - lastLine += line; - line = lastLine; - } - else - lastLine = line; - - // Use the module name as the key so that multi-line modules will be recorded properly - int firstSpace = line.indexOf(" "); //$NON-NLS-1$ - if (firstSpace > -1) { - String module = line.substring(0, firstSpace); - moduleMap.put(module, line); - } - return OK; - } - - public String[] getModuleExpansions() { - return (String[])moduleMap.values().toArray(new String[moduleMap.size()]); - } - - public void reset() { - this.moduleMap = new HashMap(); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ModuleExpansion.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ModuleExpansion.java deleted file mode 100644 index 12badc099..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/ModuleExpansion.java +++ /dev/null @@ -1,126 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; -import java.util.Map; - -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; - -/** - * - */ -public class ModuleExpansion { - - /** Name of the CVS module as found in the CVSROOT/modules file */ - private String moduleName; - - /** Expansion of the module name returned by the CVS server */ - private String[] expansions; - - private LocalOption[] options; - - ModuleExpansion(String moduleName, String[] expansions, LocalOption[] options) { - this.moduleName = moduleName; - this.expansions = expansions; - this.options = options; - } - - /** - * @see IModuleExpansion#getModuleName() - */ - public String getModuleName() { - return moduleName; - } - - /** - * @see IModuleExpansion#getModuleExpansionString() - */ - public String getModuleExpansionString() { - String result = expansions[0]; - for (int i=1;i<expansions.length; i++) - result = result + ", " + expansions[i]; //$NON-NLS-1$ - return result; - } - - /** - * @see IModuleExpansion#getExpansions() - */ - public String[] getExpansions() { - return expansions; - } - - public LocalOption[] getOptions() { - return options; - } - - /** - * Translate an array of module names to their expansions. - * The resulting List of Strings may be bigger than the original - */ - private List getExpansionsFor(String[] possibleModules, Map moduleMappings, int depth) throws CVSException { - List result = new ArrayList(); - for (int i=0;i<possibleModules.length;i++) { - // Is it a module? - if (possibleModules[i].charAt(0) == '&') - result.addAll(getExpansionsFor(possibleModules[i].substring(1), moduleMappings, depth)); - else - result.add(possibleModules[i]); - } - return result; - } - - /** - * Translate a module name to its expansion. - * The resulting List may contain one or more Strings - */ - private List getExpansionsFor(String module, Map moduleMappings, int depth) throws CVSException { - if (depth > moduleMappings.size()) { - // Indicate that a circular reference exists - throw new CVSException(Policy.bind("ModuleExpansion.circular", module));//$NON-NLS-1$ - } - Object mappings = moduleMappings.get(module); - if (mappings == null) { - // If there's no mapping assume it is a project name - List result = new ArrayList(); - result.add(module); - return result; - } else { - // Follow any expansion chains - return getExpansionsFor(((ModuleExpansion)mappings).expansions, moduleMappings, depth + 1); - } - } - - /** - * Resolve the module mappings using moduleMappings which maps - * module names to their ModuleExpansion - */ - public void resolveModuleReferencesUsing(Map moduleMappings) { - try { - List result = getExpansionsFor(expansions, moduleMappings, 0); - expansions = (String[])result.toArray(new String[result.size()]); - } catch (CVSException e) { - // Is this the best way to show the circular reference problem? - // Or should we just leave the expansions untouched? - List result = new ArrayList(); - result.add(e.getStatus().getMessage()); - result.addAll(Arrays.asList(expansions)); - expansions = (String[])result.toArray(new String[result.size()]); - } - } -} - - 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 deleted file mode 100644 index eb6b778ce..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/StatusListener.java +++ /dev/null @@ -1,87 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.Session; - -public class StatusListener extends CommandOutputListener { - private static boolean isFolder = false; - private IStatusListener statusListener; - - public StatusListener(IStatusListener statusListener) { - this.statusListener = statusListener; - } - - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, - IProgressMonitor monitor) { - - // We're only concerned about file revisions. - if (line.startsWith(" Repository revision:")) { //$NON-NLS-1$ - if (!line.startsWith(" Repository revision: No revision control file")) { //$NON-NLS-1$ - int separatingTabIndex = line.indexOf('\t', 24); - String remoteRevision = line.substring(24, separatingTabIndex); - - // This is the full location on the server (e.g. /home/cvs/repo/project/file.txt) - String fileLocation = line.substring(separatingTabIndex + 1, line.length() - 2); - - // Inform the listener about the file revision - statusListener.fileStatus(commandRoot, removeAtticSegment(fileLocation), remoteRevision); - } - } - return OK; - } - - public IStatus errorLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, IProgressMonitor monitor) { - String serverMessage = getServerMessage(line, location); - if (serverMessage != null) { - if (serverMessage.startsWith("conflict:")) {//$NON-NLS-1$ - // We get this because we made up an entry line to send to the server - // Therefore, we make this a warning!!! - return new CVSStatus(CVSStatus.WARNING, CVSStatus.CONFLICT, commandRoot, line); - } - if (serverMessage.startsWith("Examining")) {//$NON-NLS-1$ - isFolder = true; - return OK; - } - } - if (isFolder) { - // This used to do something but it was obviously wrong and there was no indication - // why it was needed. Therefore, I have removed the code to see if anything is effected - isFolder = false; - } - return super.errorLine(line, location, commandRoot, monitor); - } - - /** - * If the status returns that the file is in the Attic, then remove the - * Attic segment. This is because files added to a branch that are not in - * the main trunk (HEAD) are added to the Attic but cvs does magic on - * updateto put them in the correct location. - * (e.g. /project/Attic/file.txt -> /project/file.txt) - */ - private String removeAtticSegment(String path) { - int lastSeparator = path.lastIndexOf(Session.SERVER_SEPARATOR); - if (lastSeparator == -1) return path; - int secondLastSeparator = path.lastIndexOf(Session.SERVER_SEPARATOR, lastSeparator - 1); - if (secondLastSeparator == -1) return path; - String secondLastSegment = path.substring(secondLastSeparator + 1, lastSeparator); - if (secondLastSegment.equals("Attic")) { //$NON-NLS-1$ - return path.substring(0, secondLastSeparator) + path.substring(lastSeparator); - } - return path; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/TagListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/TagListener.java deleted file mode 100644 index b2cd6f019..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/TagListener.java +++ /dev/null @@ -1,63 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; - -public class TagListener extends CommandOutputListener { - - /* - * @see ICommandOutputListener#messageLine(String, ICVSFolder, IProgressMonitor) - */ - public IStatus messageLine( - String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor) { - - // Received a warning in the form: - // W folder/file : v1 already exists on version 1.2 : NOT MOVING tag to version 1.3 - if( line.charAt(0) == 'W' ) { - return new CVSStatus(CVSStatus.WARNING, CVSStatus.TAG_ALREADY_EXISTS, commandRoot, line.substring(2)); - } - - return OK; - } - - /* - * @see ICommandOutputListener#errorLine(String, ICVSFolder, IProgressMonitor) - */ - public IStatus errorLine( - String line, - ICVSRepositoryLocation location, - ICVSFolder commandRoot, - IProgressMonitor monitor) { - - // Ignore the lines: Tagging folder1/folder2 - String serverMessage = getServerMessage(line, location); - if ((serverMessage != null) && serverMessage.startsWith("Tagging")) { //$NON-NLS-1$ - return OK; - } - String rtagMessage = getServerRTagMessage(line, location); - if(rtagMessage != null && rtagMessage.startsWith("Tagging") ) { //$NON-NLS-1$ - return OK; - } - - return super.errorLine(line, location, commandRoot, monitor); - } - -} 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 deleted file mode 100644 index 571b4fc06..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/client/listeners/UpdateListener.java +++ /dev/null @@ -1,197 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.client.listeners; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.CommandOutputListener; -import org.eclipse.team.internal.ccvs.core.client.Update; - -public class UpdateListener extends CommandOutputListener { - - IUpdateMessageListener updateMessageListener; - boolean merging = false; - - public UpdateListener(IUpdateMessageListener updateMessageListener) { - this.updateMessageListener = updateMessageListener; - } - - public IStatus messageLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, - IProgressMonitor monitor) { - if (updateMessageListener == null) return OK; - if(line.startsWith("Merging differences")) { //$NON-NLS-1$ - merging = true; - } else if(line.indexOf(' ')==1) { - // We have a message that indicates the type of update. The possible messages are - // defined by the prefix constants MLP_*. - String path = line.substring(2); - char changeType = line.charAt(0); - - // calculate change type - int type = 0; - switch(changeType) { - case 'A': type = Update.STATE_ADDED_LOCAL; break; // new file locally that was added but not comitted to server yet - case '?': type = Update.STATE_UNKOWN; break; // new file locally but not added to server - case 'U': type = Update.STATE_REMOTE_CHANGES; break; // remote changes to an unmodified local file - case 'R': type = Update.STATE_DELETED; break; // removed locally but still exists on the server - case 'M': type = Update.STATE_MODIFIED; break; // modified locally - case 'C': type = Update.STATE_CONFLICT; break; // modified locally and on the server but cannot be auto-merged - case 'D': type = Update.STATE_DELETED; break; // deleted locally but still exists on server - default: type = Update.STATE_NONE; - } - - if (merging) { - // If we are merging the modified prefix is used both to show merges and - // local changes. We have to detect this case and use a more specific change - // type. - if (type == Update.STATE_MODIFIED) - type = Update.STATE_MERGEABLE_CONFLICT; - merging = false; - } - updateMessageListener.fileInformation(type, commandRoot, path); - } - return OK; - } - - /** - * This handler is used by the RemoteResource hierarchy to retrieve E messages - * from the CVS server in order to determine the folders contained in a parent folder. - * - * WARNING: This class parses the message output to determine the state of files in the - * repository. Unfortunately, these messages seem to be customizable on a server by server basis. - * - * Here's a list of responses we expect in various situations: - * - * Directory exists remotely: - * cvs server: Updating folder1/folder2 - * Directory doesn't exist remotely: - * cvs server: skipping directory folder1/folder2 - * New (or unknown) remote directory - * cvs server: New Directory folder1/folder2 - * File removed remotely - * cvs server: folder1/file.ext is no longer in the repository - * cvs server: warning: folder1/file.ext is not (any longer) pertinent - * Locally added file was added remotely as well - * cvs server: conflict: folder/file.ext created independently by second party - * File removed locally and modified remotely - * cvs server: conflict: removed file.txt was modified by second party - * File modified locally but removed remotely - * cvs server: conflict: file.txt is modified but no longer in the repository - * Ignored Messages - * cvs server: cannot open directory ... - * cvs server: nothing known about ... - * Tag error that really means there are no files in a directory - * cvs [server aborted]: no such tag - * Merge contained conflicts - * rcsmerge: warning: conflicts during merge - */ - public IStatus errorLine(String line, ICVSRepositoryLocation location, ICVSFolder commandRoot, - IProgressMonitor monitor) { - - try { - String serverMessage = getServerMessage(line, location); - if (serverMessage != null) { - // Strip the prefix from the line - String message = serverMessage; - if (message.startsWith("Updating")) { //$NON-NLS-1$ - if (updateMessageListener != null) { - String path = message.substring(9); - updateMessageListener.directoryInformation(commandRoot, path, false); - } - return OK; - } else if (message.startsWith("skipping directory")) { //$NON-NLS-1$ - if (updateMessageListener != null) { - String path = message.substring(18).trim(); - updateMessageListener.directoryDoesNotExist(commandRoot, path); - } - return OK; - } else if (message.startsWith("New directory")) { //$NON-NLS-1$ - if (updateMessageListener != null) { - String path = message.substring(15, message.lastIndexOf('\'')); - updateMessageListener.directoryInformation(commandRoot, path, true); - } - return OK; - } 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(commandRoot, filename); - } - return OK; - } else if (message.startsWith("conflict:")) { //$NON-NLS-1$ - /* - * We can get the following conflict warnings - * cvs server: conflict: folder/file.ext created independently by second party - * cvs server: conflict: removed file.txt was modified by second party - * cvs server: conflict: file.txt is modified but no longer in the repository - * If we get the above line, we have conflicting additions or deletions and we can expect a server error. - * We still get "C foler/file.ext" so we don't need to do anything else (except in the remotely deleted case) - */ - if (updateMessageListener != null) { - 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(commandRoot, filename); - } - } - return new CVSStatus(CVSStatus.WARNING, CVSStatus.CONFLICT, commandRoot, line); - } else if (message.startsWith("warning:")) { //$NON-NLS-1$ - /* - * We can get the following conflict warnings - * cvs server: warning: folder1/file.ext is not (any longer) pertinent - * If we get the above line, we have local changes to a remotely deleted file. - */ - if (updateMessageListener != null) { - if (message.endsWith("is not (any longer) pertinent")) { //$NON-NLS-1$ - String filename = message.substring(9, message.length() - 30); - updateMessageListener.fileDoesNotExist(commandRoot, filename); - } - } - return new CVSStatus(CVSStatus.WARNING, CVSStatus.CONFLICT, commandRoot, line); - } else if (message.startsWith("conflicts")) { //$NON-NLS-1$ - // This line is info only. The server doesn't report an error. - return new CVSStatus(IStatus.INFO, CVSStatus.CONFLICT, commandRoot, line); - } else if (!message.startsWith("cannot open directory") //$NON-NLS-1$ - && !message.startsWith("nothing known about")) { //$NON-NLS-1$ - return super.errorLine(line, location, commandRoot, monitor); - } - } else { - String serverAbortedMessage = getServerAbortedMessage(line, location); - if (serverAbortedMessage != null) { - // Strip the prefix from the line - String message = serverAbortedMessage; - if (message.startsWith("no such tag")) { //$NON-NLS-1$ - // This is reported from CVS when a tag is used on the update there are no files in the directory - // To get the folders, the update request should be re-issued for HEAD - return new CVSStatus(CVSStatus.WARNING, CVSStatus.NO_SUCH_TAG, commandRoot, line); - } else { - return super.errorLine(line, location, commandRoot, monitor); - } - } else if (line.equals("rcsmerge: warning: conflicts during merge")) { - // There were conflicts in the merge - return new CVSStatus(CVSStatus.WARNING, CVSStatus.CONFLICT, commandRoot, line); - } - } - } catch (StringIndexOutOfBoundsException e) { - // Something went wrong in the parsing of the message. - // Return a status indicating the problem - if (CVSProviderPlugin.getPlugin().isDebugging()) { - System.out.println("Error parsing E line: " + line); - } - return new CVSStatus(CVSStatus.ERROR, CVSStatus.ERROR_LINE_PARSE_FAILURE, commandRoot, line); - } - return super.errorLine(line, location, commandRoot, monitor); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSAuthenticationException.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSAuthenticationException.java deleted file mode 100644 index fc5ddfa62..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSAuthenticationException.java +++ /dev/null @@ -1,46 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.Policy; - -public class CVSAuthenticationException extends CVSException { - - /** - * Creates a new <code>CVSAuthenticationException</code> - * - * @param detail a message that describes the exception in detail. - */ - public CVSAuthenticationException(String detail) { - super(Policy.bind("CVSAuthenticationException.detail", new Object[] { detail })); //$NON-NLS-1$ - } - - /** - * Creates a new <code>CVSAuthenticationException</code> - * - * @param cvsroot the cvs server. - * @param detail a message that describes the exception in detail. - */ - public CVSAuthenticationException(String cvsroot, String detail) { - this(detail); - } - /** - * Creates a new <code>CVSAuthenticationException</code> - * - * @param status the status result describing this exception. - */ - public CVSAuthenticationException(IStatus status) { - super(status); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSCommunicationException.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSCommunicationException.java deleted file mode 100644 index 684ea5c39..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSCommunicationException.java +++ /dev/null @@ -1,78 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import java.io.InterruptedIOException; - -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.MultiStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.Policy; - -public class CVSCommunicationException extends CVSException { - - /** - * Create a new <code>CVSCommunicationException with the - * given status. - */ - private CVSCommunicationException(IStatus status) { - super(status); - } - /** - * Create a new <code>CVSCommunicationException with the - * given message. - */ - public CVSCommunicationException(String message) { - super(message); - } - /** - * Create a new <code>CVSCommunicationException. - * - * @param message a message describing the exception in detail. - * @param the caught exception that has caused the communication - * exception. - */ - public CVSCommunicationException(String message, Exception e) { - super(message, e); - } - /** - * Create a new <code>CVSCommunicationException. - * - * @param the caught exception that has caused the communication - * exception. - */ - public CVSCommunicationException(Exception e) { - this(getStatusFor(e)); - } - - public static IStatus getStatusFor(Exception e) { - if (e instanceof InterruptedIOException) { - InterruptedIOException ioEx = (InterruptedIOException) e; - MultiStatus status = new MultiStatus(CVSProviderPlugin.ID, 0, getMessageFor(e), e); - status.add(new CVSStatus(IStatus.ERROR, Policy.bind("CVSCommunicationException.interruptCause"))); //$NON-NLS-1$ - status.add(new CVSStatus(IStatus.ERROR, Policy.bind("CVSCommunicationException.interruptSolution"))); //$NON-NLS-1$ - status.add(new CVSStatus(IStatus.ERROR, Policy.bind("CVSCommunicationException.alternateInterruptCause"))); //$NON-NLS-1$ - status.add(new CVSStatus(IStatus.ERROR, Policy.bind("CVSCommunicationException.alternateInterruptSolution"))); //$NON-NLS-1$ - return status; - } - return new CVSStatus(IStatus.ERROR, getMessageFor(e), e); - } - - public static String getMessageFor(Throwable throwable) { - String message = Policy.bind(throwable.getClass().getName(), new Object[] {throwable.getMessage()}); - if (message.equals(throwable.getClass().getName())) - message = Policy.bind("CVSCommunicationException.io", new Object[] {throwable.toString()}); //$NON-NLS-1$ - return message; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSRepositoryLocation.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSRepositoryLocation.java deleted file mode 100644 index bdb1d76c5..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSRepositoryLocation.java +++ /dev/null @@ -1,979 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import java.io.IOException; -import java.net.MalformedURLException; -import java.net.URL; -import java.util.ArrayList; -import java.util.List; -import java.util.Map; -import java.util.Properties; -import java.util.StringTokenizer; - -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IConfigurationElement; -import org.eclipse.core.runtime.IExtension; -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.core.runtime.Platform; -import org.eclipse.core.runtime.PlatformObject; -import org.eclipse.core.runtime.Status; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -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.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.IConnectionMethod; -import org.eclipse.team.internal.ccvs.core.IUserAuthenticator; -import org.eclipse.team.internal.ccvs.core.IUserInfo; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFile; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFolder; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFolderTree; -import org.eclipse.team.internal.ccvs.core.resources.RemoteModule; - -/** - * This class manages a CVS repository location. - * - * It provides the mapping between connection method name and the - * plugged in ICunnectionMethod. - * - * It parses location strings into instances. - * - * It provides a method to open a connection to the server along - * with a method to validate that connections can be made. - * - * It manages its user info using the plugged in IUserAuthenticator - * (unless a username and password are provided as part of the creation - * string, in which case, no authenticator is used). - * - * Instances must be disposed of when no longer needed in order to - * notify the authenticator so cached properties can be cleared - * - */ -public class CVSRepositoryLocation extends PlatformObject implements ICVSRepositoryLocation, IUserInfo { - - // server platform constants - public static final int UNDETERMINED_PLATFORM = 0; - public static final int CVS_SERVER = 1; - public static final int CVSNT_SERVER = 2; - public static final int UNSUPPORTED_SERVER = 3; - public static final int UNKNOWN_SERVER = 4; - - // static variables for extension points - private static IUserAuthenticator authenticator; - private static IConnectionMethod[] pluggedInConnectionMethods = null; - - private IConnectionMethod method; - private String user; - private String password; - private String host; - private int port; - private String root; - private boolean userFixed; - private boolean passwordFixed; - - private int serverPlatform = UNDETERMINED_PLATFORM; - private String remoteCVSProgramName = DEFAULT_REMOTE_CVS_PROGRAM_NAME; - - public static final char COLON = ':'; - public static final char HOST_SEPARATOR = '@'; - public static final char PORT_SEPARATOR = '#'; - public static final boolean STANDALONE_MODE = (System.getProperty("eclipse.cvs.standalone")==null) ? //$NON-NLS-1$ - false :(new Boolean(System.getProperty("eclipse.cvs.standalone")).booleanValue()); //$NON-NLS-1$ - public static final String DEFAULT_REMOTE_CVS_PROGRAM_NAME = "cvs"; //$NON-NLS-1$ - - // command to start remote cvs in server mode - private static final String INVOKE_SVR_CMD = "server"; //$NON-NLS-1$ - - // fields needed for caching the password - public static final String INFO_PASSWORD = "org.eclipse.team.cvs.core.password";//$NON-NLS-1$ - public static final String INFO_USERNAME = "org.eclipse.team.cvs.core.username";//$NON-NLS-1$ - public static final String AUTH_SCHEME = "";//$NON-NLS-1$ - public static final URL FAKE_URL; - - public static final String USER_VARIABLE = "{user}"; //$NON-NLS-1$ - public static final String PASSWORD_VARIABLE = "{password}"; //$NON-NLS-1$ - public static final String HOST_VARIABLE = "{host}"; //$NON-NLS-1$ - public static final String PORT_VARIABLE = "{port}"; //$NON-NLS-1$ - - static { - URL temp = null; - try { - temp = new URL("http://org.eclipse.team.cvs.core");//$NON-NLS-1$ - } catch (MalformedURLException e) { - } - FAKE_URL = temp; - } - - /* - * Create a CVSRepositoryLocation from its composite parts. - */ - private CVSRepositoryLocation(IConnectionMethod method, String user, String password, String host, int port, String root, boolean userFixed, boolean passwordFixed) { - this.method = method; - this.user = user; - this.password = password; - this.host = host; - this.port = port; - this.root = root; - // The username can be fixed only if one is provided - if (userFixed && (user != null)) - this.userFixed = true; - // The password can only be fixed if the username is and a password is provided - if (userFixed && passwordFixed && (password != null)) - this.passwordFixed = true; - } - - /* - * Create the connection to the remote server. - * If anything fails, an exception will be thrown and must - * be handled by the caller. - */ - private Connection createConnection(String password, IProgressMonitor monitor) throws CVSException { - // FIXME Should the open() of Connection be done in the constructor? - // The only reason it should is if connections can be reused (they aren't reused now). - // FIXME! monitor is unused - Connection connection = new Connection(this, method.createConnection(this, password)); - connection.open(monitor); - return connection; - } - - /* - * Dispose of the receiver by clearing any cached authorization information. - * This method shold only be invoked when the corresponding adapter is shut - * down or a connection is being validated. - */ - public void dispose() throws CVSException { - flushCache(); - } - - /* - * Flush the keyring entry associated with the receiver - */ - private void flushCache() throws CVSException { - try { - Platform.flushAuthorizationInfo(FAKE_URL, getLocation(), AUTH_SCHEME); - } catch (CoreException e) { - // We should probably wrap the CoreException here! - CVSProviderPlugin.log(e); - throw new CVSException(IStatus.ERROR, IStatus.ERROR, Policy.bind("CVSRepositoryLocation.errorFlushing", getLocation()), e);//$NON-NLS-1$ - } - } - - /* - * @see ICVSRepositoryLocation#getHost() - */ - public String getHost() { - return host; - } - - /* - * @see IRepositoryLocation#getLocation() - * - * The username is included if it is fixed. - * The password is never included even if it is fixed. - * The port is included if it is not the default port. - */ - public String getLocation() { - return COLON + method.getName() + COLON + - (userFixed?(user + - (passwordFixed?(COLON + password):"")//$NON-NLS-1$ - + HOST_SEPARATOR):"") +//$NON-NLS-1$ - host + COLON + - ((port == USE_DEFAULT_PORT)?"":(new Integer(port).toString())) + //$NON-NLS-1$ - root; - } - - /* - * @see ICVSRepositoryLocation#getMethod() - */ - public IConnectionMethod getMethod() { - return method; - } - - public boolean setMethod(String methodName) { - IConnectionMethod newMethod = getPluggedInConnectionMethod(methodName); - if (newMethod == null) - return false; - method = newMethod; - return true; - } - - /* - * @see ICVSRepositoryLocation#getPort() - */ - public int getPort() { - return port; - } - - /* - * @see ICVSRepositoryLocation#members(CVSTag, boolean, IProgressMonitor) - */ - public ICVSRemoteResource[] members(CVSTag tag, boolean modules, IProgressMonitor progress) throws CVSException { - try { - if (modules) { - return RemoteModule.getRemoteModules(this, tag, progress); - } else { - RemoteFolder root = new RemoteFolder(null, this, "", tag); //$NON-NLS-1$ - ICVSRemoteResource[] resources = (ICVSRemoteResource[])root.members(progress); - // There is the off chance that there is a file in the root of the repository. - // This is not supported by cvs so we need to make sure there are no files - List folders = new ArrayList(resources.length); - for (int i = 0; i < resources.length; i++) { - ICVSRemoteResource remoteResource = resources[i]; - if (remoteResource.isContainer()) { - folders.add(remoteResource); - } - } - return (ICVSRemoteResource[]) folders.toArray(new ICVSRemoteResource[folders.size()]); - } - } catch(TeamException e) { - throw new CVSException(e.getStatus()); - } - } - - /* - * @see ICVSRepositoryLocation#getRemoteFolder(String, CVSTag) - */ - public ICVSRemoteFolder getRemoteFolder(String remotePath, CVSTag tag) { - return new RemoteFolder(null, this, remotePath, tag); - } - - /* - * @see ICVSRepositoryLocation#getRemoteFile(String, CVSTag) - */ - public ICVSRemoteFile getRemoteFile(String remotePath, CVSTag tag) { - IPath path = new Path(remotePath); - RemoteFolderTree remoteFolder = new RemoteFolderTree(null, this, path.removeLastSegments(1).toString(), tag); - RemoteFile remoteFile = new RemoteFile(remoteFolder, Update.STATE_ADDED_LOCAL, path.lastSegment(), tag); - remoteFolder.setChildren(new ICVSRemoteResource[] { remoteFile }); - return remoteFile; - } - - /* - * @see ICVSRepositoryLocation#getRootDirectory() - */ - public String getRootDirectory() { - return root; - } - - /* - * @see ICVSRepositoryLocation#getTimeout() - * - * For the time being, the timeout value is a system wide value - * associated with the CVSPlugin singleton. - */ - public int getTimeout() { - return CVSProviderPlugin.getPlugin().getTimeout(); - } - - /* - * @see ICVSRepositoryLocation#getUserInfo() - */ - public IUserInfo getUserInfo(boolean makeUsernameMutable) { - return new UserInfo(getUsername(), password, makeUsernameMutable ? true : isUsernameMutable()); - } - - /* - * @see ICVSRepositoryLocation#getUsername() - * @see IUserInfo#getUsername() - */ - public String getUsername() { - // If the username is mutable, get it from the cache if it's there - if (user == null && isUsernameMutable()) { - try { - retrievePassword(); - } catch (CVSException e) { - } - } - return user == null ? "" : user; //$NON-NLS-1$ - } - - /* - * @see IUserInfo#isUsernameMutable() - */ - public boolean isUsernameMutable() { - return !userFixed; - } - - /* - * Open a connection to the repository represented by the receiver. - * If the username or password are not fixed, openConnection will - * use the plugged-in authenticator to prompt for the username and/or - * password if one has not previously been provided or if the previously - * supplied username and password are invalid. - * - * This method is synchronized to ensure that authentication with the - * remote server is serialized. This is needed to avoid the situation where - * multiple failed authentications occur and result in the remote account - * being locked. The CVSProviderPlugin enforces that there is one instance - * of a CVSRepositoryLocation per remote location thus this method is called - * for any connection made to this remote location. - */ - public synchronized Connection openConnection(IProgressMonitor monitor) throws CVSException { - - try { - // Allow two ticks in case of a retry - monitor.beginTask(Policy.bind("CVSRepositoryLocation.openingConnection", getHost()), 2);//$NON-NLS-1$ - - // If we have a username and password, use them to attempt a connection - if ((user != null) && (password != null)) { - return createConnection(password, monitor); - } - - // Get the repository in order to ensure that the location is known by CVS. - // (The get will record the location if it's not already recorded. - CVSProviderPlugin.getPlugin().getRepository(getLocation()); - - while (true) { - try { - // The following will throw an exception if authentication fails - String password = retrievePassword(); - if (user == null) { - // This is possible if the cache was cleared somehow for a location with a mutable username - throw new CVSAuthenticationException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.usernameRequired"))); //$NON-NLS-1$ - } - if (password == null) - password = "";//$NON-NLS-1$ - return createConnection(password, monitor); - } catch (CVSAuthenticationException ex) { - String message = ex.getMessage(); - try { - IUserAuthenticator authenticator = getAuthenticator(); - if (authenticator == null) { - throw new CVSAuthenticationException(getLocation(), Policy.bind("Client.noAuthenticator"));//$NON-NLS-1$ - } - authenticator.promptForUserInfo(this, this, message); - updateCache(); - } catch (OperationCanceledException e) { - throw new CVSAuthenticationException(new CVSStatus(CVSStatus.ERROR, message)); - } - } - } - } finally { - monitor.done(); - } - } - - /* - * Implementation of inherited toString() - */ - public String toString() { - return getLocation(); - } - - public boolean equals(Object o) { - if (!(o instanceof CVSRepositoryLocation)) return false; - return getLocation().equals(((CVSRepositoryLocation)o).getLocation()); - } - public int hashCode() { - return getLocation().hashCode(); - } - - /* - * Return the cached password from the keyring. - * Also, set the username of the receiver if the username is mutable - */ - private String retrievePassword() throws CVSException { - Map map = Platform.getAuthorizationInfo(FAKE_URL, getLocation(), AUTH_SCHEME); - if (map != null) { - String username = (String) map.get(INFO_USERNAME); - if (username != null && isUsernameMutable()) - setUsername(username); - String password = (String) map.get(INFO_PASSWORD); - if (password != null) { - return password; - } - } - return null; - } - /* - * @see IUserInfo#setPassword(String) - */ - public void setPassword(String password) { - if (passwordFixed) - throw new UnsupportedOperationException(); - // We set the password here but it will be cleared - // if the user info is cached using updateCache() - this.password = password; - } - - public void setUserInfo(IUserInfo userinfo) { - user = userinfo.getUsername(); - password = ((UserInfo)userinfo).getPassword(); - } - /* - * @see IUserInfo#setUsername(String) - */ - public void setUsername(String user) { - if (userFixed) - throw new UnsupportedOperationException(); - this.user = user; - } - - public void setUserMuteable(boolean muteable) { - userFixed = !muteable; - } - - public void updateCache() throws CVSException { - if (passwordFixed) - return; - updateCache(user, password, true); - password = null; - // Ensure that the receiver is known by the CVS provider - CVSProviderPlugin.getPlugin().getRepository(getLocation()); - } - - /* - * Cache the user info in the keyring - */ - private void updateCache(String username, String password, boolean createIfAbsent) throws CVSException { - // put the password into the Platform map - Map map = Platform.getAuthorizationInfo(FAKE_URL, getLocation(), AUTH_SCHEME); - if (map == null) { - if ( ! createIfAbsent) return; - map = new java.util.HashMap(10); - } - if (username != null) - map.put(INFO_USERNAME, username); - if (password != null) - map.put(INFO_PASSWORD, password); - try { - Platform.addAuthorizationInfo(FAKE_URL, getLocation(), AUTH_SCHEME, map); - } catch (CoreException e) { - // We should probably wrap the CoreException here! - CVSProviderPlugin.log(e); - throw new CVSException(IStatus.ERROR, IStatus.ERROR, Policy.bind("CVSRepositoryLocation.errorCaching", getLocation()), e);//$NON-NLS-1$ - } - } - - /* - * Validate that the receiver contains valid information for - * making a connection. If the receiver contains valid - * information, the method returns. Otherwise, an exception - * indicating the problem is throw. - */ - public void validateConnection(IProgressMonitor monitor) throws CVSException { - try { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - ICVSFolder root = CVSWorkspaceRoot.getCVSFolderFor(ResourcesPlugin.getWorkspace().getRoot()); - Session session = new Session(this, root, false /* output to console */); - session.open(Policy.subMonitorFor(monitor, 50)); - try { - IStatus status = Command.VERSION.execute(session, this, Policy.subMonitorFor(monitor, 50)); - // Log any non-ok status - if (! status.isOK()) { - CVSProviderPlugin.log(status); - } - } finally { - session.close(); - monitor.done(); - } - if (getServerPlatform() == CVSNT_SERVER) { - // check for the use of a repository prefix - if (getRootDirectory().startsWith(Session.SERVER_SEPARATOR)) { - // A prefix is in use. Log a warning - CVSProviderPlugin.log(IStatus.WARNING, Policy.bind("CVSRepositoryLocation.cvsntPrefix", getLocation()), null); //$NON-NLS-1$ - throw new CVSAuthenticationException(new Status(IStatus.WARNING, CVSProviderPlugin.ID, 0, - Policy.bind("CVSRepositoryLocation.cvsntPrefix", getLocation()), null)); //$NON-NLS-1$ - } - } - } catch (CVSException e) { - // If the validation failed, dispose of any cached info - dispose(); - throw e; - } - } - - /** - * Return the server platform type. It will be one of the following: - * UNDETERMINED_PLATFORM: The platform has not been determined - * CVS_SERVER: The platform is regular CVS server - * CVSNT_SERVER: The platform in CVSNT - * If UNDETERMINED_PLATFORM is returned, the platform can be determined - * using the Command.VERSION command. - */ - public int getServerPlatform() { - return serverPlatform; - } - - /** - * This method is called from Command.VERSION to set the platform type. - */ - public void setServerPlaform(IStatus status) { - // OK means that its a regular cvs server - if (status.isOK()) { - serverPlatform = CVS_SERVER; - return; - } - // Find the status that reports the CVS platform - if (status.isMultiStatus()) { - IStatus[] children = status.getChildren(); - for (int i = 0; i < children.length; i++) { - IStatus iStatus = children[i]; - if (iStatus.getCode() == CVSStatus.SERVER_IS_CVSNT - || iStatus.getCode() == CVSStatus.UNSUPPORTED_SERVER_VERSION - || iStatus.getCode() == CVSStatus.SERVER_IS_UNKNOWN) { - status = iStatus; - break; - } - } - } - // Second, check the code of the status itself to see if it is NT - switch (status.getCode()) { - case CVSStatus.SERVER_IS_CVSNT: - serverPlatform = CVSNT_SERVER; - break; - case CVSStatus.UNSUPPORTED_SERVER_VERSION: - serverPlatform = UNSUPPORTED_SERVER; - break; - case CVSStatus.SERVER_IS_UNKNOWN: - serverPlatform = UNKNOWN_SERVER; - break; - default: - // We had an error status with no info about the server. - // Mark it as undetermined. - serverPlatform = UNDETERMINED_PLATFORM; - } - } - - public static boolean validateConnectionMethod(String methodName) { - IConnectionMethod[] methods = getPluggedInConnectionMethods(); - for (int i=0;i<methods.length;i++) { - if (methodName.equals(methods[i].getName())) - return true; - } - return false; - } - - /* - * Create a repository location instance from the given properties. - * The supported properties are: - * - * connection The connection method to be used - * user The username for the connection (optional) - * password The password used for the connection (optional) - * host The host where the repository resides - * port The port to connect to (optional) - * root The server directory where the repository is located - */ - public static CVSRepositoryLocation fromProperties(Properties configuration) throws CVSException { - // We build a string to allow validation of the components that are provided to us - String connection = configuration.getProperty("connection");//$NON-NLS-1$ - if (connection == null) - connection = "pserver";//$NON-NLS-1$ - IConnectionMethod method = getPluggedInConnectionMethod(connection); - if (method == null) - throw new CVSException(new Status(IStatus.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSRepositoryLocation.methods", new Object[] {getPluggedInConnectionMethodNames()}), null));//$NON-NLS-1$ - String user = configuration.getProperty("user");//$NON-NLS-1$ - if (user.length() == 0) - user = null; - String password = configuration.getProperty("password");//$NON-NLS-1$ - if (user == null) - password = null; - String host = configuration.getProperty("host");//$NON-NLS-1$ - if (host == null) - throw new CVSException(new Status(IStatus.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSRepositoryLocation.hostRequired"), null));//$NON-NLS-1$ - String portString = configuration.getProperty("port");//$NON-NLS-1$ - int port; - if (portString == null) - port = ICVSRepositoryLocation.USE_DEFAULT_PORT; - else - port = Integer.parseInt(portString); - String root = configuration.getProperty("root");//$NON-NLS-1$ - if (root == null) - throw new CVSException(new Status(IStatus.ERROR, CVSProviderPlugin.ID, TeamException.UNABLE, Policy.bind("CVSRepositoryLocation.rootRequired"), null));//$NON-NLS-1$ - root = root.replace('\\', '/'); - - return new CVSRepositoryLocation(method, user, password, host, port, root, user != null, false); - } - - /* - * Parse a location string and return a CVSRepositoryLocation. - * - * On failure, the status of the exception will be a MultiStatus - * that includes the original parsing error and a general status - * displaying the passed location and proper form. This form is - * better for logging, etc. - */ - public static CVSRepositoryLocation fromString(String location) throws CVSException { - try { - return fromString(location, false); - } catch (CVSException e) { - // Parsing failed. Include a status that - // shows the passed location and the proper form - MultiStatus error = new MultiStatus(CVSProviderPlugin.ID, CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.invalidFormat", new Object[] {location}), null);//$NON-NLS-1$ - error.merge(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.locationForm")));//$NON-NLS-1$ - error.merge(e.getStatus()); - throw new CVSException(error); - } - } - - /* - * Parse a location string and return a CVSRepositoryLocation. - * - * The valid format (from the cederqvist) is: - * - * :method:[[user][:password]@]hostname[:[port]]/path/to/repository - * - * However, this does not work with CVS on NT so we use the format - * - * :method:[user[:password]@]hostname[#port]:/path/to/repository - * - * Some differences to note: - * The : after the host/port is not optional because of NT naming including device - * e.g. :pserver:username:password@hostname#port:D:\cvsroot - * - * If validateOnly is true, this method will always throw an exception. - * The status of the exception indicates success or failure. The status - * of the exception contains a specific message suitable for displaying - * to a user who has knowledge of the provided location string. - * @see CVSRepositoryLocation.fromString(String) - */ - public static CVSRepositoryLocation fromString(String location, boolean validateOnly) throws CVSException { - String partId = null; - try { - // Get the connection method - partId = "CVSRepositoryLocation.parsingMethod";//$NON-NLS-1$ - int start = location.indexOf(COLON); - String methodName; - int end; - if (start == 0) { - end = location.indexOf(COLON, start + 1); - methodName = location.substring(start + 1, end); - start = end + 1; - } else { - // this could be an alternate format for ext: username:password@host:path - methodName = "ext"; //$NON-NLS-1$ - start = 0; - } - - IConnectionMethod method = getPluggedInConnectionMethod(methodName); - if (method == null) - throw new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.methods", new Object[] {getPluggedInConnectionMethodNames()})));//$NON-NLS-1$ - - // Get the user name and password (if provided) - partId = "CVSRepositoryLocation.parsingUser";//$NON-NLS-1$ - - end = location.indexOf(HOST_SEPARATOR, start); - String user = null;; - String password = null; - // if end is -1 then there is no host separator meaning that the username is not present - if (end != -1) { - // Get the optional user and password - user = location.substring(start, end); - // Separate the user and password (if there is a password) - start = user.indexOf(COLON); - if (start != -1) { - partId = "CVSRepositoryLocation.parsingPassword";//$NON-NLS-1$ - password = user.substring(start+1); - user = user.substring(0, start); - } - // Set start to point after the host separator - start = end + 1; - } - - // Get the host (and port) - partId = "CVSRepositoryLocation.parsingHost";//$NON-NLS-1$ - end= location.indexOf(COLON, start); - String host = location.substring(start, end); - int port = USE_DEFAULT_PORT; - // Separate the port and host if there is a port - start = host.indexOf(PORT_SEPARATOR); - if (start != -1) { - // Initially, we used a # between the host and port - partId = "CVSRepositoryLocation.parsingPort";//$NON-NLS-1$ - port = Integer.parseInt(host.substring(start+1)); - host = host.substring(0, start); - } else { - // In the correct CVS format, the port follows the COLON - partId = "CVSRepositoryLocation.parsingPort";//$NON-NLS-1$ - int index = end; - char c = location.charAt(++index); - String portString = new String(); - while (Character.isDigit(c)) { - portString += c; - c = location.charAt(++index); - } - if (portString.length() > 0) { - end = index - 1; - port = Integer.parseInt(portString); - } - } - - // Get the repository path (translating backslashes to slashes) - partId = "CVSRepositoryLocation.parsingRoot";//$NON-NLS-1$ - start = end + 1; - String root = location.substring(start).replace('\\', '/'); - - if (validateOnly) - throw new CVSException(new CVSStatus(CVSStatus.OK, Policy.bind("ok")));//$NON-NLS-1$ - - return new CVSRepositoryLocation(method, user, password, host, port, root, (user != null), (password != null)); - } - catch (IndexOutOfBoundsException e) { - // We'll get here if anything funny happened while extracting substrings - throw new CVSException(Policy.bind(partId)); - } - catch (NumberFormatException e) { - // We'll get here if we couldn't parse a number - throw new CVSException(Policy.bind(partId)); - } - } - - public static IUserAuthenticator getAuthenticator() { - if (authenticator == null) { - authenticator = getPluggedInAuthenticator(); - } - return authenticator; - } - - /* - * Return the connection method registered for the given name or null if none - * are registered - */ - private static IConnectionMethod getPluggedInConnectionMethod(String methodName) { - IConnectionMethod[] methods = getPluggedInConnectionMethods(); - for(int i=0; i<methods.length; i++) { - if(methodName.equals(methods[i].getName())) - return methods[i]; - } - return null; - } - - /* - * Return a string containing a list of all connection methods - */ - private static String getPluggedInConnectionMethodNames() { - IConnectionMethod[] methods = getPluggedInConnectionMethods(); - StringBuffer methodNames = new StringBuffer(); - for(int i=0; i<methods.length; i++) { - String name = methods[i].getName(); - if (i>0) - methodNames.append(", ");//$NON-NLS-1$ - methodNames.append(name); - } - return methodNames.toString(); - } - - public static IConnectionMethod[] getPluggedInConnectionMethods() { - if(pluggedInConnectionMethods==null) { - List connectionMethods = new ArrayList(); - - if (STANDALONE_MODE) { - connectionMethods.add(new PServerConnectionMethod()); - } else { - IExtension[] extensions = Platform.getPluginRegistry().getExtensionPoint(CVSProviderPlugin.ID, CVSProviderPlugin.PT_CONNECTIONMETHODS).getExtensions(); - for(int i=0; i<extensions.length; i++) { - IExtension extension = extensions[i]; - IConfigurationElement[] configs = extension.getConfigurationElements(); - if (configs.length == 0) { - CVSProviderPlugin.log(IStatus.ERROR, Policy.bind("CVSProviderPlugin.execProblem"), null);//$NON-NLS-1$ - continue; - } - try { - IConfigurationElement config = configs[0]; - connectionMethods.add(config.createExecutableExtension("run"));//$NON-NLS-1$ - } catch (CoreException ex) { - CVSProviderPlugin.log(IStatus.ERROR, Policy.bind("CVSProviderPlugin.execProblem"), ex);//$NON-NLS-1$ - } - } - } - pluggedInConnectionMethods = (IConnectionMethod[])connectionMethods.toArray(new IConnectionMethod[0]); - } - return pluggedInConnectionMethods; - } - - private static IUserAuthenticator getPluggedInAuthenticator() { - IExtension[] extensions = Platform.getPluginRegistry().getExtensionPoint(CVSProviderPlugin.ID, CVSProviderPlugin.PT_AUTHENTICATOR).getExtensions(); - if (extensions.length == 0) - return null; - IExtension extension = extensions[0]; - IConfigurationElement[] configs = extension.getConfigurationElements(); - if (configs.length == 0) { - CVSProviderPlugin.log(IStatus.ERROR, Policy.bind("CVSAdapter.noConfigurationElement", new Object[] {extension.getUniqueIdentifier()}), null);//$NON-NLS-1$ - return null; - } - try { - IConfigurationElement config = configs[0]; - return (IUserAuthenticator) config.createExecutableExtension("run");//$NON-NLS-1$ - } catch (CoreException ex) { - CVSProviderPlugin.log(IStatus.ERROR, Policy.bind("CVSAdapter.unableToInstantiate", new Object[] {extension.getUniqueIdentifier()}), ex);//$NON-NLS-1$ - return null; - } - } - - /* - * Validate that the given string could ne used to succesfully create - * an instance of the receiver. - * - * This method performs some initial checks to provide displayable - * feedback and also tries a more in-depth parse using fromString(String, boolean). - */ - public static IStatus validate(String location) { - - // Check some simple things that are not checked in creation - if (location == null) - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.nullLocation"));//$NON-NLS-1$ - if (location.equals(""))//$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.emptyLocation"));//$NON-NLS-1$ - if (location.endsWith(" ") || location.endsWith("\t"))//$NON-NLS-1$ //$NON-NLS-2$ - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.endWhitespace"));//$NON-NLS-1$ - if (!location.startsWith(":") || location.indexOf(COLON, 1) == -1)//$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSRepositoryLocation.startOfLocation"));//$NON-NLS-1$ - - // Do some quick checks to provide geberal feedback - String formatError = Policy.bind("CVSRepositoryLocation.locationForm");//$NON-NLS-1$ - int secondColon = location.indexOf(COLON, 1); - int at = location.indexOf(HOST_SEPARATOR); - if (at != -1) { - String user = location.substring(secondColon + 1, at); - if (user.equals(""))//$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, formatError); - } else - at = secondColon; - int colon = location.indexOf(COLON, at + 1); - if (colon == -1) - return new CVSStatus(CVSStatus.ERROR, formatError); - String host = location.substring(at + 1, colon); - if (host.equals(""))//$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, formatError); - String path = location.substring(colon + 1, location.length()); - if (path.equals(""))//$NON-NLS-1$ - return new CVSStatus(CVSStatus.ERROR, formatError); - - // Do a full parse and see if it passes - try { - fromString(location, true); - } catch (CVSException e) { - // An exception is always throw. Return the status - return e.getStatus(); - } - - // Looks ok (we'll actually never get here because above - // fromString(String, boolean) will always throw an exception). - return new CVSStatus(IStatus.OK, Policy.bind("ok"));//$NON-NLS-1$ - } - /** - * @see ICVSRepositoryLocation#flushUserInfo() - */ - public void flushUserInfo() throws CVSException { - flushCache(); - } - - /* - * Return the command string that is to be used by the EXT connection method. - */ - String[] getExtCommand(String password) throws IOException { - // Get the user specified connection parameters - String CVS_RSH = CVSProviderPlugin.getPlugin().getCvsRshCommand(); - String CVS_RSH_PARAMETERS = CVSProviderPlugin.getPlugin().getCvsRshParameters(); - String CVS_SERVER = CVSProviderPlugin.getPlugin().getCvsServer(); - if(CVS_RSH == null || CVS_SERVER == null) { - throw new IOException(Policy.bind("EXTServerConnection.varsNotSet")); //$NON-NLS-1$ - } - - // If there is only one token, assume it is the command and use the default parameters and order - if (CVS_RSH_PARAMETERS == null || CVS_RSH_PARAMETERS.length() == 0) { - if (port != USE_DEFAULT_PORT) - throw new IOException(Policy.bind("EXTServerConnection.invalidPort")); //$NON-NLS-1$ - return new String[] {CVS_RSH, host, "-l", user, CVS_SERVER, INVOKE_SVR_CMD}; //$NON-NLS-1$ - } - - // Substitute any variables for their appropriate values - CVS_RSH_PARAMETERS = stringReplace(CVS_RSH_PARAMETERS, USER_VARIABLE, user); - CVS_RSH_PARAMETERS = stringReplace(CVS_RSH_PARAMETERS, PASSWORD_VARIABLE, password); - CVS_RSH_PARAMETERS = stringReplace(CVS_RSH_PARAMETERS, HOST_VARIABLE, host); - CVS_RSH_PARAMETERS = stringReplace(CVS_RSH_PARAMETERS, PORT_VARIABLE, new Integer(port).toString()); - - // Build the command list to be sent to the OS. - List commands = new ArrayList(); - commands.add(CVS_RSH); - StringTokenizer tokenizer = new StringTokenizer(CVS_RSH_PARAMETERS); - while (tokenizer.hasMoreTokens()) { - String next = tokenizer.nextToken(); - commands.add(next); - } - commands.add(CVS_SERVER); - commands.add(INVOKE_SVR_CMD); - return (String[]) commands.toArray(new String[commands.size()]); - } - - /* - * Replace all occurances of oldString with newString - */ - private String stringReplace(String string, String oldString, String newString) { - int index = string.toLowerCase().indexOf(oldString); - if (index == -1) return string; - return stringReplace( - string.substring(0, index) + newString + string.substring(index + oldString.length()), - oldString, newString); - } - - /** - * Return the name of the cvs program on the remote server. - * The default is "cvs" but it can be tailored for some servers - * @return String - */ - public String getRemoteCVSProgramName() { - return remoteCVSProgramName; - } - - /** - * Sets the remoteCVSProgramName. - * @param remoteCVSProgramName The remoteCVSProgramName to set - */ - public void setRemoteCVSProgramName(String remoteCVSProgramName) { - this.remoteCVSProgramName = remoteCVSProgramName; - } - - /** - * Return the server message with the prefix removed. - * Server aborted messages typically start with - * "cvs server: ..." - * "cvs [server aborted]: ..." - * "cvs rtag: ..." - */ - public String getServerMessageWithoutPrefix(String errorLine, String prefix) { - String message = errorLine; - String programName = getRemoteCVSProgramName(); - if (message.startsWith(programName)) { - // remove the program name and the space - message = message.substring(programName.length() + 1); - if (message.startsWith(prefix)) { - message = message.substring(prefix.length()); - if (message.charAt(0) == ' ') { - message = message.substring(1); - } - return message; - } - } - // This is not a server message with the desired prefix - return null; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSServerException.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSServerException.java deleted file mode 100644 index 99bf0b6dc..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/CVSServerException.java +++ /dev/null @@ -1,77 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.MultiStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; - -/** - * Client has received an error response from the server. - */ -public class CVSServerException extends CVSException { - - /** - * Return true if the exception from the cvs server is the no tag error, and false - * otherwise. - */ - public boolean isNoTagException() { - IStatus status = getStatus(); - if ( ! status.isMultiStatus()) - return false; - IStatus[] children = ((MultiStatus)status).getChildren(); - for (int i = 0; i < children.length; i++) { - if (children[i].getCode() == CVSStatus.NO_SUCH_TAG) { - return true; - } - } - return false; - } - - /** - * Return true if the exceptions status contains any error status messages - */ - public boolean containsErrors() { - IStatus status = getStatus(); - if ( ! status.isMultiStatus()) - return status.getSeverity() == IStatus.ERROR; - IStatus[] children = ((MultiStatus)status).getChildren(); - for (int i=0;i<children.length;i++) { - if (children[i].getSeverity() == IStatus.ERROR) - return true; - } - return false; - } - - /** - * Return the CVSServerException for the given error message and error list - * - * This is public due to packaging and should not be used by clients. - */ - public static CVSServerException forError(String message, IStatus[] children) { - if (children.length > 0) { - return new CVSServerException(message, children); - } else { - return new CVSServerException(new CVSStatus(IStatus.ERROR, CVSStatus.SERVER_ERROR, message, null)); - } - } - - public CVSServerException(IStatus status) { - super(status); - } - - private CVSServerException(String message, IStatus[] children) { - super(new MultiStatus(CVSProviderPlugin.ID, CVSStatus.SERVER_ERROR, children, message, null)); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/Connection.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/Connection.java deleted file mode 100644 index e99e4f12e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/Connection.java +++ /dev/null @@ -1,231 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.IServerConnection; -import org.eclipse.team.internal.ccvs.core.Policy; - -/** - * A connection to talk to a cvs server. The life cycle of a connection is - * as follows: - * <ul> - * <li> constructor: creates a new connection object that wraps the given - * repository location and connection method. - * <li> open: opens a connection. - * <li> send a request: use write* method or use the request stream directly. - * <code>GetRequestStream</code> returns an output stream to directly - * talk to the server. - * <li> read responses: use read* methods or use the response stream directly. - * <code>GetResponseStream</code> returns an input stream to directly - * read output from the server. - * <li> close: closes the connection. A closed connection can be reopened by - * calling open again. - * </ul> - */ -public class Connection { - private static final byte NEWLINE= 0xA; - - private IServerConnection serverConnection; - private ICVSRepositoryLocation fCVSRoot; - private String fCVSRootDirectory; - private boolean fIsEstablished; - private InputStream fResponseStream; - private byte[] readLineBuffer = new byte[256]; - - public Connection(ICVSRepositoryLocation cvsroot, IServerConnection serverConnection) { - fCVSRoot = cvsroot; - this.serverConnection = serverConnection; - } - - private static byte[] append(byte[] buffer, int index, byte b) { - if (index >= buffer.length) { - byte[] newBuffer= new byte[index * 2]; - System.arraycopy(buffer, 0, newBuffer, 0, buffer.length); - buffer= newBuffer; - } - buffer[index]= b; - return buffer; - } - /** - * Closes the connection. - */ - public void close() throws CVSException { - if (!isEstablished()) - return; - try { - serverConnection.close(); - } catch (IOException ex) { - // Generally, errors on close are of no interest. - // However, log them if debugging is on - if (CVSProviderPlugin.getPlugin().isDebugging()) { - CVSProviderPlugin.log(new CVSCommunicationException(Policy.bind("Connection.cannotClose"), ex));//$NON-NLS-1$ - } - } finally { - fResponseStream = null; - fIsEstablished = false; - } - } - /** - * Flushes the request stream. - */ - public void flush() throws CVSException { - if (!isEstablished()) - return; - try { - getOutputStream().flush(); - } catch(IOException e) { - throw new CVSCommunicationException(e); - } - } - - /** - * Returns the <code>OutputStream</code> used to send requests - * to the server. - */ - public OutputStream getOutputStream() throws CVSException { - if (!isEstablished()) - return null; - return serverConnection.getOutputStream(); - } - /** - * Returns the <code>InputStream</code> used to read responses from - * the server. - */ - public InputStream getInputStream() throws CVSException { - if (!isEstablished()) - return null; - if (fResponseStream == null) - fResponseStream = serverConnection.getInputStream(); - return fResponseStream; - } - - /** - * Returns <code>true</code> if the connection is established; - * otherwise <code>false</code>. - */ - public boolean isEstablished() { - return fIsEstablished; - } - - /** - * Opens the connection. - */ - public void open(IProgressMonitor monitor) throws CVSException { - if (isEstablished()) - return; - try { - serverConnection.open(monitor); - } catch (IOException e) { - throw new CVSCommunicationException(e); - } - fIsEstablished= true; - } - /** - * Reads a line from the response stream. - */ - public String readLine() throws CVSException { - if (!isEstablished()) - throw new CVSCommunicationException(Policy.bind("Connection.readUnestablishedConnection"));//$NON-NLS-1$ - try { - InputStream in = getInputStream(); - int index = 0; - int r; - while ((r = in.read()) != -1) { - if (r == NEWLINE) break; - readLineBuffer = append(readLineBuffer, index++, (byte) r); - } - String result = new String(readLineBuffer, 0, index); - if (Policy.DEBUG_CVS_PROTOCOL) System.out.println(result); - return result; - } catch (IOException e) { - throw new CVSCommunicationException(e); - } - } - - static String readLine(InputStream in) throws IOException { - byte[] buffer = new byte[256]; - int index = 0; - int r; - while ((r = in.read()) != -1) { - if (r == NEWLINE) - break; - buffer = append(buffer, index++, (byte) r); - } - String result = new String(buffer, 0, index); - if (Policy.DEBUG_CVS_PROTOCOL) - System.out.println(result); - return result; - } - - //---- Helper to send strings to the server ---------------------------- - - /** - * Sends the given string to the server. - */ - public void write(String s) throws CVSException { - write(s.getBytes(), false); - } - - /** - * Sends the given bytes to the server. - */ - public void write(byte[] b, int off, int len) throws CVSException { - write(b, off, len, false); - } - /** - * Sends the given string and a newline to the server. - */ - public void writeLine(String s) throws CVSException { - write(s.getBytes(), true); - } - /** - * Sends the given bytes and a newline to the server. - */ - public void writeLine(byte[] b, int off, int len) throws CVSException { - write(b, off, len, true); - } - - void write (byte[] bytes, boolean newLine) throws CVSException { - write(bytes, 0, bytes.length, newLine); - } - - /** - * Low level method to write a string to the server. All write* methods are - * funneled through this method. - */ - void write(byte[] b, int off, int len, boolean newline) throws CVSException { - if (!isEstablished()) - throw new CVSCommunicationException(Policy.bind("Connection.writeUnestablishedConnection"));//$NON-NLS-1$ - - if (Policy.DEBUG_CVS_PROTOCOL) - System.out.print(new String(b, off, len) + (newline ? "\n" : ""));//$NON-NLS-1$ //$NON-NLS-2$ - - try { - OutputStream out= getOutputStream(); - out.write(b, off, len); - if (newline) - out.write(NEWLINE); - out.flush(); - - } catch (IOException e) { - throw new CVSCommunicationException(e); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/ExtConnection.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/ExtConnection.java deleted file mode 100644 index b45b8da64..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/ExtConnection.java +++ /dev/null @@ -1,136 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.IServerConnection; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.core.streams.PollingInputStream; -import org.eclipse.team.internal.core.streams.PollingOutputStream; -import org.eclipse.team.internal.core.streams.TimeoutInputStream; -import org.eclipse.team.internal.core.streams.TimeoutOutputStream; - -/** - * Implements a connection method which invokes an external tool to - * establish the connection to the cvs server. Authentication and starting - * of the cvs server are the responsibility of the external connection - * tool. - */ -public class ExtConnection implements IServerConnection { - - // The default port for rsh - private static final int DEFAULT_PORT = 9999; - - // cvs format for the repository (e.g. :extssh:user@host:/home/cvs/repo) - private ICVSRepositoryLocation location; - private String password; - - // incoming from remote host - InputStream inputStream; - - // outgoing to remote host - OutputStream outputStream; - - // Process spawn to run the command - Process process; - - protected ExtConnection(ICVSRepositoryLocation location, String password) { - this.location = location; - this.password = password; - } - - /** - * Closes the connection. - */ - public void close() throws IOException { - try { - if (inputStream != null) inputStream.close(); - } finally { - inputStream = null; - try { - if (outputStream != null) outputStream.close(); - } finally { - outputStream = null; - process.destroy(); - } - } - } - - /** - * Returns the <code>InputStream</code> used to read data from the - * server. - */ - public InputStream getInputStream() { - return inputStream; - } - - /** - * Returns the <code>OutputStream</code> used to send data to the - * server. - */ - public OutputStream getOutputStream() { - return outputStream; - } - - /** - * Opens the connection and invokes cvs in server mode. - * - * @see Connection.open() - */ - public void open(IProgressMonitor monitor) throws IOException { - String[] command = ((CVSRepositoryLocation)location).getExtCommand(password); - boolean connected = false; - try { - process = Runtime.getRuntime().exec(command); - - inputStream = new PollingInputStream(new TimeoutInputStream(process.getInputStream(), - 8192 /*bufferSize*/, 1000 /*readTimeout*/, -1 /*closeTimeout*/), location.getTimeout(), monitor); - outputStream = new PollingOutputStream(new TimeoutOutputStream(process.getOutputStream(), - 8192 /*buffersize*/, 1000 /*writeTimeout*/, 1000 /*closeTimeout*/), location.getTimeout(), monitor); - - // XXX need to do something more useful with stderr - // discard the input to prevent the process from hanging due to a full pipe - Thread thread = new DiscardInputThread(process.getErrorStream()); - connected = true; - } finally { - if (! connected) { - try { - close(); - } finally { - throw new IOException(Policy.bind("EXTServerConnection.ioError", command[0])); //$NON-NLS-1$ - } - } - } - } - - private static class DiscardInputThread extends Thread { - private InputStream in; - public DiscardInputThread(InputStream in) { - this.in = in; - } - public void run() { - try { - try { - while (in.read() != -1); - } finally { - in.close(); - } - } catch (IOException e) { - } - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/ExtConnectionMethod.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/ExtConnectionMethod.java deleted file mode 100644 index 94c5f0de9..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/ExtConnectionMethod.java +++ /dev/null @@ -1,33 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import org.eclipse.team.internal.ccvs.core.*; - -public class ExtConnectionMethod implements IConnectionMethod { - /** - * @see IConnectionMethod#getName - */ - public String getName() { - return "ext"; //$NON-NLS-1$ - } - - /** - * @see IConnectionMethod#createConnection - */ - public IServerConnection createConnection(ICVSRepositoryLocation repositoryRoot, String password) { - return new ExtConnection(repositoryRoot, password); - } - - public void disconnect(ICVSRepositoryLocation location) { - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/PServerConnection.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/PServerConnection.java deleted file mode 100644 index 4ebf779f9..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/PServerConnection.java +++ /dev/null @@ -1,252 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import java.io.BufferedInputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.InterruptedIOException; -import java.io.OutputStream; -import java.net.Socket; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.IServerConnection; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.util.Util; -import org.eclipse.team.internal.core.streams.PollingInputStream; -import org.eclipse.team.internal.core.streams.PollingOutputStream; -import org.eclipse.team.internal.core.streams.TimeoutOutputStream; - -/** - * A connection used to talk to an cvs pserver. - */ -public class PServerConnection implements IServerConnection { - - public static final char NEWLINE= 0xA; - - /** default CVS pserver port */ - private static final int DEFAULT_PORT= 2401; - - /** error line indicators */ - private static final char ERROR_CHAR = 'E'; - private static final String ERROR_MESSAGE = "error 0";//$NON-NLS-1$ - private static final String NO_SUCH_USER = "no such user";//$NON-NLS-1$ - - private static final char[] SCRAMBLING_TABLE=new char[] { - 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15, - 16,17,18,19,20,21,22,23,24,25,26,27,28,29,30,31, - 114,120,53,79,96,109,72,108,70,64,76,67,116,74,68,87, - 111,52,75,119,49,34,82,81,95,65,112,86,118,110,122,105, - 41,57,83,43,46,102,40,89,38,103,45,50,42,123,91,35, - 125,55,54,66,124,126,59,47,92,71,115,78,88,107,106,56, - 36,121,117,104,101,100,69,73,99,63,94,93,39,37,61,48, - 58,113,32,90,44,98,60,51,33,97,62,77,84,80,85,223, - 225,216,187,166,229,189,222,188,141,249,148,200,184,136,248,190, - 199,170,181,204,138,232,218,183,255,234,220,247,213,203,226,193, - 174,172,228,252,217,201,131,230,197,211,145,238,161,179,160,212, - 207,221,254,173,202,146,224,151,140,196,205,130,135,133,143,246, - 192,159,244,239,185,168,215,144,139,165,180,157,147,186,214,176, - 227,231,219,169,175,156,206,198,129,164,150,210,154,177,134,127, - 182,128,158,208,162,132,167,209,149,241,153,251,237,236,171,195, - 243,233,253,240,194,250,191,155,142,137,245,235,163,242,178,152 - }; - - /** Communication strings */ - private static final String BEGIN= "BEGIN AUTH REQUEST";//$NON-NLS-1$ - private static final String END= "END AUTH REQUEST";//$NON-NLS-1$ - private static final String LOGIN_OK= "I LOVE YOU";//$NON-NLS-1$ - private static final String LOGIN_FAILED= "I HATE YOU";//$NON-NLS-1$ - - private String password; - private ICVSRepositoryLocation cvsroot; - - private Socket fSocket; - - private InputStream inputStream; - private OutputStream outputStream; - - /** - * @see Connection#doClose() - */ - public void close() throws IOException { - try { - if (inputStream != null) inputStream.close(); - } finally { - inputStream = null; - try { - if (outputStream != null) outputStream.close(); - } finally { - outputStream = null; - try { - if (fSocket != null) fSocket.close(); - } finally { - fSocket = null; - } - } - } - } - - /** - * @see Connection#doOpen() - */ - public void open(IProgressMonitor monitor) throws IOException, CVSAuthenticationException { - - monitor.subTask(Policy.bind("PServerConnection.authenticating"));//$NON-NLS-1$ - monitor.worked(1); - - fSocket = createSocket(monitor); - boolean connected = false; - try { - this.inputStream = new BufferedInputStream(new PollingInputStream(fSocket.getInputStream(), - cvsroot.getTimeout(), monitor)); - this.outputStream = new PollingOutputStream(new TimeoutOutputStream( - fSocket.getOutputStream(), 8192 /*bufferSize*/, 1000 /*writeTimeout*/, 1000 /*closeTimeout*/), - cvsroot.getTimeout(), monitor); - authenticate(); - connected = true; - } finally { - if (! connected) cleanUpAfterFailedConnection(); - } - } - - /** - * @see Connection#getInputStream() - */ - public InputStream getInputStream() { - return inputStream; - } - /** - * @see Connection#getOutputStream() - */ - public OutputStream getOutputStream() { - return outputStream; - } - - /** - * Creates a new <code>PServerConnection</code> for the given - * cvs root. - */ - PServerConnection(ICVSRepositoryLocation cvsroot, String password) { - this.cvsroot = cvsroot; - this.password = password; - } - /** - * Does the actual authentification. - */ - private void authenticate() throws IOException, CVSAuthenticationException { - String scrambledPassword = scramblePassword(password); - - String user = cvsroot.getUsername(); - OutputStream out = getOutputStream(); - - StringBuffer request = new StringBuffer(); - request.append(BEGIN); - request.append(NEWLINE); - request.append(cvsroot.getRootDirectory()); - request.append(NEWLINE); - request.append(user); - request.append(NEWLINE); - request.append(scrambledPassword); - request.append(NEWLINE); - request.append(END); - request.append(NEWLINE); - out.write(request.toString().getBytes()); - out.flush(); - String line = Connection.readLine(getInputStream()); - - // Return if we succeeded - if (LOGIN_OK.equals(line)) - return; - - // Otherwise, determine the type of error - if (line.length() == 0) - throw new IOException(Policy.bind("PServerConnection.noResponse"));//$NON-NLS-1$ - if (LOGIN_FAILED.equals(line)) - throw new CVSAuthenticationException(cvsroot.getLocation(), Policy.bind("PServerConnection.loginRefused"));//$NON-NLS-1$ - String message = "";//$NON-NLS-1$ - // Skip any E messages for now - while (line.charAt(0) == ERROR_CHAR) { - // message += line.substring(1) + " "; - line = Connection.readLine(getInputStream()); - } - // Remove leading "error 0" - if (line.startsWith(ERROR_MESSAGE)) - message += line.substring(ERROR_MESSAGE.length() + 1); - else - message += line; - if (message.indexOf(NO_SUCH_USER) != -1) - throw new CVSAuthenticationException(cvsroot.getLocation(), Policy.bind("PServerConnection.invalidUser", new Object[] {message}));//$NON-NLS-1$ - throw new IOException(Policy.bind("PServerConnection.connectionRefused", new Object[] { message }));//$NON-NLS-1$ - } - /* - * Called if there are exceptions when connecting. - * This method makes sure that all connections are closed. - */ - private void cleanUpAfterFailedConnection() throws IOException { - try { - if (inputStream != null) - inputStream.close(); - } finally { - try { - if (outputStream != null) - outputStream.close(); - } finally { - try { - if (fSocket != null) - fSocket.close(); - } finally { - fSocket = null; - } - } - } - - } - /** - * Creates the actual socket - */ - protected Socket createSocket(IProgressMonitor monitor) throws IOException { - // Determine what port to use - int port = cvsroot.getPort(); - if (port == ICVSRepositoryLocation.USE_DEFAULT_PORT) - port = DEFAULT_PORT; - // Make the connection - Socket result; - try { - result= Util.createSocket(cvsroot.getHost(), port, monitor); - // Bug 36351: disable buffering and send bytes immediately - result.setTcpNoDelay(true); - } catch (InterruptedIOException e) { - // If we get this exception, chances are the host is not responding - throw new InterruptedIOException(Policy.bind("PServerConnection.socket", new Object[] {cvsroot.getHost()}));//$NON-NLS-1$ - } - result.setSoTimeout(1000); // 1 second between timeouts - return result; - } - - private String scramblePassword(String password) throws CVSAuthenticationException { - int length = password.length(); - char[] out= new char[length]; - for (int i= 0; i < length; i++) { - char value = password.charAt(i); - if( value < 0 || value > 255 ) - throwInValidCharacter(); - out[i]= SCRAMBLING_TABLE[value]; - } - return "A" + new String(out);//$NON-NLS-1$ - } - - private void throwInValidCharacter() throws CVSAuthenticationException { - throw new CVSAuthenticationException(cvsroot.getLocation(), - Policy.bind("PServerConnection.invalidChars"));//$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/PServerConnectionMethod.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/PServerConnectionMethod.java deleted file mode 100644 index 48e152429..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/PServerConnectionMethod.java +++ /dev/null @@ -1,35 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.IConnectionMethod; -import org.eclipse.team.internal.ccvs.core.IServerConnection; -public class PServerConnectionMethod implements IConnectionMethod { - /** - * @see IConnectionMethod#createConnection(ICVSRepositoryLocation, String) - */ - public IServerConnection createConnection(ICVSRepositoryLocation location, String password) { - return new PServerConnection(location, password); - } - /** - * @see IConnectionMethod#getName() - */ - public String getName() { - return "pserver";//$NON-NLS-1$ - } - - /** - * @see org.eclipse.team.internal.ccvs.core.IConnectionMethod#disconnect(org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation) - */ - public void disconnect(ICVSRepositoryLocation location) { - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/UserInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/UserInfo.java deleted file mode 100644 index 110aeedcb..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/connection/UserInfo.java +++ /dev/null @@ -1,64 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.connection; - - -import org.eclipse.team.internal.ccvs.core.IUserInfo; - -/** - * @version 1.0 - * @author - */ -public class UserInfo implements IUserInfo { - - private String username; - private String password; - private boolean isUsernameMutable; - - protected UserInfo(String username, String password, boolean isUsernameMutable) { - this.username = username; - this.password = password; - this.isUsernameMutable = isUsernameMutable; - } - - /* - * @see IUserInfo#getUsername() - */ - public String getUsername() { - return username; - } - - protected String getPassword() { - return password; - } - - /* - * @see IUserInfo#isUsernameMutable() - */ - public boolean isUsernameMutable() { - return false; - } - - /* - * @see IUserInfo#setPassword(String) - */ - public void setPassword(String password) { - this.password = password; - } - - /* - * @see IUserInfo#setUsername(String) - */ - public void setUsername(String username) { - this.username = username; - } - -} 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 deleted file mode 100644 index d14eae708..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/messages.properties +++ /dev/null @@ -1,315 +0,0 @@ -############################################################################### -# Copyright (c) 2000, 2003 IBM Corporation and others. -# All rights reserved. This program and the accompanying materials -# are made available under the terms of the Common Public License v1.0 -# which accompanies this distribution, and is available at -# http://www.eclipse.org/legal/cpl-v10.html -# -# Contributors: -# IBM Corporation - initial API and implementation -############################################################################### -org.eclipse.team.internal.provider.cvs.CVSException=CVS Error: {0} - -ok=ok -null=null -internal=An internal error has occurred. Consult the error log for details. - -AbstractStructureVisitor.sendingFolder=Processing {0} -AbstractStructureVisitor.sendingFile=Processing {0} -AbstractStructureVisitor.noRemote=Unable to determine remote location for resource - -AddDeleteMoveListener.deletedResource={0} has been deleted locally -AddDeleteMoveListener.Error_creating_deletion_marker_1=Error creating deletion marker -AddDeleteMoveListener.Local_addition_not_under_CVS_control_2=Local addition not under CVS control -AddDeleteMoveListener.Error_creating_addition_marker_3=Error creating addition marker -AddDeleteMoveListener.Error_updating_marker_state_4=Error updating marker state - -CVSAuthenticationException.detail=Authentication error: {0} -CVSCommunicationException.io=CVS communication error: {0} -CVSCommunicationException.interruptCause=The most likely cause of the interrupt is either an intermittent network failure or a communications timeout. -CVSCommunicationException.interruptSolution=The CVS communications timeout can be adjusted in the Team/CVS preferences. -CVSCommunicationException.alternateInterruptCause=Another possible cause is the improper configuration of the "ext" connection method. -CVSCommunicationException.alternateInterruptSolution=The "ext" connection method can be configured on the Team/CVS/EXT Connection Method preference page -CVSFileException.io=Error accessing CVS file -CVSDiffException.message=The compared files are different -CVSStatus.messageWithRoot={0}: {1} - -CVSTag.nullName=Name must not be null -CVSTag.emptyName=Name must not be empty -CVSTag.beginName=Name must start with a letter -CVSTag.badCharName=Name must not contain spaces or the characters `$,.:;@|' - -CVSWorkspaceRoot.notCVSFolder=The CVS synchronization information for {0} has become corrupt or does not exist - -java.io.IOException=I/O exception occurred: {0} -java.io.EOFException=End of file encountered: {0} -java.io.FileNotFoundException=File not found: {0} -java.io.InterruptedIOException=I/O has been interrupted. -java.net.UnknownHostException=Cannot locate host -java.net.ConnectException=Cannot connect to host -java.net.SocketException=Socket Exception: {0} - -Connection.cannotClose=Cannot close connection -Connection.readUnestablishedConnection=Failure due to attempt to read from an unestablished connection -Connection.writeUnestablishedConnection=Failure due to attempt to write to an unestablished connection - -PServerConnection.invalidChars=Invalid characters in password -PServerConnection.hostInvalid=Invalid host -PServerConnection.loginRefused=Incorrect user name or password -PServerConnection.invalidUser={0} -PServerConnection.socket=Cannot connect to host: {0} -PServerConnection.connectionRefused=Connection refused: {0} -PServerConnection.stream=Error opening socket connection -PServerConnection.noResponse=No response from server -PServerConnection.authenticating=Authenticating using pserver - -CVSProviderPlugin.cannotUpdateDescription=Error updating project description -CVSProviderPlugin.errorDeletingCache=Error occurred deleting cache: {0} -CVSProviderPlugin.errorCreatingCache=Error occurred creating cache: {0} -CVSProviderPlugin.unknownStateFileVersion=Could not read CVS state file: unknown version '{0}'. - -CVSProvider.exception=Internal error occurred. -CVSProvider.invalidResource=Resource {0} is not a CVS resource -CVSProvider.initialImport=Initial import -CVSProvider.alreadyExists=The specified repository location already exists. -CVSProvider.rename=An I/O Exception occurred while renaming the state file {0} -CVSProvider.save=An I/O Exception occurred while saving the state file {0} -CVSProvider.ioException=I/O Exception occurred on the state file -CVSProvider.errorSaving=Error saving state -CVSProvider.errorLoading=Error loading state -CVSProvider.infoMismatch=Provided CVS information does not match that on disk for project {0} - -CVSTeamProvider.noFolderInfo=Project {0} does not contain CVS folder meta-information -CVSTeamProvider.deconfigureProblem=Error while deconfiguring CVS project {0} -CVSTeamProvider.initializationFailed=Initialization of CVS for project {0} failed -CVSTeamProvider.visitError=An error occurred while visiting resource {0} -CVSTeamProvider.invalidResource=Resource {0} is not a child of project {1} -CVSTeamProvider.checkinProblems=Problems occurred committing resources to server -CVSTeamProvider.invalidProjectState=CVS sharing information is missing from project {0} -CVSTeamProvider.unmanagedParent=Error retrieving remote resource tree for {0}. Parent is not managed by CVS. -CVSTeamProvider.typesDiffer=Error retrieving remote resource tree. Local and remote resource types differ for {0} -CVSTeamProvider.connectionInfo=Updating connection information for project {0} -CVSTeamProvider.folderInfo=Updating folder synchronization information for project {0} -CVSTeamProvider.updatingFolder=Updating {0} -CVSTeamProvider.scrubbingResource=Scrubbing {0} -CVSTeamProvider.updatingFile=Updating {0} -CVSTeamProvider.makeBranch=Creating branch -CVSTeamProvider.preparingToSetKSubst=Preparing to set keyword substitution mode -CVSTeamProvider.settingKSubst=Setting keyword substitution mode -CVSTeamProvider.cleanLineDelimitersException=Exception occurred while cleaning line delimiters -CVSTeamProvider.changingKeywordComment=*** keyword substitution change *** -CVSTeamProvider.errorGettingFetchProperty=Could not get "fetch new directory" property for project ''{0}''. -CVSTeamProvider.errorSettingFetchProperty=Could not set "fetch new directory" property for project ''{0}''. -CVSTeamProvider.overlappingRemoteFolder=Cannot create linked resource ''{0}'' because a folder of the same name exists remotely. -CVSTeamProvider.overlappingFileDeletion=Cannot create linked resource ''{0}'' because a deletion for the file of that name has not been committed. -CVSTeamProvider.errorGettingWatchEdit=Could not get "watch/edit" property for project ''{0}''. -CVSTeamProvider.errorSettingWatchEdit=Could not set "watch/edit" property for project ''{0}''. -CVSTeamProvider.errorAddingFileToDiff=An I/O error occurred adding file ''{0}'' to the patch output. - -ProjectDescriptionManager.unableToSetDescription=An error occurred setting the project description -ProjectDescriptionManager.unableToReadDescription=An error occurred reading the project description -ProjectDescriptionManager.ioDescription=An I/O error occurred while writing the project description -ProjectDescriptionManager.coreDescription=A Core error occurred while writing the project description -ProjectDescriptionManager.vcmmetaIgnored=.vcm_meta file ignored for project {0} -ProjectDescriptionManager.cannotUpdateDesc=Cannot update project description -ProjectDescriptionManager.markerError=Error creating marker for .vcm_meta file. -ProjectDescriptionManager.vcmmetaMarker=The file {0} exists in {1} but is no longer being read; its usage has been replaced with .project. - -ResourceDeltaVisitor.visitError=Error while processing resource deltas - -ResponseDispatcher.serverError=The CVS server responded with an error (see the CVS console) -ResponseDispatcher.problemsReported= Errors occurred during the CVS operation -ResponseDispatcher.receiving=Receiving response - -FileProperties.invalidEntryLine=Invalid entry line: {0} - -EclipseResource.invalidResourceClass=Two different implementations of ICVSResource used - -RemoteResource.invalidResourceClass=Two different implementations of ICVSResource used -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 occurred fetching the members of a remote folder -RemoteFolder.doesNotExist=Folder {0} does not exist remotely - -RemoteFile.noContentsReceived=No contents received from server for {0} -RemoteFile.errorRetrievingFromCache=Error occurred retrieving cached contents: {0} - -RemoteFolderTreeBuilder.buildingBase=Collecting local synchronization information -RemoteFolderTreeBuilder.receivingDelta=Receiving delta for {0} -RemoteFolderTreeBuilder.receivingRevision=Receiving revision for {0} -RemoteFolderTreeBuilder.missingParent=An error has occurred processing file ''{0} {1}'' -RemoteFolderTreeBuild.folderDeletedFromServer=Folder ''{0}'' has been deleted from the server. - -ReplaceWithBaseVisitor.replacing=Replacing ''{0}'' - -Session.badInt="Malformed file transmission received" -Session.receiving=Receiving file: {0} -Session.sending=Sending file: {0} -Session.transfer={0} ({1}K of {2}K bytes) -Session.transferNoSize={0} -Session.calculatingCompressedSize=Calculating compressed size: {0} - -Command.receivingResponses=Receiving server response -Command.warnings=The following warnings were reported while performing the "cvs {0}" command. -Command.serverError=The server reported an error while performing the "cvs {0}" command. -Command.noMoreInfoAvailable=The server did not provide any additional information. -Command.add=add -Command.admin=admin -Command.co=checkout -Command.ci=commit -Command.diff=diff -Command.import=import -Command.log=log -Command.remove=remove -Command.status=status -Command.tag=tag -Command.update=update -Command.version=version -Command.valid-requests=valid-requests -Command.expand-modules=expand-modules -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 -Command.seriousServerError=The server reported an error: {0} - -Commit.syncInfoMissing=The commit operation succeeded. However, committed file ''{0}'' no longer has CVS synchronization information. -Commit.timestampReset=The modification timestamp was changed for ''{0}'' but the contents match that of the server. The timstamp has been reset. - -Diff.serverError=The server reported an error while performing the "cvs diff" command which may only indicate that a difference exists. - -Tag.notVersionOrBranchError=Error applying tag: the tag provided is not a version or branch tag. - -DefaultHandler.connectionClosed=The connection to the server has been closed -ModTimeHandler.invalidFormat=The server modification time {0} is in an unknown format -Updated.numberFormat=Server did not send length of the file -UnsupportedHandler.message=Unsupported response received from server -RemovedHandler.invalid=Invalid removed response received from CVS server for {0} -CheckInHandler.checkedIn= Receiving confirmation for file {0}. - -KSubstOption.-kb.short=Binary -KSubstOption.-kb.long=Binary (-kb) -KSubstOption.-ko.short=ASCII -ko -KSubstOption.-ko.long=ASCII without keyword substitution (-ko) -KSubstOption.-kkv.short=ASCII -kkv -KSubstOption.-kkv.long=ASCII with keyword expansion (-kkv) -KSubstOption.-kkvl.short=ASCII -kkvl -KSubstOption.-kkvl.long=ASCII with keyword expansion and locker (-kkvl) -KSubstOption.-kv.short=ASCII -kv -KSubstOption.-kv.long=ASCII with keyword replacement (-kv) -KSubstOption.-kk.short=ASCII -kk -KSubstOption.-kk.long=ASCII with keyword compression (-kk) -KSubstOption.unknown.short=Unknown {0} -KSubstOption.unknown.long=Unknown ({0}) - -AdminKSubstListener.expectedRCSFile=Expected RCS file {0} to end in ',v' -AdminKSubstListener.commandRootNotManaged=Local root for this command is not managed -AdminKSubstListener.expectedChildOfCommandRoot=Expected RCS file {0} to be a child of remote root for this command {1} -AdminKSubstListener.couldNotSetResourceSyncInfo=Could not set resource sync info for {0}: {1} - -CVSRepositoryLocation.nullLocation=Location must not be null -CVSRepositoryLocation.emptyLocation=Location must not be empty -CVSRepositoryLocation.endWhitespace=Location must not end with whitespace -CVSRepositoryLocation.locationForm=Location must have form ':methodname:[user[:password]@]host:[port]/path/to/cvsroot' -CVSRepositoryLocation.startOfLocation=Location must start with a connection method name enclosed in colons -CVSRepositoryLocation.methods=Only the following methods are supported: {0} -CVSRepositoryLocation.parsingMethod=Error in connection method specification -CVSRepositoryLocation.parsingUser=Error in user name specification -CVSRepositoryLocation.parsingPassword=Error in password specification -CVSRepositoryLocation.parsingHost=Error in host specification -CVSRepositoryLocation.parsingPort=Error in port specification -CVSRepositoryLocation.parsingRoot=Error in repository root directory specification -CVSRepositoryLocation.invalidFormat=Invalid CVS repository location format: {0} -CVSRepositoryLocation.authenticationCanceled=Authentication canceled by user -CVSRepositoryLocation.errorCaching=Error occurred while saving password for {0} -CVSRepositoryLocation.errorFlushing=Error occurred while flushing password for {0} -CVSRepositoryLocation.openingConnection=Opening connection to {0} -CVSRepositoryLocation.usernameRequired=A username is required to make a connection -CVSRepositoryLocation.cvsntPrefix=CVSNT repository ''{0}'' is configured to use a repository prefix. However, CVSNT does not always properly communicate resource paths in this mode resulting in the failure of some specialized Eclipse CVS operations. The use of a repository prefix should be disable if the full functionality of the Eclipse CVS client is desired - -ProjectDescriptionContentHandler.xml=Error parsing project description file - -Util.invalidResource=Resource {1} is not relative to root {0} -Util.timeout=A timeout occurred connecting to host {0} -Util.truncatedPath=...{0} - -Synchronizer.reload=Examining {0} -Checking_out_from_CVS..._5=Checking out from CVS... -FileSystemSynchronizer_Error_loading_from_CVS/Entries_file_1=Error loading from CVS/Entries file -FileSystemSynchronizer_Error_loading_from_.cvsignore_file_2=Error loading from .cvsignore file -FileSystemSynchronizer_Error_loading_from_CVS/Root,Repository_files_3=Error loading from CVS/Root,Repository files -FileSystemSynchronizer_Error_reloading_sync_information_5=Error reloading sync information -Malformed_entry_line___11=Malformed entry line: -Malformed_entry_line,_missing_name___12=Malformed entry line, missing name: -Malformed_entry_line,_missing_revision___13=Malformed entry line, missing revision: -FolderSyncInfo_Maleformed_root_4=Malformed root -SyncFileUtil_Error_writing_to_Entries.log_48=Error writing to Entries.log -SyncFileUtil_Cannot_close_Entries.log_49=Cannot close Entries.log -SyncFileUtil_Error_reloading_sync_information_58=Error reloading sync information -SyncFileUtil_Error_writing_to_.cvsignore_61=Error writing to .cvsignore -SyncFileUtil_Cannot_close_.cvsignore_62=Cannot close .cvsignore -SyncFileWriter.baseNotAvailable=Could not restore the base contents of ''{0}'' from the local cache. -BaseRevInfo.malformedEntryLine=Malformed entry line ''{0}'' for base revision information file. - -FileModificationValidator.isReadOnly=File is Read Only. - -EXTServerConnection.invalidPort=A port cannot be specified for the ext connection method. -EXTServerConnection.varsNotSet=Cannot run external ext program because CVS_RSH and CVS_SERVER variables are not initialized. -EXTServerConnection.ioError=Error starting external connection program: {0}. Ensure that the path is correct and that you can connect manually using this program. - -CVSRemoteSyncElement.rootDiffers=Error mapping local folder {0} to repository {1}. It is already managed by repository {2}. -CVSRemoteSyncElement.repositoryDiffers=Error mapping local folder {0} to remote folder {1}. It is already mapped to {2}. -Util.Internal_error,_resource_does_not_start_with_root_3=Internal error, resource does not start with root - -CVSProvider.Scrubbing_local_project_1=Scrubbing local project -CVSProvider.Scrubbing_projects_1=Scrubbing projects -CVSProvider.Creating_projects_2=Creating projects - -EclipseFile_Problem_deleting_resource=Problem deleting resource: {0}. {1} -EclipseFile_Problem_accessing_resource=Problem accessing resource: {0}. {1} Perform a Refresh. -EclipseFile_Problem_creating_resource=Problem creating resource: {0}. {1} -EclipseFile_Problem_writing_resource=Problem writing resource ''{0}''. {1} -EclipseFolder_problem_creating=Problem creating folder: {0}. {1} -EclipseFolder.isModifiedProgress=Determining if {0} has outgoing changes... - -EclipseSynchronizer.UpdatingSyncEndOperation=Updating CVS synchronization information... -EclipseSynchronizer.UpdatingSyncEndOperationCancelled=Operation cancelled: updating CVS synchronization information... -EclipseSynchronizer.NotifyingListeners=Notifying of CVS changes... -EclipseSynchronizer.ErrorSettingFolderSync=Cannot set folder sync info on {0} -EclipseSynchronizer.ErrorSettingResourceSync=Cannot set resource sync info on {0} -EclipseSynchronizer.ErrorSettingIgnorePattern=Cannot set ignored pattern on {0} -EclipseSynchronizer.ErrorCommitting=Errors saving CVS synchronization information to disk. Please fix the problems listed below and then update the affected resources from the CVS repository. -EclipseSynchronizer.folderSyncInfoMissing=CVS synchronization information could not be found for folder ''{0}'' -EclipseSynchronizer.workspaceClosedForResource=Invalid attempt to modify the sync info for resource ''{0}'' - -SynchrnoizerSyncInfoCache.failedToSetSyncBytes=Could not change sync info for ''{0}'' from ''{1}'' to ''{2}'' because the workspace is locked. - -SyncFileChangeListener.errorSettingTeamPrivateFlag=Error setting team-private flag on resource - -RemoteFile.getContents=Retrieving remote file contents -RemoteFile.getLogEntries=Retrieving log entries -RemoteFolder.exists=Checking if resource exists remotely -RemoteFolder.getMembers=Retrieving children of remote folder -RemoteModule.getRemoteModules=Retrieving remote modules -RemoteModule.invalidDefinition=Invalid module definition ''{0}'' received from ''{1}''. - -PruneFolderVisitor.caseVariantsExist=The following resources could not be created. -PruneFolderVisitor.caseVariantExists=The resource ''{0}'' could not be created because another resource exists whose path differs only by case. - -Version.unsupportedVersion=Host ''{0}'' is running unsupported CVS version {1}. Although most functionality works, use version 1.11.1p1 or later for full support. -Version.unsupportedCVSNT=Host ''{0}'' is running CVS NT (version {1}) which is not fully supported. However, most functionality is available. -Version.unknownVersionFormat=Host ''{0}'' is running ''{1}'' which is an unknown version to the workbench. Although most functionality may work, use version 1.11.1p1 or later for full support. -Version.versionNotValidRequest=Unable to determine server version. Host ''{0}'' does not support the ''cvs version'' command. Although most functionality works, use version 1.11.1p1 or later for full support. - -LogListener.invalidRevisionFormat=Invalid revision format ''{1}'' for tag ''{0}''. -RemoteFile.Could_not_cache_remote_contents_to_disk._Caching_remote_file_in_memory_instead._1=Could not cache remote contents to disk. Caching remote file in memory instead. Exception follows. - -NotifyInfo.MalformedLine=Invalid Notify format: ''{0}'' -NotifyInfo.MalformedNotificationType=Invalid notification type in line: ''{0}'' -NotifyInfo.MalformedNotifyDate=Invalid date format in line: ''{0}'' - -Session.dot_2=dot - -ResourceSynchronizer.missingBytes=Synchronization bytes are missing for resource ''{1}'' in synchronization partner ''{0}''. 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 deleted file mode 100644 index 69db9b3ad..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSEntryLineTag.java +++ /dev/null @@ -1,64 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import org.eclipse.team.internal.ccvs.core.CVSTag; - -public class CVSEntryLineTag extends CVSTag { - - /* - * The parameter tag must not be null. - */ - public CVSEntryLineTag(CVSTag tag) { - super(tag.getName(), tag.getType()); - } - - public CVSEntryLineTag(String entryLineTag) { - switch (entryLineTag.charAt(0)) { - case 'T' : type = BRANCH; break; - case 'N' : type = VERSION; break; - case 'D' : type = DATE; break; - default: type = HEAD; - } - name = entryLineTag.substring(1); - } - /* - * Returns the tag name - */ - public String getName() { - return name; - } - /* - * Returns the tag type - */ - public int getType() { - return type; - } - - public String toEntryLineFormat(boolean useSamePrefixForBranchAndTag) { - if (type == BRANCH || (type == VERSION && useSamePrefixForBranchAndTag)) - return "T" + name;//$NON-NLS-1$ - else if (type == VERSION) - return "N" + name;//$NON-NLS-1$ - else if (type == DATE) - return "D" + name;//$NON-NLS-1$ - return "";//$NON-NLS-1$ - } - - /* - * For debugging purposes. - */ - public String toString() { - return toEntryLineFormat(false); - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSLocalSyncElement.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSLocalSyncElement.java deleted file mode 100644 index e2334ca51..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSLocalSyncElement.java +++ /dev/null @@ -1,107 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -import org.eclipse.team.core.sync.ILocalSyncElement; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.core.sync.LocalSyncElement; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; - -public class CVSLocalSyncElement extends LocalSyncElement { - - protected IRemoteResource base; - protected IResource local; - - public CVSLocalSyncElement(IResource local, IRemoteResource base) { - this.local = local; - this.base = base; - } - - /* - * @see RemoteSyncElement#create(IResource, IRemoteResource, IRemoteResource) - */ - public ILocalSyncElement create(IResource local, IRemoteResource base, Object data) { - return new CVSLocalSyncElement(local, base); - } - - /* - * @see ILocalSyncElement#getLocal() - */ - public IResource getLocal() { - return local; - } - - /* - * @see ILocalSyncElement#getBase() - */ - public IRemoteResource getBase() { - return base; - } - - /* - * @see ILocalSyncElement#isCheckedOut() - */ - public boolean isCheckedOut() { - return getLocal() != null; - } - - /* - * @see ILocalSyncElement#hasRemote() - */ - public boolean hasRemote() { - return getLocal() != null; - } - - /* - * @see RemoteSyncElement#getData() - */ - protected Object getData() { - return null; - } - - /* - * Answers the CVS resource for this sync element - */ - public ICVSResource getCVSResource() { - return getCVSResourceFor(getLocal()); - } - - /* - * @see LocalSyncElement#isIgnored(IResource) - */ - public boolean isIgnored(IResource child) { - ICVSResource cvsResource = getCVSResourceFor(getLocal()); - if(cvsResource==null || !cvsResource.isFolder() ) { - return false; - } else { - try { - ICVSResource managedChild = ((ICVSFolder)cvsResource).getChild(child.getName()); - return managedChild.isIgnored(); - } catch(CVSException e) { - return false; - } - } - } - - private ICVSResource getCVSResourceFor(IResource resource) { - if(resource.getType() != IResource.FILE) { - return new EclipseFolder((IContainer)resource); - } else { - return new EclipseFile((IFile)resource); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSRemoteSyncElement.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSRemoteSyncElement.java deleted file mode 100644 index 5082f03b9..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSRemoteSyncElement.java +++ /dev/null @@ -1,444 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.ILocalSyncElement; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.core.sync.IRemoteSyncElement; -import org.eclipse.team.core.sync.RemoteSyncElement; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFile; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -public class CVSRemoteSyncElement extends RemoteSyncElement { - - CVSLocalSyncElement localSync; - IRemoteResource remote; - boolean isThreeWay = true; - - public CVSRemoteSyncElement(boolean isThreeWay, IResource local, IRemoteResource base, IRemoteResource remote) { - localSync = new CVSLocalSyncElement(local, base); - this.remote = remote; - this.isThreeWay = isThreeWay; - } - - /* - * @see RemoteSyncElement#create(IResource, IRemoteResource, IRemoteResource) - */ - public IRemoteSyncElement create(boolean isThreeWay, IResource local, IRemoteResource base, IRemoteResource remote, Object data) { - return new CVSRemoteSyncElement(isThreeWay, local, base, remote); - } - - /* - * @see IRemoteSyncElement#getRemote() - */ - public IRemoteResource getRemote() { - return remote; - } - - /* - * @see LocalSyncElement#getData() - */ - protected Object getData() { - return localSync.getData(); - } - - /* - * @see ILocalSyncElement#getLocal() - */ - public IResource getLocal() { - return localSync.getLocal(); - } - - /* - * @see ILocalSyncElement#getBase() - */ - public IRemoteResource getBase() { - return localSync.getBase(); - } - - /* - * @see ILocalSyncElement#isCheckedOut() - */ - public boolean isCheckedOut() { - return localSync.isCheckedOut(); - } - - /* - * Local helper to indicate if the corresponding local resource has a base - */ - public boolean hasBase() { - return getBase() != null; - } - - /* - * @see ILocalSyncElement#hasRemote() - */ - public boolean hasRemote() { - return remote != null; - } - - /* - * @see LocalSyncElement#create(IResource, IRemoteResource, Object) - */ - public ILocalSyncElement create(IResource local, IRemoteResource base, Object data) { - return localSync.create(local, base, data); - } - /* - * @see LocalSyncElement#isIgnored(IResource) - */ - public boolean isIgnored(IResource resource) { - return localSync.isIgnored(resource); - } - /* - * @see IRemoteSyncElement#ignoreBaseTree() - */ - public boolean isThreeWay() { - return isThreeWay; - } - - /* - * Update the sync info of the local resource in such a way that the local changes can be committed. - */ - public void makeOutgoing(IProgressMonitor monitor) throws TeamException { - - int syncKind = getSyncKind(GRANULARITY_TIMESTAMP, monitor); - boolean incoming = (syncKind & DIRECTION_MASK) == INCOMING; - boolean outgoing = (syncKind & DIRECTION_MASK) == OUTGOING; - - ICVSResource local = localSync.getCVSResource(); - RemoteResource remote = (RemoteResource)getRemote(); - ResourceSyncInfo origInfo = local.getSyncInfo(); - MutableResourceSyncInfo info = null; - if(origInfo!=null) { - info = origInfo.cloneMutable(); - } - - if (outgoing) { - // The sync info is alright, it's already outgoing! - return; - } else if (incoming) { - // We have an incoming change, addition, or deletion that we want to ignore - if (local.exists()) { - // We could have an incoming change or deletion - if (remote == null) { - info.setAdded(); - } else { - // Otherwise change the revision to the remote revision and dirty the file - info.setRevision(remote.getSyncInfo().getRevision()); - info.setTimeStamp(null); - } - } else { - // We have an incoming add, turn it around as an outgoing delete - info = remote.getSyncInfo().cloneMutable(); - info.setDeleted(true); - } - } else if (local.exists()) { - // We have a conflict and a local resource! - if (hasRemote()) { - if (hasBase()) { - // We have a conflicting change, Update the local revision - info.setRevision(remote.getSyncInfo().getRevision()); - } else { - // We have conflictin additions. - // We need to fetch the contents of the remote to get all the relevant information (timestamp, permissions) - remote.getContents(Policy.monitorFor(monitor)); - info = remote.getSyncInfo().cloneMutable(); - } - } else if (hasBase()) { - // We have a remote deletion. Make the local an addition - info.setAdded(); - } else { - // There's a local, no base and no remote. We can't possible have a conflict! - Assert.isTrue(false); - } - } else { - // We have a conflict and there is no local! - if (hasRemote()) { - // We have a local deletion that conflicts with remote changes. - info.setRevision(remote.getSyncInfo().getRevision()); - info.setDeleted(true); - } else { - // We have conflicting deletions. Clear the sync info - info = null; - return; - } - } - if(info!=null) { - info.setTag(local.getParent().getFolderSyncInfo().getTag()); - } - ((ICVSFile)local).setSyncInfo(info, ICVSFile.UNKNOWN); - } - - /* - * Update the sync info of the local resource in such a way that the remote resource can be loaded - * ignore any local changes. - */ - public void makeIncoming(IProgressMonitor monitor) throws TeamException { - // To make outgoing deletions incoming, the local will not exist but - // it is still important to unmanage (e.g. delete all meta info) for the - // deletion. - CVSWorkspaceRoot.getCVSResourceFor(getLocal()).unmanage(null); - } - - /* - * Load the resource and folder sync info into the local from the remote - * - * This method can be used on incoming folder additions to set the folder sync info properly - * without hitting the server again. It also applies to conflicts that involves unmanaged - * local resources. - * - * If the local folder is already managed and is a cvs folder, this operation - * will throw an exception if the mapping does not match that of the remote. - */ - public void makeInSync(IProgressMonitor monitor) throws TeamException { - - // Only work on folders - if (! isContainer()) return; - - int syncKind = getSyncKind(GRANULARITY_TIMESTAMP, monitor); - boolean outgoing = (syncKind & DIRECTION_MASK) == OUTGOING; - if (outgoing) return; - - ICVSFolder local = (ICVSFolder)localSync.getCVSResource(); - RemoteFolder remote = (RemoteFolder)getRemote(); - - // The parent must be managed - if (! local.getParent().isCVSFolder()) - return; - - // If the folder already has CVS info, check that the remote and local match - if(local.isManaged() && local.isCVSFolder()) { - // Verify that the root and repository are the same - FolderSyncInfo remoteInfo = remote.getFolderSyncInfo(); - FolderSyncInfo localInfo = local.getFolderSyncInfo(); - if ( ! localInfo.getRoot().equals(remoteInfo.getRoot())) { - throw new CVSException(Policy.bind("CVSRemoteSyncElement.rootDiffers", new Object[] {local.getName(), remoteInfo.getRoot(), localInfo.getRoot()}));//$NON-NLS-1$ - } else if ( ! localInfo.getRepository().equals(remoteInfo.getRepository())) { - throw new CVSException(Policy.bind("CVSRemoteSyncElement.repositoryDiffers", new Object[] {local.getName(), remoteInfo.getRepository(), localInfo.getRepository()}));//$NON-NLS-1$ - } - // The folders are in sync so just return - return; - } - - // Ensure that the folder exists locally - if (! local.exists()) { - local.mkdir(); - } - - // Since the parent is managed, this will also set the resource sync info. It is - // impossible for an incoming folder addition to map to another location in the - // repo, so we assume that using the parent's folder sync as a basis is safe. - // It is also impossible for an incomming folder to be static. - FolderSyncInfo remoteInfo = remote.getFolderSyncInfo(); - FolderSyncInfo localInfo = local.getParent().getFolderSyncInfo(); - local.setFolderSyncInfo(new FolderSyncInfo(remoteInfo.getRepository(), remoteInfo.getRoot(), localInfo.getTag(), false)); - } - /* - * Make all the folders that have both a remote and local in sync by copying - * the sync information from the remote to the local - */ - protected void makeFoldersInSync(IProgressMonitor progress) throws TeamException { - FolderSyncInfo remoteInfo = ((RemoteFolder)getRemote()).getFolderSyncInfo(); - ((ICVSFolder)localSync.getCVSResource()).setFolderSyncInfo(remoteInfo); - ILocalSyncElement[] children = members(progress); - for (int i = 0; i < children.length; i++) { - CVSRemoteSyncElement child = (CVSRemoteSyncElement)children[i]; - if (child.isContainer() && child.getLocal().exists() && child.getRemote() != null) { - child.makeFoldersInSync(progress); - } - } - } - /* - * @see ILocalSyncElement#getSyncKind(int, IProgressMonitor) - */ - public int getSyncKind(int granularity, IProgressMonitor progress) { - - // special handling for folders, the generic sync algorithm doesn't work well - // with CVS because folders are not in namespaces (e.g. they exist in all versions - // and branches). - if(isContainer() && isThreeWay()) { - int folderKind = IRemoteSyncElement.IN_SYNC; - IResource local = getLocal(); - ICVSRemoteFolder remote = (ICVSRemoteFolder)getRemote(); - ICVSFolder cvsFolder = (ICVSFolder)localSync.getCVSResource(); - boolean isCVSFolder = false; - try { - isCVSFolder = cvsFolder.isCVSFolder(); - } catch (CVSException e) { - // Assume the folder is not a CVS folder - } - if(!local.exists()) { - if(remote != null) { - if (isCVSFolder) { - if (containsOutgoingDeletions(cvsFolder)) { - // say the folder is in_sync even though it doesn't exist locally - folderKind = IRemoteSyncElement.IN_SYNC; - } else { - folderKind = IRemoteSyncElement.INCOMING | IRemoteSyncElement.ADDITION; - } - } else { - folderKind = IRemoteSyncElement.INCOMING | IRemoteSyncElement.ADDITION; - } - } else { - // ignore conflicting deletion to keep phantom sync info - } - } else { - if(remote == null) { - if(isCVSFolder) { - folderKind = IRemoteSyncElement.INCOMING | IRemoteSyncElement.DELETION; - } else { - folderKind = IRemoteSyncElement.OUTGOING | IRemoteSyncElement.ADDITION; - } - } else if(!isCVSFolder) { - folderKind = IRemoteSyncElement.CONFLICTING | IRemoteSyncElement.ADDITION; - } else { - // folder exists both locally and remotely and are considered in sync, however - // we aren't checking the folder mappings to ensure that they are the same. - } - } - return folderKind; - } - - // 1. Run the generic sync calculation algorithm, then handle CVS specific - // sync cases. - int kind = super.getSyncKind(granularity, progress); - - // 2. Set the CVS specific sync type based on the workspace sync state provided - // by the CVS server. - if(remote!=null && (kind & IRemoteSyncElement.PSEUDO_CONFLICT) == 0) { - int type = ((RemoteResource)remote).getWorkspaceSyncState(); - switch(type) { - // the server compared both text files and decided that it cannot merge - // them without line conflicts. - case Update.STATE_CONFLICT: - return kind | ILocalSyncElement.MANUAL_CONFLICT; - - // the server compared both text files and decided that it can safely merge - // them without line conflicts. - case Update.STATE_MERGEABLE_CONFLICT: - return kind | ILocalSyncElement.AUTOMERGE_CONFLICT; - } - } - - // 3. unmanage delete/delete conflicts and return that they are in sync - kind = handleDeletionConflicts(kind); - - return kind; - } - - /** - * Return true if the provided phantom folder conyains any outgoing file deletions. - * We only need to detect if there are any files since a phantom folder can only - * contain outgoing filre deletions and other folder. - * - * @param cvsFolder a phantom folder - * @return boolean - */ - private boolean containsOutgoingDeletions(ICVSFolder cvsFolder) { - final boolean result[] = new boolean[] { false }; - try { - cvsFolder.accept(new ICVSResourceVisitor() { - public void visitFile(ICVSFile file) throws CVSException { - // Do nothing. Files are handled below - } - public void visitFolder(ICVSFolder folder) throws CVSException { - if (folder.members(ICVSFolder.FILE_MEMBERS).length > 0) { - result[0] = true; - } else { - folder.acceptChildren(this); - } - } - }); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - return result[0]; - } - - - /* - * If the resource has a delete/delete conflict then ensure that the local is unmanaged so that the - * sync info can be properly flushed. - */ - private int handleDeletionConflicts(int kind) { - if(kind == (IRemoteSyncElement.CONFLICTING | IRemoteSyncElement.DELETION | IRemoteSyncElement.PSEUDO_CONFLICT)) { - try { - ICVSResource cvsResource = localSync.getCVSResource(); - if(!isContainer() && cvsResource.isManaged()) { - cvsResource.unmanage(null); - } - return IRemoteSyncElement.IN_SYNC; - } catch(CVSException e) { - CVSProviderPlugin.log(e); - return IRemoteSyncElement.CONFLICTING | IRemoteSyncElement.DELETION; - } - } - return kind; - } - - /** - * @see RemoteSyncElement#timestampEquals(IRemoteResource, IRemoteResource) - */ - protected boolean timestampEquals(IRemoteResource e1, IRemoteResource e2) { - if(e1.isContainer()) { - if(e2.isContainer()) { - return true; - } - return false; - } - return e1.equals(e2); - } - - /** - * @see RemoteSyncElement#timestampEquals(IResource, IRemoteResource) - */ - protected boolean timestampEquals(IResource e1, IRemoteResource e2) { - if(e1.getType() != IResource.FILE) { - if(e2.isContainer()) { - return true; - } - return false; - } - ICVSFile cvsFile = CVSWorkspaceRoot.getCVSFileFor((IFile)e1); - try { - byte[] syncBytes1 = cvsFile.getSyncBytes(); - byte[] syncBytes2 = ((ICVSRemoteFile)e2).getSyncBytes(); - - if(syncBytes1 != null) { - if(ResourceSyncInfo.isDeletion(syncBytes1) || ResourceSyncInfo.isMerge(syncBytes1) || cvsFile.isModified(null)) { - return false; - } - return ResourceSyncInfo.getRevision(syncBytes1).equals(ResourceSyncInfo.getRevision(syncBytes2)); - } - return false; - } catch(CVSException e) { - CVSProviderPlugin.log(e); - return false; - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSWorkspaceRoot.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSWorkspaceRoot.java deleted file mode 100644 index 757aa8e77..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/CVSWorkspaceRoot.java +++ /dev/null @@ -1,712 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.io.File; -import java.util.ArrayList; -import java.util.HashSet; -import java.util.List; -import java.util.Set; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IWorkspaceRunnable; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteSyncElement; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -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.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder; -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.ICVSRunnable; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Checkout; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Import; -import org.eclipse.team.internal.ccvs.core.client.Request; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * This class provides static methods for checking out projects from a repository - * into the local workspace and for converting IResources into CVSRespources - * and sync trees. - * Instances of this class represent a local workspace root (i.e. a project). - */ -public class CVSWorkspaceRoot { - - private ICVSFolder localRoot; - - public CVSWorkspaceRoot(IContainer resource){ - this.localRoot = getCVSFolderFor(resource); - } - - /** - * Checkout a CVS module. - * - * The provided project represents the target project. Any existing contents - * may or may not get overwritten. If project is <code>null</code> then a project - * will be created based on the provided sourceModule. If soureModule is null, - * then the project name will be used as the module to - * check out. If both are absent, an exception is thrown. - * - * Resources existing in the local file system at the target project location but now - * known to the workbench will be overwritten. - * - * After the successful completion of this method, the project will exist - * and be open. - */ - public static void checkout( - ICVSRepositoryLocation repository, - IProject project, - String sourceModule, - CVSTag tag, - IProgressMonitor monitor) - throws TeamException { - - if (sourceModule == null) - sourceModule = project.getName(); - checkout(new ICVSRemoteFolder[] { new RemoteFolder(null, repository, sourceModule, tag)}, - new IProject[] { project }, monitor); - } - - /** - * Checkout the remote resources into the local workspace. Each resource will - * be checked out into the corresponding project. If the corresponding project is - * null or if projects is null, the name of the remote resource is used as the name of the project. - * - * Resources existing in the local file system at the target project location but now - * known to the workbench will be overwritten. - */ - public static void checkout(final ICVSRemoteFolder[] resources, final IProject[] projects, final IProgressMonitor monitor) throws TeamException { - final TeamException[] eHolder = new TeamException[1]; - try { - IWorkspaceRunnable workspaceRunnable = new IWorkspaceRunnable() { - public void run(IProgressMonitor pm) throws CoreException { - try { - pm.beginTask(null, 1000 * resources.length); - - // Get the location of the workspace root - ICVSFolder root = CVSWorkspaceRoot.getCVSFolderFor(ResourcesPlugin.getWorkspace().getRoot()); - - for (int i=0;i<resources.length;i++) { - IProject project = null; - RemoteFolder resource = (RemoteFolder)resources[i]; - - // Determine the provided target project if there is one - if (projects != null) - project = projects[i]; - - // Determine the remote module to be checked out - String moduleName; - if (resource instanceof RemoteModule) { - moduleName = ((RemoteModule)resource).getName(); - } else { - moduleName = resource.getRepositoryRelativePath(); - } - - // Open a connection session to the repository - ICVSRepositoryLocation repository = resource.getRepository(); - Session session = new Session(repository, root); - try { - session.open(Policy.subMonitorFor(pm, 50)); - - // Determine the local target projects (either the project provider or the module expansions) - final Set targetProjects = new HashSet(); - if (project == null) { - - // Fetch the module expansions - IStatus status = Request.EXPAND_MODULES.execute(session, new String[] {moduleName}, Policy.subMonitorFor(pm, 50)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - - // Convert the module expansions to local projects - String[] expansions = session.getModuleExpansions(); - for (int j = 0; j < expansions.length; j++) { - targetProjects.add(ResourcesPlugin.getWorkspace().getRoot().getProject(new Path(expansions[j]).segment(0))); - } - - } else { - targetProjects.add(project); - } - - // Prepare the target projects to receive resources - root.run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - scrubProjects((IProject[]) targetProjects.toArray(new IProject[targetProjects.size()]), monitor); - } - }, Policy.subMonitorFor(pm, 100)); - - // Build the local options - List localOptions = new ArrayList(); - // Add the option to load into the target project if one was supplied - if (project != null) { - localOptions.add(Checkout.makeDirectoryNameOption(project.getName())); - } - // Prune empty directories if pruning enabled - if (CVSProviderPlugin.getPlugin().getPruneEmptyDirectories()) - localOptions.add(Checkout.PRUNE_EMPTY_DIRECTORIES); - // Add the options related to the CVSTag - CVSTag tag = resource.getTag(); - if (tag == null) { - // A null tag in a remote resource indicates HEAD - tag = CVSTag.DEFAULT; - } - localOptions.add(Update.makeTagOption(tag)); - - // Perform the checkout - IStatus status = Command.CHECKOUT.execute(session, - Command.NO_GLOBAL_OPTIONS, - (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]), - new String[]{moduleName}, - null, - Policy.subMonitorFor(pm, 800)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - // XXX Should we cleanup any partially checked out projects? - throw new CVSServerException(status); - } - - // Bring the project into the workspace - refreshProjects((IProject[])targetProjects.toArray(new IProject[targetProjects.size()]), Policy.subMonitorFor(pm, 100)); - - } finally { - session.close(); - } - } - } - catch (TeamException e) { - // Pass it outside the workspace runnable - eHolder[0] = e; - } finally { - pm.done(); - } - // CoreException and OperationCanceledException are propagated - } - }; - ResourcesPlugin.getWorkspace().run(workspaceRunnable, monitor); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - monitor.done(); - } - // Re-throw the TeamException, if one occurred - if (eHolder[0] != null) { - throw eHolder[0]; - } - } - - private static void manageFolder(ICVSFolder folder, String root) throws CVSException { - // Ensure that the parent is a CVS folder - ICVSFolder parent = folder.getParent(); - if (!parent.isCVSFolder()) { - parent.setFolderSyncInfo(new FolderSyncInfo(FolderSyncInfo.VIRTUAL_DIRECTORY, root, CVSTag.DEFAULT, true)); - IResource resource = parent.getIResource(); - if (resource.getType() != IResource.PROJECT) { - manageFolder(parent, root); - } - } - // reset the folder sync info so it will be managed by it's parent - folder.setFolderSyncInfo(folder.getFolderSyncInfo()); - } - - /** - * Create a remote module in the CVS repository and link the project directory to this remote module. - * The contents of the project are not imported. - */ - public static void createModule(final ICVSRepositoryLocation location, final IProject project, String moduleName, IProgressMonitor monitor) throws TeamException { - - // Determine if the repository is known - boolean alreadyExists = CVSProviderPlugin.getPlugin().isKnownRepository(location.getLocation()); - // Set the folder sync info of the project to point to the remote module - final ICVSFolder folder = (ICVSFolder)CVSWorkspaceRoot.getCVSResourceFor(project); - - try { - // Get the import properties - String message = Policy.bind("CVSProvider.initialImport"); //$NON-NLS-1$ - String vendor = "vendor"; //$NON-NLS-1$ - String tag = "start"; //$NON-NLS-1$ - String projectName = project.getName(); - if (moduleName == null) - moduleName = projectName; - - // Perform the import using a dummy root so the local project is not traversed - Session s = new Session(location, new RemoteFolderTree(null, location, Path.EMPTY.toString(), null)); - s.open(monitor); - try { - IStatus status = Command.IMPORT.execute(s, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] {Import.makeArgumentOption(Command.MESSAGE_OPTION, message)}, - new String[] { moduleName, vendor, tag }, - null, - monitor); - // If we get a warning, the operation most likely failed so check that the status is OK - if (status.getCode() == CVSStatus.SERVER_ERROR || ! status.isOK()) { - throw new CVSServerException(status); - } - } finally { - s.close(); - } - - // perform the workspace modifications in a runnable - try { - final TeamException[] exception = new TeamException[] {null}; - final String modName = moduleName; - ResourcesPlugin.getWorkspace().run(new IWorkspaceRunnable() { - public void run(IProgressMonitor monitor) throws CoreException { - try { - // Link the project to the newly created module - folder.setFolderSyncInfo(new FolderSyncInfo(modName, location.getLocation(), null, false)); - //Register it with Team. If it already is, no harm done. - RepositoryProvider.map(project, CVSProviderPlugin.getTypeId()); - } catch (TeamException e) { - exception[0] = e; - } - } - }, monitor); - if (exception[0] != null) - throw exception[0]; - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } catch (TeamException e) { - // The checkout may have triggered password caching - // Therefore, if this is a newly created location, we want to clear its cache - if ( ! alreadyExists) - CVSProviderPlugin.getPlugin().disposeRepository(location); - throw e; - } - // Add the repository if it didn't exist already - if ( ! alreadyExists) - CVSProviderPlugin.getPlugin().addRepository(location); - } - - /** - * Set the sharing for a project to enable it to be used with the CVSTeamProvider. - * This method ensure that the repository in the FolderSyncInfo is known and that - * the project is mapped to a CVS repository provider. It does not modify the sync - * info associated with the project's resources in any way. - */ - public static void setSharing(IProject project, FolderSyncInfo info, IProgressMonitor monitor) throws TeamException { - - // Ensure provided info matches that of the project - ICVSFolder folder = (ICVSFolder)CVSWorkspaceRoot.getCVSResourceFor(project); - FolderSyncInfo folderInfo = folder.getFolderSyncInfo(); - if ( ! info.equals(folderInfo)) { - throw new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSProvider.infoMismatch", project.getName())));//$NON-NLS-1$ - } - - // Ensure that the provided location is managed - ICVSRepositoryLocation location = CVSProviderPlugin.getPlugin().getRepository(info.getRoot()); - - // Register the project with Team - RepositoryProvider.map(project, CVSProviderPlugin.getTypeId()); - } - - /** - * Answer the list of directories that a checkout of the given resources would expand to. - * In other words, the returned strings represent the root paths that the given resources would - * be loaded into. - */ - public static String[] getExpansions(ICVSRemoteFolder[] resources, IProgressMonitor monitor) throws CVSException { - - if (resources.length == 0) return new String[0]; - - // Get the location of the workspace root - ICVSFolder root = CVSWorkspaceRoot.getCVSFolderFor(ResourcesPlugin.getWorkspace().getRoot()); - - // Get the command arguments - String[] arguments = new String[resources.length]; - for (int i = 0; i < resources.length; i++) { - if (resources[i] instanceof RemoteModule) { - arguments[i] = ((RemoteModule)resources[i]).getName(); - } else { - arguments[i] = resources[i].getRepositoryRelativePath(); - } - } - - // Perform the Expand-Modules command - IStatus status; - Session s = new Session(resources[0].getRepository(), root); - s.open(monitor); - try { - status = Request.EXPAND_MODULES.execute(s, arguments, monitor); - } finally { - s.close(); - } - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - - return s.getModuleExpansions(); - } - - /* - * Delete the target projects before checking out - */ - private static void scrubProjects(IProject[] projects, IProgressMonitor monitor) throws CVSException { - if (projects == null) { - monitor.done(); - return; - } - monitor.beginTask(Policy.bind("CVSProvider.Scrubbing_projects_1"), projects.length * 100); //$NON-NLS-1$ - try { - for (int i=0;i<projects.length;i++) { - IProject project = projects[i]; - if (project != null && project.exists()) { - if(!project.isOpen()) { - project.open(Policy.subMonitorFor(monitor, 10)); - } - // We do not want to delete the project to avoid a project deletion delta - // We do not want to delete the .project to avoid core exceptions - monitor.subTask(Policy.bind("CVSProvider.Scrubbing_local_project_1")); //$NON-NLS-1$ - // unmap the project from any previous repository provider - if (RepositoryProvider.getProvider(project) != null) - RepositoryProvider.unmap(project); - IResource[] children = project.members(IContainer.INCLUDE_TEAM_PRIVATE_MEMBERS); - IProgressMonitor subMonitor = Policy.subMonitorFor(monitor, 80); - subMonitor.beginTask(null, children.length * 100); - try { - for (int j = 0; j < children.length; j++) { - if ( ! children[j].getName().equals(".project")) {//$NON-NLS-1$ - children[j].delete(true /*force*/, Policy.subMonitorFor(subMonitor, 100)); - } - } - } finally { - subMonitor.done(); - } - } else if (project != null) { - // Make sure there is no directory in the local file system. - File location = new File(project.getParent().getLocation().toFile(), project.getName()); - if (location.exists()) { - deepDelete(location); - } - } - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - monitor.done(); - } - } - - private static void deepDelete(File resource) { - if (resource.isDirectory()) { - File[] fileList = resource.listFiles(); - for (int i = 0; i < fileList.length; i++) { - deepDelete(fileList[i]); - } - } - resource.delete(); - } - - /* - * Bring the provied projects into the workspace - */ - private static void refreshProjects(IProject[] projects, IProgressMonitor monitor) throws CoreException, TeamException { - monitor.beginTask(Policy.bind("CVSProvider.Creating_projects_2"), projects.length * 100); //$NON-NLS-1$ - try { - for (int i = 0; i < projects.length; i++) { - IProject project = projects[i]; - // Register the project with Team - RepositoryProvider.map(project, CVSProviderPlugin.getTypeId()); - CVSTeamProvider provider = (CVSTeamProvider)RepositoryProvider.getProvider(project, CVSProviderPlugin.getTypeId()); - provider.setWatchEditEnabled(CVSProviderPlugin.getPlugin().isWatchEditEnabled()); - } - - } finally { - monitor.done(); - } - } - - public static ICVSFolder getCVSFolderFor(IContainer resource) { - return new EclipseFolder(resource); - } - - - public static ICVSFile getCVSFileFor(IFile resource) { - return new EclipseFile(resource); - } - - - public static ICVSResource getCVSResourceFor(IResource resource) { - if (resource.getType() == IResource.FILE) - return getCVSFileFor((IFile) resource); - else - return getCVSFolderFor((IContainer) resource); - } - - public static ICVSRemoteResource getRemoteResourceFor(IResource resource) throws CVSException { - ICVSResource managed = getCVSResourceFor(resource); - return getRemoteResourceFor(managed); - } - - public static ICVSRemoteResource getRemoteResourceFor(ICVSResource resource) throws CVSException { - if (resource.isFolder()) { - ICVSFolder folder = (ICVSFolder)resource; - FolderSyncInfo syncInfo = folder.getFolderSyncInfo(); - if (syncInfo != null) { - return new RemoteFolder(null, CVSProviderPlugin.getPlugin().getRepository(syncInfo.getRoot()), syncInfo.getRepository(), syncInfo.getTag()); - } - } else { - if (resource.isManaged()) - return RemoteFile.getBase((RemoteFolder)getRemoteResourceFor(resource.getParent()), (ICVSFile)resource); - } - return null; - } - - public static ICVSRemoteResource getBaseFor(ICVSResource resource) throws CVSException { - if (resource.isFolder()) { - ICVSFolder folder = (ICVSFolder)resource; - FolderSyncInfo syncInfo = folder.getFolderSyncInfo(); - if (syncInfo != null) { - return new RemoteFolder(null, CVSProviderPlugin.getPlugin().getRepository(syncInfo.getRoot()), syncInfo.getRepository(), syncInfo.getTag()); - } - } else { - if (resource.isManaged()) - return RemoteFile.getBase((RemoteFolder)getRemoteResourceFor(resource.getParent()), (ICVSFile)resource); - } - return null; - } - - public static ICVSRemoteResource getBaseFor(IResource resource) throws CVSException { - ICVSResource managed = getCVSResourceFor(resource); - return getBaseFor(managed); - } - - /* - * Helper method that uses the parent of a local resource that has no base to ensure that the resource - * wasn't added remotely by a third party - */ - private static ICVSRemoteResource getRemoteTreeFromParent(IResource resource, ICVSResource managed, CVSTag tag, IProgressMonitor progress) throws TeamException { - // If the parent isn't mapped to CVS, there's nothing we can do - ICVSFolder parent = managed.getParent(); - FolderSyncInfo syncInfo = parent.getFolderSyncInfo(); - if (syncInfo == null) { - throw new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTeamProvider.unmanagedParent", resource.getFullPath().toString()), null)); //$NON-NLS-1$ - } - ICVSRepositoryLocation location = CVSProviderPlugin.getPlugin().getRepository(parent.getFolderSyncInfo().getRoot()); - RemoteFolder remoteParent = RemoteFolderTreeBuilder.buildRemoteTree((CVSRepositoryLocation)location, parent, tag, progress); - ICVSRemoteResource remote = null; - if (remoteParent != null) { - try { - remote = (ICVSRemoteResource)remoteParent.getChild(resource.getName()); - } catch (CVSException e) { - remote = null; - } - // The types need to match or we're in trouble - if (remote != null && !(remote.isContainer() == managed.isFolder())) - throw new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTeamProvider.typesDiffer", resource.getFullPath().toString()), null)); //$NON-NLS-1$ - } - return remote; - } - - public static IRemoteSyncElement getRemoteSyncTree(IResource resource, CVSTag tag, IProgressMonitor progress) throws TeamException { - ICVSResource managed = CVSWorkspaceRoot.getCVSResourceFor(resource); - ICVSRemoteResource remote = CVSWorkspaceRoot.getRemoteResourceFor(resource); - ICVSRemoteResource baseTree = null; - - // The resource doesn't have a remote base. - // However, we still need to check to see if its been created remotely by a third party. - if(resource.getType() == IResource.FILE) { - baseTree = remote; - ICVSRepositoryLocation location; - if (remote == null) { - // If there's no base for the file, get the repository location from the parent - ICVSRemoteResource parent = CVSWorkspaceRoot.getRemoteResourceFor(resource.getParent()); - if (parent == null) { - throw new CVSException(new CVSStatus(CVSStatus.ERROR, Policy.bind("CVSTeamProvider.unmanagedParent", resource.getFullPath().toString()), null)); //$NON-NLS-1$ - } - location = parent.getRepository(); - } else { - location = remote.getRepository(); - } - remote = RemoteFolderTreeBuilder.buildRemoteTree((CVSRepositoryLocation)location, (ICVSFile)managed, tag, progress); - } else { - if (remote == null) { - remote = getRemoteTreeFromParent(resource, managed, tag, progress); - } else { - ICVSRepositoryLocation location = remote.getRepository(); - baseTree = RemoteFolderTreeBuilder.buildBaseTree((CVSRepositoryLocation)location, (ICVSFolder)managed, tag, progress); - remote = RemoteFolderTreeBuilder.buildRemoteTree((CVSRepositoryLocation)location, (ICVSFolder)managed, tag, progress); - } - } - return new CVSRemoteSyncElement(true /*three way*/, resource, baseTree, remote); - } - - /** - * Sync the given unshared project with the given repository and module. - */ - public static IRemoteSyncElement getRemoteSyncTree(IProject project, ICVSRepositoryLocation location, String moduleName, CVSTag tag, IProgressMonitor progress) throws TeamException { - if (CVSWorkspaceRoot.getCVSFolderFor(project).isCVSFolder()) { - return getRemoteSyncTree(project, tag, progress); - } else { - progress.beginTask(null, 100); - RemoteFolder folder = new RemoteFolder(null, location, moduleName, tag); - RemoteFolderTree remote = RemoteFolderTreeBuilder.buildRemoteTree((CVSRepositoryLocation)folder.getRepository(), folder, folder.getTag(), Policy.subMonitorFor(progress, 80)); - CVSRemoteSyncElement tree = new CVSRemoteSyncElement(true /*three way*/, project, null, remote); - tree.makeFoldersInSync(Policy.subMonitorFor(progress, 10)); - - RepositoryProvider.map(project, CVSProviderPlugin.getTypeId()); - - progress.done(); - return tree; - } - } - - public static IRemoteSyncElement getRemoteSyncTree(IProject project, IResource[] resources, CVSTag tag, IProgressMonitor progress) throws TeamException { - ICVSResource managed = CVSWorkspaceRoot.getCVSResourceFor(project); - ICVSRemoteResource remote = CVSWorkspaceRoot.getRemoteResourceFor(project); - if (remote == null) { - return new CVSRemoteSyncElement(true /*three way*/, project, null, null); - } - ArrayList cvsResources = new ArrayList(); - for (int i = 0; i < resources.length; i++) { - cvsResources.add(CVSWorkspaceRoot.getCVSResourceFor(resources[i])); - } - CVSRepositoryLocation location = (CVSRepositoryLocation)remote.getRepository(); - ICVSRemoteResource base = RemoteFolderTreeBuilder.buildBaseTree(location, (ICVSFolder)managed, tag, progress); - remote = RemoteFolderTreeBuilder.buildRemoteTree(location, (ICVSFolder)managed, (ICVSResource[]) cvsResources.toArray(new ICVSResource[cvsResources.size()]), tag, progress); - return new CVSRemoteSyncElement(true /*three way*/, project, base, remote); - } - - public static ICVSRemoteResource getRemoteTree(IResource resource, CVSTag tag, IProgressMonitor progress) throws TeamException { - return getRemoteTree(resource, tag, false /* cache file contents hint */, progress); - } - - public static ICVSRemoteResource getRemoteTree(IResource resource, CVSTag tag, boolean cacheFileContentsHint, IProgressMonitor progress) throws TeamException { - ICVSResource managed = CVSWorkspaceRoot.getCVSResourceFor(resource); - ICVSRemoteResource remote = CVSWorkspaceRoot.getRemoteResourceFor(resource); - if (remote == null) { - progress.beginTask(null, 100); - remote = getRemoteTreeFromParent(resource, managed, tag, Policy.subMonitorFor(progress, 50)); - if (cacheFileContentsHint && remote != null && remote instanceof RemoteFile) { - RemoteFile file = (RemoteFile)remote; - if (!file.isContentsCached()) { - file.fetchContents(Policy.subMonitorFor(progress, 50)); - } - } - progress.done(); - } else if(resource.getType() == IResource.FILE) { - ICVSRepositoryLocation location = remote.getRepository(); - if (cacheFileContentsHint) { - remote = FileContentCachingService.buildRemoteTree((CVSRepositoryLocation)location, (ICVSFile)managed, tag, progress); - } else { - remote = RemoteFolderTreeBuilder.buildRemoteTree((CVSRepositoryLocation)location, (ICVSFile)managed, tag, progress); - } - } else { - ICVSRepositoryLocation location = remote.getRepository(); - if (cacheFileContentsHint) { - remote = FileContentCachingService.buildRemoteTree((CVSRepositoryLocation)location, (ICVSFolder)managed, tag, progress); - } else { - remote = RemoteFolderTreeBuilder.buildRemoteTree((CVSRepositoryLocation)location, (ICVSFolder)managed, tag, progress); - } - } - return remote; - } - - public static boolean hasRemote(IResource resource) { - try { - ICVSResource cvsResource = getCVSResourceFor(resource); - int type = resource.getType(); - if(type!=IResource.FILE) { - if(type==IResource.PROJECT) { - return ((ICVSFolder)cvsResource).isCVSFolder(); - } else { - return cvsResource.isManaged(); - } - } else { - byte[] syncBytes = ((ICVSFile)cvsResource).getSyncBytes(); - if(syncBytes!=null) { - return !ResourceSyncInfo.isAddition(syncBytes); - } else { - return false; - } - } - } catch(CVSException e) { - return false; - } - } - - public ICVSRepositoryLocation getRemoteLocation() throws CVSException { - FolderSyncInfo info = localRoot.getFolderSyncInfo(); - if (info == null) { - throw new CVSException(Policy.bind("CVSWorkspaceRoot.notCVSFolder", localRoot.getName())); //$NON-NLS-1$ - } - return CVSProviderPlugin.getPlugin().getRepository(info.getRoot()); - } - - public ICVSFolder getLocalRoot() { - return localRoot; - } - - - /** - * Return true if the resource is part of a link (i.e. a linked resource or - * one of it's children. - * - * @param container - * @return boolean - */ - public static boolean isLinkedResource(IResource resource) { - // check the resource directly first - if (resource.isLinked()) return true; - // projects and root cannot be links - if (resource.getType() == IResource.PROJECT || resource.getType() == IResource.ROOT) { - return false; - } - // look one level under the project to see if the resource is part of a link - String linkedParentName = resource.getProjectRelativePath().segment(0); - IFolder linkedParent = resource.getProject().getFolder(linkedParentName); - return linkedParent.isLinked(); - } - - /** - * A resource is considered shared - * @param resource - * @return boolean - */ - public static boolean isSharedWithCVS(IResource resource) throws CVSException { - if (!resource.isAccessible()) return false; - if(isLinkedResource(resource)) return false; - - if(RepositoryProvider.getProvider(resource.getProject(), CVSProviderPlugin.getTypeId()) == null) { - return false; - } - - ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(resource); - if (cvsResource.isManaged()) return true; - if (!cvsResource.exists()) return false; - if (cvsResource.isFolder() && ((ICVSFolder) cvsResource).isCVSFolder()) return true; - if (cvsResource.isIgnored()) return false; - return cvsResource.getParent().isCVSFolder(); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseFile.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseFile.java deleted file mode 100644 index 3305c6489..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseFile.java +++ /dev/null @@ -1,562 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.io.File; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Date; -import java.util.List; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceStatus; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -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.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.syncinfo.BaserevInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Represents handles to CVS resource on the local file system. Synchronization - * information is taken from the CVS subdirectories. - */ -public class EclipseFile extends EclipseResource implements ICVSFile { - - private static final String TEMP_FILE_EXTENSION = ".tmp";//$NON-NLS-1$ - private static final IPath PROJECT_META_DATA_PATH = new Path(".project");//$NON-NLS-1$ - - /** - * Create a handle based on the given local resource. - */ - protected EclipseFile(IFile file) { - super(file); - } - - /* - * @see ICVSResource#delete() - */ - public void delete() throws CVSException { - try { - ((IFile)resource).delete(false /*force*/, true /*keepHistory*/, null); - } catch(CoreException e) { - throw CVSException.wrapException(resource, Policy.bind("EclipseFile_Problem_deleting_resource", resource.getFullPath().toString(), e.getStatus().getMessage()), e); //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - public long getSize() { - return getIOFile().length(); - } - - public InputStream getContents() throws CVSException { - try { - return getIFile().getContents(); - } catch (CoreException e) { - throw CVSException.wrapException(resource, Policy.bind("EclipseFile_Problem_accessing_resource", resource.getFullPath().toString(), e.getStatus().getMessage()), e); //$NON-NLS-1$ //$NON-NLS-2$ - } - } - - /* - * @see ICVSFile#getTimeStamp() - */ - public Date getTimeStamp() { - File ioFile = getIOFile(); - if (ioFile == null) { - // If there is no file, return the same timestamp as ioFile.lastModified() would - return new Date(0L); - } - return new Date((ioFile.lastModified()/1000)*1000); - } - - /* - * @see ICVSFile#setTimeStamp(String) - */ - public void setTimeStamp(Date date) throws CVSException { - long time; - if (date == null) { - time = System.currentTimeMillis(); - } else { - time = date.getTime(); - } - getIOFile().setLastModified(time); - try { - // Needed for workaround to Platform Core Bug # - resource.refreshLocal(IResource.DEPTH_ZERO, null); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /* - * @see ICVSResource#isFolder() - */ - public boolean isFolder() { - return false; - } - - /* - * @see ICVSFile#isModified() - */ - public boolean isModified(IProgressMonitor monitor) throws CVSException { - - // ignore the monitor, there is no valuable progress to be shown when - // calculating the dirty state for files. It is relatively fast. - - if (!exists()) { - return getSyncBytes() != null; - } - int state = EclipseSynchronizer.getInstance().getModificationState(getIFile()); - - if (state != UNKNOWN) { - return state != CLEAN; - } - - // nothing cached, need to manually check (and record) - ResourceSyncInfo info = getSyncInfo(); - if (info == null && isIgnored()) return false; - // unmanaged files are reported as modified - boolean dirty = computeModified(info); - setModified(dirty); - return dirty; - } - - /* - * Deteremine if the receiver is modified when compared with the given sync - * info. - */ - private boolean computeModified(ResourceSyncInfo info) throws CVSException { - // if there is no sync info and it doesn't exist then it is a phantom we don't care - // about. - if (info == null) { - return exists(); - } - - // isMerged() must be called because when a file is updated and merged by the cvs server the timestamps - // are equal. Merged files should however be reported as dirty because the user should take action and commit - // or review the merged contents. - if(info.isAdded() || info.isMerged() || !exists()) return true; - return !getTimeStamp().equals(info.getTimeStamp()); - } - - /* - * @see ICVSResource#accept(ICVSResourceVisitor) - */ - public void accept(ICVSResourceVisitor visitor) throws CVSException { - visitor.visitFile(this); - } - - /* - * @see ICVSResource#accept(ICVSResourceVisitor, boolean) - */ - public void accept(ICVSResourceVisitor visitor, boolean recurse) throws CVSException { - visitor.visitFile(this); - } - - /* - * This is to be used by the Copy handler. The filename of the form .#filename - */ - public void copyTo(String filename) throws CVSException { - try { - IPath targetPath = new Path(filename); - IFile targetFile = getIFile().getParent().getFile(targetPath); - if (targetFile.exists()) { - // There is a file in the target location. - // Delete it and keep the history just in case - targetFile.delete(false /* force */, true /* keep history */, null); - } - getIFile().copy(targetPath, true /*force*/, null); - } catch(CoreException e) { - throw new CVSException(e.getStatus()); - } - } - - /* - * @see ICVSResource#getRemoteLocation() - */ - public String getRemoteLocation(ICVSFolder stopSearching) throws CVSException { - return getParent().getRemoteLocation(stopSearching) + SEPARATOR + getName(); - } - - /* - * @see ICVSFile#setReadOnly() - */ - public void setContents(InputStream stream, int responseType, boolean keepLocalHistory, IProgressMonitor monitor) throws CVSException { - try { - IFile file = getIFile(); - if (PROJECT_META_DATA_PATH.equals(file.getFullPath().removeFirstSegments(1))) { - responseType = UPDATED; - } - switch (responseType) { - case UPDATED: - if (resource.exists()) { - file.setContents(stream, true /*force*/, true /*keep history*/, monitor); - break; - } - case CREATED: // creating a new file so it should not exist locally - file.create(stream, false /*force*/, monitor); - break; - case MERGED: // merging contents into a file that exists locally - // Ensure we don't leave the file in a partially written state - IFile tempFile = file.getParent().getFile(new Path(file.getName() + TEMP_FILE_EXTENSION)); - monitor.beginTask(null, 100); - if (tempFile.exists()) - tempFile.delete(true, Policy.subMonitorFor(monitor, 25)); - tempFile.create(stream, true /*force*/, Policy.subMonitorFor(monitor, 25)); - file.delete(false, true, Policy.subMonitorFor(monitor, 25)); - tempFile.move(new Path(file.getName()), true /*force*/, false /*history*/, Policy.subMonitorFor(monitor, 25)); - monitor.done(); - break; - case UPDATE_EXISTING: // creating a new file so it should exist locally - file.setContents(stream, true /*force*/, true /*keep history*/, monitor); - break; - } - } catch(CoreException e) { - String message = null; - if (e.getStatus().getCode() == IResourceStatus.FAILED_READ_LOCAL) { - // This error indicates that Core couldn't read from the server stream - // The real reason will be in the message of the wrapped exception - Throwable t = e.getStatus().getException(); - if (t != null) message = t.getMessage(); - } - if (message == null) message = e.getMessage(); - throw CVSException.wrapException(resource, Policy.bind("EclipseFile_Problem_writing_resource", resource.getFullPath().toString(), message), e); //$NON-NLS-1$ - } - } - - /* - * @see ICVSFile#setReadOnly() - */ - public void setReadOnly(boolean readOnly) throws CVSException { - getIFile().setReadOnly(readOnly); - } - - /* - * @see ICVSFile#isReadOnly() - */ - public boolean isReadOnly() throws CVSException { - return getIFile().isReadOnly(); - } - - /* - * Typecasting helper - */ - public IFile getIFile() { - return (IFile)resource; - } - - /* - * To allow accessing size and timestamp for the underlying java.io.File - */ - private File getIOFile() { - IPath location = resource.getLocation(); - if(location!=null) { - return location.toFile(); - } - return null; - } - /** - * @see ICVSFile#getLogEntries(IProgressMonitor) - */ - public ILogEntry[] getLogEntries(IProgressMonitor monitor) throws TeamException { - byte[] syncBytes = getSyncBytes(); - if(syncBytes != null && !ResourceSyncInfo.isAddition(syncBytes)) { - ICVSRemoteResource remoteFile = CVSWorkspaceRoot.getRemoteResourceFor(resource); - return ((ICVSRemoteFile)remoteFile).getLogEntries(monitor); - } - return new ILogEntry[0]; - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#setNotifyInfo(NotifyInfo) - */ - public void setNotifyInfo(NotifyInfo info) throws CVSException { - if (isManaged()) { - EclipseSynchronizer.getInstance().setNotifyInfo(resource, info); - // On an edit, the base should be cached - // On an unedit, the base should be restored (and cleared?) - // On a commit, the base should be cleared - } - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#getNotifyInfo() - */ - public NotifyInfo getNotifyInfo() throws CVSException { - if (isManaged()) { - return EclipseSynchronizer.getInstance().getNotifyInfo(resource); - } - return null; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#setNotifyInfo(NotifyInfo) - */ - public void setBaserevInfo(BaserevInfo info) throws CVSException { - if (isManaged()) { - if (info == null) { - EclipseSynchronizer.getInstance().deleteBaserevInfo(resource); - EclipseSynchronizer.getInstance().deleteFileFromBaseDirectory(getIFile(), null); - } else - EclipseSynchronizer.getInstance().setBaserevInfo(resource, info); - } - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#getNotifyInfo() - */ - public BaserevInfo getBaserevInfo() throws CVSException { - if (isManaged()) { - return EclipseSynchronizer.getInstance().getBaserevInfo(resource); - } - return null; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#checkout(int) - */ - public void edit(final int notifications, IProgressMonitor monitor) throws CVSException { - if (!isReadOnly()) return; - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - byte[] syncBytes = getSyncBytes(); - if (syncBytes == null || ResourceSyncInfo.isAddition(syncBytes)) return; - - // convert the notifications to internal form - char[] internalFormat; - if (notifications == NO_NOTIFICATION) { - internalFormat = null; - } else if (notifications == NOTIFY_ON_ALL) { - internalFormat = NotifyInfo.ALL; - } else { - List notificationCharacters = new ArrayList(); - if ((notifications & NOTIFY_ON_EDIT) >0) - notificationCharacters.add(new Character(NotifyInfo.EDIT)); - if ((notifications & NOTIFY_ON_UNEDIT) >0) - notificationCharacters.add(new Character(NotifyInfo.UNEDIT)); - if ((notifications & NOTIFY_ON_COMMIT) >0) - notificationCharacters.add(new Character(NotifyInfo.COMMIT)); - internalFormat = new char[notificationCharacters.size()]; - for (int i = 0; i < internalFormat.length; i++) { - internalFormat[i] = ((Character)notificationCharacters.get(i)).charValue(); - } - } - - // record the notification - NotifyInfo notifyInfo = new NotifyInfo(getName(), NotifyInfo.EDIT, new Date(), internalFormat); - setNotifyInfo(notifyInfo); - - // Only record the base if the file is not modified - if (!isModified(null)) { - EclipseSynchronizer.getInstance().copyFileToBaseDirectory(getIFile(), monitor); - setBaserevInfo(new BaserevInfo(getName(), ResourceSyncInfo.getRevision(syncBytes))); - } - - // allow editing - setReadOnly(false); - } - }, monitor); - - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#uncheckout() - */ - public void unedit(IProgressMonitor monitor) throws CVSException { - if (isReadOnly()) return; - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - // record the notification - NotifyInfo info = getNotifyInfo(); - if (info != null && info.getNotificationType() == NotifyInfo.EDIT) { - info = null; - } else { - info = new NotifyInfo(getName(), NotifyInfo.UNEDIT, new Date(), null); - } - setNotifyInfo(info); - - if (isModified(null)) { - ResourceSyncInfo syncInfo = getSyncInfo(); - BaserevInfo baserevInfo = getBaserevInfo(); - EclipseSynchronizer.getInstance().restoreFileFromBaseDirectory(getIFile(), monitor); - // reset any changes that may have been merged from the server - if (!syncInfo.getRevision().equals(baserevInfo.getRevision())) { - MutableResourceSyncInfo newInfo = syncInfo.cloneMutable(); - newInfo.setRevision(baserevInfo.getRevision()); - newInfo.setTimeStamp(getTimeStamp()); - newInfo.setDeleted(false); - setSyncInfo(newInfo, ICVSFile.CLEAN); - } else { - // an unedited file is no longer modified - setModified(false); - } - } else { - // We still need to report a state change - setSyncBytes(getSyncBytes(), ICVSFile.CLEAN); - } - setBaserevInfo(null); - - // prevent editing - setReadOnly(true); - } - }, monitor); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#notificationCompleted() - */ - public void notificationCompleted() throws CVSException { - EclipseSynchronizer.getInstance().deleteNotifyInfo(resource); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#getPendingNotification() - */ - public NotifyInfo getPendingNotification() throws CVSException { - return getNotifyInfo(); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#committed(String) - */ - public void checkedIn(String entryLine) throws CVSException { - ResourceSyncInfo oldInfo = getSyncInfo(); - ResourceSyncInfo newInfo = null; - int modificationState = ICVSFile.CLEAN; - if (entryLine == null) { - // The file contents matched the server contents so no entry line was sent - if (oldInfo == null) return; - Date timeStamp = oldInfo.getTimeStamp(); - if (timeStamp == null || oldInfo.isMergedWithConflicts()) { - // If the entry line has no timestamp, put the file timestamp in the entry line - if(! oldInfo.isAdded()) { - MutableResourceSyncInfo mutable = oldInfo.cloneMutable(); - mutable.setTimeStamp(getTimeStamp(), true /* clear merged */); - newInfo = mutable; - } - } else { - // reset the file timestamp to the one from the entry line - setTimeStamp(timeStamp); - // (newInfo = null) No need to set the newInfo as there is no sync info change - } - // (modified = false) the file will be no longer modified - } else if (oldInfo == null) { - // cvs add of a file - newInfo = new ResourceSyncInfo(entryLine, null, null); - // an added file should show up as modified - modificationState = ICVSFile.DIRTY; - } else { - // commit of a changed file - newInfo = new ResourceSyncInfo(entryLine, oldInfo.getPermissions(), getTimeStamp()); - // (modified = false) a committed file is no longer modified - - } - if (newInfo != null) setSyncInfo(newInfo, modificationState); - clearCachedBase(); - } - - private void clearCachedBase() throws CVSException { - BaserevInfo base = getBaserevInfo(); - if (base != null) { - setBaserevInfo(null); - setReadOnly(true); - } - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResource#unmanage(org.eclipse.core.runtime.IProgressMonitor) - */ - public void unmanage(IProgressMonitor monitor) throws CVSException { - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - EclipseFile.super.unmanage(monitor); - clearCachedBase(); - } - }, monitor); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#isEdited() - */ - public boolean isEdited() throws CVSException { - return EclipseSynchronizer.getInstance().isEdited(getIFile()); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResource#setSyncInfo(org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo) - */ - public void setSyncInfo(ResourceSyncInfo info, int modificationState) throws CVSException { - setSyncBytes(info.getBytes(), info, modificationState); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.EclipseResource#setSyncBytes(byte[], int) - */ - public void setSyncBytes(byte[] syncBytes, int modificationState) throws CVSException { - setSyncBytes(syncBytes, null, modificationState); - } - - /* - * @see org.eclipse.team.internal.ccvs.core.resources.EclipseResource#setSyncBytes(byte[], int) - */ - private void setSyncBytes(byte[] syncBytes, ResourceSyncInfo info, int modificationState) throws CVSException { - Assert.isNotNull(syncBytes); - setSyncBytes(syncBytes); - boolean modified; - if (modificationState == UNKNOWN) { - if (info == null) { - info = new ResourceSyncInfo(syncBytes); - } - modified = computeModified(info); - } else { - modified = modificationState == DIRTY; - } - setModified(modified); - } - - public void handleModification(boolean forAddition) throws CVSException { - if (isIgnored()) { - // Special case handling for when a resource passes from the un-managed state - // to the ignored state (e.g. ignoring the ignore file). Parent dirty state must be - // recalculated but since the resource's end state is ignored there is a lot of code - // in the plugin that simply disregards the change to the resource. - // There may be a better was of handling resources that transition from un-managed to - // ignored but for now this seems like the safest change. - if(! resource.isDerived()) { - setModified(false); - } - return; - } - // set the modification state to what it really is and return true if the modification state changed - setModified(computeModified(getSyncInfo())); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.EclipseResource#run(org.eclipse.team.internal.ccvs.core.ICVSRunnable, org.eclipse.core.runtime.IProgressMonitor) - */ - protected void run(ICVSRunnable job, IProgressMonitor monitor) throws CVSException { - getParent().run(job, monitor); - } - -} - - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseFolder.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseFolder.java deleted file mode 100644 index 5217287a7..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseFolder.java +++ /dev/null @@ -1,404 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IWorkspaceRoot; -import org.eclipse.core.resources.IWorkspaceRunnable; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -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.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * Implements the ICVSFolder interface on top of an - * instance of the ICVSFolder interface - * - * @see ICVSFolder - */ -class EclipseFolder extends EclipseResource implements ICVSFolder { - - protected EclipseFolder(IContainer container) { - super(container); - } - - /** - * @see ICVSFolder#members(int) - */ - public ICVSResource[] members(int flags) throws CVSException { - final List result = new ArrayList(); - IResource[] resources = EclipseSynchronizer.getInstance().members((IContainer)resource); - boolean includeFiles = (((flags & FILE_MEMBERS) != 0) || ((flags & (FILE_MEMBERS | FOLDER_MEMBERS)) == 0)); - boolean includeFolders = (((flags & FOLDER_MEMBERS) != 0) || ((flags & (FILE_MEMBERS | FOLDER_MEMBERS)) == 0)); - boolean includeManaged = (((flags & MANAGED_MEMBERS) != 0) || ((flags & (MANAGED_MEMBERS | UNMANAGED_MEMBERS | IGNORED_MEMBERS)) == 0)); - boolean includeUnmanaged = (((flags & UNMANAGED_MEMBERS) != 0) || ((flags & (MANAGED_MEMBERS | UNMANAGED_MEMBERS | IGNORED_MEMBERS)) == 0)); - boolean includeIgnored = ((flags & IGNORED_MEMBERS) != 0); - boolean includeExisting = (((flags & EXISTING_MEMBERS) != 0) || ((flags & (EXISTING_MEMBERS | PHANTOM_MEMBERS)) == 0)); - boolean includePhantoms = (((flags & PHANTOM_MEMBERS) != 0) || ((flags & (EXISTING_MEMBERS | PHANTOM_MEMBERS)) == 0)); - for (int i = 0; i < resources.length; i++) { - IResource resource = resources[i]; - ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(resource); - if ((includeFiles && (resource.getType()==IResource.FILE)) - || (includeFolders && (resource.getType()==IResource.FOLDER))) { - boolean isManaged = cvsResource.isManaged(); - boolean isIgnored = cvsResource.isIgnored(); - if ((isManaged && includeManaged)|| (isIgnored && includeIgnored) - || ( ! isManaged && ! isIgnored && includeUnmanaged)) { - boolean exists = cvsResource.exists(); - if ((includeExisting && exists) || (includePhantoms && !exists)) { - result.add(cvsResource); - } - } - - } - } - return (ICVSResource[]) result.toArray(new ICVSResource[result.size()]); - } - - /** - * @see ICVSFolder#createFolder(String) - */ - public ICVSFolder getFolder(String name) throws CVSException { - if ((CURRENT_LOCAL_FOLDER.equals(name)) || ((CURRENT_LOCAL_FOLDER + SEPARATOR).equals(name))) - return this; - IPath path = new Path(name); - if(resource.getType()==IResource.ROOT && path.segmentCount()==1) { - return new EclipseFolder(((IWorkspaceRoot)resource).getProject(name)); - } else { - return new EclipseFolder(((IContainer)resource).getFolder(new Path(name))); - } - } - - /** - * @see ICVSFolder#createFile(String) - */ - public ICVSFile getFile(String name) throws CVSException { - return new EclipseFile(((IContainer)resource).getFile(new Path(name))); - } - - /** - * @see ICVSFolder#mkdir() - */ - public void mkdir() throws CVSException { - try { - if(resource.getType()==IResource.PROJECT) { - IProject project = (IProject)resource; - project.create(null); - project.open(null); - } else { - ((IFolder)resource).create(false /*don't force*/, true /*make local*/, null); - // We need to signal the creation to the synchronizer immediately because - // we may do additional CVS operations on the folder before the next delta - // occurs. - EclipseSynchronizer.getInstance().created(getIResource());; - } - } catch (CoreException e) { - throw CVSException.wrapException(resource, Policy.bind("EclipseFolder_problem_creating", resource.getFullPath().toString(), e.getStatus().getMessage()), e); //$NON-NLS-1$ - } - } - - /** - * @see ICVSResource#isFolder() - */ - public boolean isFolder() { - return true; - } - - /** - * @see ICVSFolder#acceptChildren(ICVSResourceVisitor) - */ - public void acceptChildren(ICVSResourceVisitor visitor) throws CVSException { - - // Visit files and then folders - ICVSResource[] subFiles = members(FILE_MEMBERS); - for (int i=0; i<subFiles.length; i++) { - subFiles[i].accept(visitor); - } - ICVSResource[] subFolders = members(FOLDER_MEMBERS); - for (int i=0; i<subFolders.length; i++) { - subFolders[i].accept(visitor); - } - } - - /** - * @see ICVSResource#accept(ICVSResourceVisitor) - */ - public void accept(ICVSResourceVisitor visitor) throws CVSException { - visitor.visitFolder(this); - } - - /** - * @see ICVSResource#accept(ICVSResourceVisitor, boolean) - */ - public void accept(ICVSResourceVisitor visitor, boolean recurse) throws CVSException { - visitor.visitFolder(this); - ICVSResource[] resources; - if (recurse) { - resources = members(ICVSFolder.ALL_MEMBERS); - } else { - resources = members(ICVSFolder.FILE_MEMBERS); - } - for (int i = 0; i < resources.length; i++) { - resources[i].accept(visitor, recurse); - } - } - - /** - * @see ICVSResource#getRemoteLocation(ICVSFolder) - */ - public String getRemoteLocation(ICVSFolder stopSearching) throws CVSException { - - if (getFolderSyncInfo() != null) { - return getFolderSyncInfo().getRemoteLocation(); - } - - ICVSFolder parent = getParent(); - if(parent!=null && !equals(stopSearching)) { - String parentLocation; - parentLocation = parent.getRemoteLocation(stopSearching); - if (parentLocation!=null) { - return parentLocation + SEPARATOR + getName(); - } - } - return null; - } - - /* - * @see ICVSFolder#getFolderInfo() - */ - public FolderSyncInfo getFolderSyncInfo() throws CVSException { - return EclipseSynchronizer.getInstance().getFolderSync((IContainer)resource); - } - - /* - * @see ICVSFolder#setFolderInfo(FolderSyncInfo) - */ - public void setFolderSyncInfo(final FolderSyncInfo folderInfo) throws CVSException { - // ignore folder sync on the root (i.e. CVSROOT/config/TopLevelAdmin=yes but we just ignore it) - if (resource.getType() == IResource.ROOT) return; - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - EclipseSynchronizer synchronizer = EclipseSynchronizer.getInstance(); - synchronizer.setFolderSync((IContainer)resource, folderInfo); - // the server won't add directories as sync info, therefore it must be done when - // a directory is shared with the repository. - byte[] newSyncBytes = new ResourceSyncInfo(getName()).getBytes(); - byte[] oldSyncBytes = getSyncBytes(); - // only set the bytes if the new differes from the old. - // this avoids unnecessary saving of sync files - if (oldSyncBytes == null || ! Util.equals(newSyncBytes, oldSyncBytes)) - setSyncBytes(newSyncBytes); - } - }, null); - - } - - /* - * @see ICVSFolder#isCVSFolder() - */ - public boolean isCVSFolder() throws CVSException { - return EclipseSynchronizer.getInstance().getFolderSync((IContainer)resource) != null; - } - - /* - * @see ICVSResource#unmanage() - */ - public void unmanage(IProgressMonitor monitor) throws CVSException { - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - recursiveUnmanage((IContainer) resource, Policy.subMonitorFor(monitor, 99)); - EclipseFolder.super.unmanage(Policy.subMonitorFor(monitor, 1)); - monitor.done(); - } - }, Policy.subMonitorFor(monitor, 99)); - } - - private static void recursiveUnmanage(IContainer container, IProgressMonitor monitor) throws CVSException { - try { - monitor.beginTask(null, 10); - monitor.subTask(container.getFullPath().toOSString()); - EclipseSynchronizer.getInstance().deleteFolderSync(container); - - IResource[] members = container.members(true); - for (int i = 0; i < members.length; i++) { - monitor.worked(1); - IResource resource = members[i]; - if (members[i].getType() != IResource.FILE) { - recursiveUnmanage((IContainer) resource, monitor); - } - } - } catch (CoreException e) { - } finally { - monitor.done(); - } - } - - /* - * @see ICVSResource#isIgnored() - */ - public boolean isIgnored() throws CVSException { - if(isCVSFolder()) { - return false; - } - return super.isIgnored(); - } - - /* - * @see ICVSFolder#getChild(String) - */ - public ICVSResource getChild(String namedPath) throws CVSException { - IPath path = new Path(namedPath); - if(path.segmentCount()==0) { - return this; - } - IResource child = ((IContainer)resource).findMember(path, true /* include phantoms */); - if(child!=null) { - if(child.getType()==IResource.FILE) { - return new EclipseFile((IFile)child); - } else { - return new EclipseFolder((IContainer)child); - } - } - return null; - } - - /* - * @see ICVSFolder#run(ICVSRunnable, IProgressMonitor) - */ - public void run(final ICVSRunnable job, IProgressMonitor monitor) throws CVSException { - final CVSException[] error = new CVSException[1]; - try { - ResourcesPlugin.getWorkspace().run(new IWorkspaceRunnable() { - public void run(IProgressMonitor monitor) throws CoreException { - try { - EclipseSynchronizer.getInstance().run(job, monitor); - } catch(CVSException e) { - error[0] = e; - } - } - }, monitor); - } catch(CoreException e) { - throw CVSException.wrapException(e); - } - if(error[0]!=null) { - throw error[0]; - } - } - - /** - * @see ICVSFolder#fetchChildren(IProgressMonitor) - */ - public ICVSResource[] fetchChildren(IProgressMonitor monitor) throws CVSException { - return members(FILE_MEMBERS | FOLDER_MEMBERS); - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResource#delete() - */ - public void delete() throws CVSException { - if (!exists()) return; - if (isCVSFolder()) { - EclipseSynchronizer.getInstance().prepareForDeletion((IContainer)getIResource()); - } - super.delete(); - } - - /** - * Assumption this is only called from decorator and isIgnored() is purposely - * ommited here for performance reasons. - */ - public boolean isModified(IProgressMonitor monitor) throws CVSException { - try { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(Policy.bind("EclipseFolder.isModifiedProgress", resource.getFullPath().toString()), 1000); //$NON-NLS-1$ - - IContainer container = (IContainer)getIResource(); - - // TODO: Added optimization to avoid loading sync info if possible - // This will place a modified indicator on non-cvs folders - // (i.e. the call to getModifiedState will cache a session property) - int state = EclipseSynchronizer.getInstance().getModificationState(getIResource()); - - boolean modified; - if (state == ICVSFile.UNKNOWN) { - - if (!isCVSFolder()) { - return container.exists(); - } - - // We have no cached info for the folder. We'll need to check directly, - // caching as go. This will recursively determined the modified state - // for all child resources until a modified child is found. - modified = calculateAndSaveChildModificationStates(monitor); - setModified(modified); - } else { - modified = (state == ICVSFile.DIRTY); - } - return modified; - } finally { - monitor.done(); - } - } - - public void handleModification(boolean forAddition) throws CVSException { - // For non-additions, we are only interested in sync info changes - if (isIgnored() || !forAddition) return; - - // the folder is an addition. - FolderSyncInfo info = getFolderSyncInfo(); - // if the folder has sync info, it was handled is setFolderInfo - // otherwise, flush the ancestors to recalculate - if (info == null) { - setModified(true); - } - } - - /** - * Determines the modification state of the receiver by examining it's children. - * This method may result in modification state being cached with the children but - * does not cache it for the receiver. - */ - private boolean calculateAndSaveChildModificationStates(IProgressMonitor monitor) throws CVSException { - IContainer container = (IContainer)getIResource(); - ICVSResource[] children = members(ALL_UNIGNORED_MEMBERS); - - for (int i = 0; i < children.length; i++) { - ICVSResource resource = children[i]; - if (resource.isModified(null)) { - // if a child resource is dirty consider the parent dirty as well, there - // is no need to continue checking other siblings. - return true; - } - monitor.worked(1); - } - - return false; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseResource.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseResource.java deleted file mode 100644 index 58d49659e..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseResource.java +++ /dev/null @@ -1,292 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.Team; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSRunnable; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * Represents handles to CVS resource on the local file system. Synchronization - * information is taken from the CVS subdirectories. - * - * @see LocalFolder - * @see LocalFile - */ -abstract class EclipseResource implements ICVSResource, Comparable { - - // The separator that must be used when creating CVS resource paths. Never use - // the platform default separator since it is not compatible with CVS resources. - protected static final String SEPARATOR = Session.SERVER_SEPARATOR; - protected static final String CURRENT_LOCAL_FOLDER = Session.CURRENT_LOCAL_FOLDER; - - /* - * The local resource represented by this handle - */ - IResource resource; - - /* - * Creates a CVS handle to the provided resource - */ - protected EclipseResource(IResource resource) { - Assert.isNotNull(resource); - this.resource = resource; - } - - /* - * Get the extention of the path of resource relative to the path of root - * - * @throws CVSException if root is not a root-folder of resource - */ - public String getRelativePath(ICVSFolder root) throws CVSException { - try { - EclipseResource rootFolder; - String result; - rootFolder = (EclipseResource)root; - result = Util.getRelativePath(rootFolder.getPath(), getPath()); - if (result.length() == 0) return CURRENT_LOCAL_FOLDER; - return result; - } catch (ClassCastException e) { - throw new CVSException(Policy.bind("EclipseResource.invalidResourceClass"), e); //$NON-NLS-1$ - } - } - - /* - * @see ICVSResource#delete() - */ - public void delete() throws CVSException { - try { - resource.delete(false /*force*/, null); - } catch(CoreException e) { - throw new CVSException(e.getStatus()); - } - } - - /* - * @see ICVSResource#exists() - */ - public boolean exists() { - return resource.exists(); - } - - /* - * Returns the parent folder of this resource of <code>null</code> if resource - * the resource. - * - * @see ICVSResource#getParent() - */ - public ICVSFolder getParent() { - IContainer parent = resource.getParent(); - if (parent==null) { - return null; - } - return new EclipseFolder(parent); - } - - /* - * @see ICVSResource#getName() - */ - public String getName() { - return resource.getName(); - } - - /* - * @see ICVSResource#isIgnored() - */ - public boolean isIgnored() throws CVSException { - // a managed resource is never ignored - if(isManaged() || resource.getType()==IResource.ROOT || resource.getType()==IResource.PROJECT) { - return false; - } - - // If the resource is a derived or linked resource, it is ignored - if (resource.isDerived() || resource.isLinked()) { - return true; - } - - // always ignore CVS - String name = getName(); - if (name.equals("CVS")) return true; //$NON-NLS-1$ - - // check the global ignores from Team - if (Team.isIgnoredHint(resource)) return true; - - // check ignore patterns from the .cvsignore file. - if(EclipseSynchronizer.getInstance().isIgnored(resource)) { - return true; - } - - // check the parent, if the parent is ignored or mapped to CVSROOT/Emptydir - // then this resource is ignored also - ICVSFolder parent = getParent(); - if(parent==null) return false; - if (parent.isIgnored()) return true; - FolderSyncInfo info = parent.getFolderSyncInfo(); - if (info == null) return false; - return info.getRepository().equals(FolderSyncInfo.VIRTUAL_DIRECTORY); - } - - /* - * @see ICVSResource#setIgnored() - */ - public void setIgnored() throws CVSException { - EclipseSynchronizer.getInstance().addIgnored(resource.getParent(), resource.getName()); - } - - /* - * @see ICVSResource#setIgnoredAs(String) - */ - public void setIgnoredAs(final String pattern) throws CVSException { - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - EclipseSynchronizer.getInstance().addIgnored(resource.getParent(), pattern); - } - }, null); - } - - /* - * @see ICVSResource#isManaged() - */ - public boolean isManaged() throws CVSException { - return isManaged(getSyncBytes()); - } - - /* - * Helper method that captures the sematics of isManaged given a ResourceSyncInfo - */ - public boolean isManaged(byte[] syncBytes) { - return syncBytes != null; - } - - /** - * Two ManagedResources are equal, if there cvsResources are - * equal (and that is, if the point to the same file) - */ - public boolean equals(Object obj) { - - if (!(obj instanceof EclipseResource)) { - return false; - } else { - return getPath().equals(((EclipseResource) obj).getPath()); - } - } - - /* - * @see ICVSResource#getPath() - */ - public String getPath() { - return resource.getFullPath().toString(); - } - - /* - * @see ICVSResource#isFolder() - */ - public boolean isFolder() { - return false; - } - - /* - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#getSyncBytes() - */ - public byte[] getSyncBytes() throws CVSException { - return EclipseSynchronizer.getInstance().getSyncBytes(getIResource()); - } - - /* - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#setSyncBytes(byte[]) - */ - public void setSyncBytes(byte[] syncBytes) throws CVSException { - if (getParent().isCVSFolder()) { - EclipseSynchronizer.getInstance().setSyncBytes(getIResource(), syncBytes); - } - } - - /* - * @see ICVSResource#getSyncInfo() - */ - public ResourceSyncInfo getSyncInfo() throws CVSException { - return EclipseSynchronizer.getInstance().getResourceSync(resource); - } - - /* - * Implement the hashcode on the underlying strings, like it is done in the equals. - */ - public int hashCode() { - return getPath().hashCode(); - } - - /* - * Give the pathname back - */ - public String toString() { - return getPath(); - } - - /* - * @see ICVSResource#unmanage() - */ - public void unmanage(IProgressMonitor monitor) throws CVSException { - EclipseSynchronizer.getInstance().deleteResourceSync(resource); - } - - /* - * @see Comparable#compareTo(Object) - */ - public int compareTo(Object arg0) { - EclipseResource other = (EclipseResource)arg0; - return resource.getFullPath().toString().compareTo(other.resource.getFullPath().toString()); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResource#getIResource() - */ - public IResource getIResource() { - return resource; - } - - /** - * Called by a resource change listener when a resource is changed or added. This allows - * CVS resources to adjust any internal state based on the change. - * - * @param forAddition modification is an addition - * @throws CVSException - */ - public abstract void handleModification(boolean forAddition) throws CVSException; - - /* - * Run method which obtains both the CVS synchronizer lock and the workspace - * lock - */ - protected abstract void run(final ICVSRunnable job, IProgressMonitor monitor) throws CVSException; - - /** - * Sets the modified status of the receiver. This is done to ensure that any - * cached state kept by it or its parents is updated properly. The invoked method - * (setDirtyIndicator) will adjust the parent dirty state if the modification - * state of the resource has changed. - */ - protected void setModified(boolean modified) throws CVSException { - EclipseSynchronizer.getInstance().setDirtyIndicator(getIResource(), modified); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseSynchronizer.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseSynchronizer.java deleted file mode 100644 index 96c58f66a..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/EclipseSynchronizer.java +++ /dev/null @@ -1,1470 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Set; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceStatus; -import org.eclipse.core.resources.IResourceVisitor; -import org.eclipse.core.resources.IWorkspaceRoot; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -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.Path; -import org.eclipse.core.runtime.Platform; -import org.eclipse.core.runtime.jobs.ILock; -import org.eclipse.core.runtime.jobs.ISchedulingRule; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSRunnable; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.syncinfo.BaserevInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.FileNameMatcher; -import org.eclipse.team.internal.ccvs.core.util.SyncFileWriter; - -/** - * A synchronizer is responsible for managing synchronization information for local - * CVS resources. - * - * This class is thread safe but only allows one thread to modify the cache at a time. It - * doesn't support fine grain locking on a resource basis. Lock ordering between the workspace - * lock and the synchronizer lock is guaranteed to be deterministic. That is, the workspace - * lock is *always* acquired before the synchronizer lock. This protects against possible - * deadlock cases where the synchronizer lock is acquired before a workspace lock. - * - * Special processing has been added for linked folders and their childen so - * that their CVS meta files are never read or written. - * - * @see ResourceSyncInfo - * @see FolderSyncInfo - */ -public class EclipseSynchronizer { - private static final String IS_DIRTY_INDICATOR = SyncInfoCache.IS_DIRTY_INDICATOR; - private static final String NOT_DIRTY_INDICATOR = SyncInfoCache.NOT_DIRTY_INDICATOR; - private static final String RECOMPUTE_INDICATOR = SyncInfoCache.RECOMPUTE_INDICATOR; - - // the cvs eclipse synchronizer is a singleton - private static EclipseSynchronizer instance; - - // track resources that have changed in a given operation - private ILock lock = Platform.getJobManager().newLock(); - - private Set changedResources = new HashSet(); - private Set changedFolders = new HashSet(); - - private SessionPropertySyncInfoCache sessionPropertyCache = new SessionPropertySyncInfoCache(); - private SynchronizerSyncInfoCache synchronizerCache = new SynchronizerSyncInfoCache(); - - /* - * Package private contructor to allow specialized subclass for handling folder deletions - */ - EclipseSynchronizer() { - } - - /** - * Returns the singleton instance of the synchronizer. - */ - public static EclipseSynchronizer getInstance() { - if(instance==null) { - instance = new EclipseSynchronizer(); - } - return instance; - } - - public SyncInfoCache getSyncInfoCacheFor(IResource resource) { - if (resource.exists()) { - return sessionPropertyCache; - } else { - return synchronizerCache; - } - } - - private boolean isValid(IResource resource) { - return resource.exists() || resource.isPhantom(); - } - - /** - * Sets the folder sync info for the specified folder. - * The folder must exist and must not be the workspace root. - * - * @param folder the folder - * @param info the folder sync info, must not be null - * @see #getFolderSync, #deleteFolderSync - */ - public void setFolderSync(IContainer folder, FolderSyncInfo info) throws CVSException { - Assert.isNotNull(info); // enforce the use of deleteFolderSync - // ignore folder sync on the root (i.e. CVSROOT/config/TopLevelAdmin=yes but we just ignore it) - if (folder.getType() == IResource.ROOT) return; - if (!isValid(folder)) { - throw new CVSException(IStatus.ERROR, CVSException.UNABLE, - Policy.bind("EclipseSynchronizer.ErrorSettingFolderSync", folder.getFullPath().toString())); //$NON-NLS-1$ - } - try { - beginOperation(folder, null); - // get the old info - FolderSyncInfo oldInfo = getFolderSync(folder); - // set folder sync and notify - getSyncInfoCacheFor(folder).setCachedFolderSync(folder, info); - // if the sync info changed from null, we may need to adjust the ancestors - if (oldInfo == null) { - adjustDirtyStateRecursively(folder, RECOMPUTE_INDICATOR); - } - changedFolders.add(folder); - } finally { - endOperation(null); - } - } - - /** - * Gets the folder sync info for the specified folder. - * - * @param folder the folder - * @return the folder sync info associated with the folder, or null if none. - * @see #setFolderSync, #deleteFolderSync - */ - public FolderSyncInfo getFolderSync(IContainer folder) throws CVSException { - if (folder.getType() == IResource.ROOT || !isValid(folder)) return null; - try { - beginOperation(folder, null); - cacheFolderSync(folder); - return getSyncInfoCacheFor(folder).getCachedFolderSync(folder); - } finally { - endOperation(null); - } - } - - /** - * Deletes the folder sync for the specified folder and the resource sync - * for all of its children. Does not recurse. - * - * @param folder the folder - * @see #getFolderSync, #setFolderSync - */ - public void deleteFolderSync(IContainer folder) throws CVSException { - if (folder.getType() == IResource.ROOT || !isValid(folder)) return; - try { - beginOperation(folder, null); - // iterate over all children with sync info and prepare notifications - // this is done first since deleting the folder sync may remove a phantom - cacheResourceSyncForChildren(folder); - IResource[] children = folder.members(true); - for (int i = 0; i < children.length; i++) { - IResource resource = children[i]; - changedResources.add(resource); - // delete resource sync for all children - getSyncInfoCacheFor(resource).setCachedSyncBytes(resource, null); - } - // delete folder sync - getSyncInfoCacheFor(folder).setCachedFolderSync(folder, null); - changedFolders.add(folder); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - endOperation(null); - } - } - - /** - * Sets the resource sync info for the specified resource. - * The parent folder must exist and must not be the workspace root. - * - * @param resource the resource - * @param info the resource sync info, must not be null - * @see #getResourceSync, #deleteResourceSync - */ - public void setResourceSync(IResource resource, ResourceSyncInfo info) throws CVSException { - Assert.isNotNull(info); // enforce the use of deleteResourceSync - IContainer parent = resource.getParent(); - if (parent == null || parent.getType() == IResource.ROOT || !isValid(parent)) { - throw new CVSException(IStatus.ERROR, CVSException.UNABLE, - Policy.bind("EclipseSynchronizer.ErrorSettingResourceSync", resource.getFullPath().toString())); //$NON-NLS-1$ - } - try { - beginOperation(resource, null); - // cache resource sync for siblings, set for self, then notify - cacheResourceSyncForChildren(parent); - setCachedResourceSync(resource, info); - changedResources.add(resource); - } finally { - endOperation(null); - } - } - - /** - * Gets the resource sync info for the specified folder. - * - * @param resource the resource - * @return the resource sync info associated with the resource, or null if none. - * @see #setResourceSync, #deleteResourceSync - */ - public ResourceSyncInfo getResourceSync(IResource resource) throws CVSException { - byte[] info = getSyncBytes(resource); - if (info == null) return null; - return new ResourceSyncInfo(info); - } - - /** - * Gets the resource sync info for the specified folder. - * - * @param resource the resource - * @return the resource sync info associated with the resource, or null if none. - * @see #setResourceSync, #deleteResourceSync - */ - public byte[] getSyncBytes(IResource resource) throws CVSException { - IContainer parent = resource.getParent(); - if (parent == null || parent.getType() == IResource.ROOT || !isValid(parent)) return null; - try { - beginOperation(resource, null); - // cache resource sync for siblings, then return for self - try { - cacheResourceSyncForChildren(parent); - } catch (CVSException e) { - if (e.getStatus().getCode() == IResourceStatus.WORKSPACE_LOCKED) { - // This can occur if the resource sync is loaded during the POST_CHANGE delta phase. - // We will resort to loading the sync info for the requested resource from disk - return getSyncBytesFromDisk(resource); - } else { - throw e; - } - } - return getCachedSyncBytes(resource); - } finally { - endOperation(null); - } - } - - /** - * Sets the resource sync info for the specified resource. - * The parent folder must exist and must not be the workspace root. - * - * @param resource the resource - * @param info the resource sync info, must not be null - * @see #getResourceSync, #deleteResourceSync - */ - public void setSyncBytes(IResource resource, byte[] syncBytes) throws CVSException { - Assert.isNotNull(syncBytes); // enforce the use of deleteResourceSync - IContainer parent = resource.getParent(); - if (parent == null || parent.getType() == IResource.ROOT || !isValid(parent)) { - throw new CVSException(IStatus.ERROR, CVSException.UNABLE, - Policy.bind("EclipseSynchronizer.ErrorSettingResourceSync", resource.getFullPath().toString())); //$NON-NLS-1$ - } - try { - beginOperation(resource, null); - // cache resource sync for siblings, set for self, then notify - cacheResourceSyncForChildren(parent); - setCachedSyncBytes(resource, syncBytes); - changedResources.add(resource); - } finally { - endOperation(null); - } - } - - /** - * Deletes the resource sync info for the specified resource, if it exists. - * - * @param resource the resource - * @see #getResourceSync, #setResourceSync - */ - public void deleteResourceSync(IResource resource) throws CVSException { - IContainer parent = resource.getParent(); - if (parent == null || parent.getType() == IResource.ROOT || !isValid(parent)) return; - try { - beginOperation(resource, null); - // cache resource sync for siblings, delete for self, then notify - cacheResourceSyncForChildren(parent); - if (getCachedSyncBytes(resource) != null) { // avoid redundant notifications - setCachedSyncBytes(resource, null); - clearDirtyIndicator(resource); - changedResources.add(resource); - } - } finally { - endOperation(null); - } - } - - /** - * @param resource - */ - private void clearDirtyIndicator(IResource resource) throws CVSException { - getSyncInfoCacheFor(resource).flushDirtyCache(resource); - adjustDirtyStateRecursively(resource.getParent(), RECOMPUTE_INDICATOR); - } - - /** - * Gets the array of ignore patterns for the specified folder. - * - * @param folder the folder - * @return the patterns, or an empty array if none - * @see #addIgnored - */ - public boolean isIgnored(IResource resource) throws CVSException { - if (resource.getType() == IResource.ROOT || - resource.getType() == IResource.PROJECT || - ! resource.exists()) { - return false; - } - try { - beginOperation(resource, null); - FileNameMatcher matcher = cacheFolderIgnores(resource.getParent()); - return matcher.match(resource.getName()); - } finally { - endOperation(null); - } - } - - /** - * Adds a pattern to the set of ignores for the specified folder. - * - * @param folder the folder - * @param pattern the pattern - */ - public void addIgnored(IContainer folder, String pattern) throws CVSException { - if (folder.getType() == IResource.ROOT || ! folder.exists()) { - throw new CVSException(IStatus.ERROR, CVSException.UNABLE, - Policy.bind("EclipseSynchronizer.ErrorSettingIgnorePattern", folder.getFullPath().toString())); //$NON-NLS-1$ - } - try { - beginOperation(folder, null); - String[] ignores = SyncFileWriter.readCVSIgnoreEntries(folder); - if (ignores != null) { - // verify that the pattern has not already been added - for (int i = 0; i < ignores.length; i++) { - if (ignores[i].equals(pattern)) return; - } - // add the pattern - String[] oldIgnores = ignores; - ignores = new String[oldIgnores.length + 1]; - System.arraycopy(oldIgnores, 0, ignores, 0, oldIgnores.length); - ignores[oldIgnores.length] = pattern; - } else { - ignores = new String[] { pattern }; - } - setCachedFolderIgnores(folder, ignores); - SyncFileWriter.writeCVSIgnoreEntries(folder, ignores); - // broadcast changes to unmanaged children - they are the only candidates for being ignored - List possibleIgnores = new ArrayList(); - accumulateNonManagedChildren(folder, possibleIgnores); - CVSProviderPlugin.broadcastSyncInfoChanges((IResource[])possibleIgnores.toArray(new IResource[possibleIgnores.size()])); - } finally { - endOperation(null); - } - } - - /** - * Returns the members of this folder including deleted resources with sync info, - * but excluding special resources such as CVS subdirectories. - * - * @param folder the container to list - * @return the array of members - */ - public IResource[] members(IContainer folder) throws CVSException { - if (! isValid(folder)) return new IResource[0]; - try { - beginOperation(folder, null); - if (folder.getType() != IResource.ROOT) { - // ensure that the sync info is cached so any required phantoms are created - cacheResourceSyncForChildren(folder); - } - return folder.members(true); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - endOperation(null); - } - } - - /** - * Begins a batch of operations. - * - * @param monitor the progress monitor, may be null - */ - public void beginOperation(IResource resource, IProgressMonitor monitor) throws CVSException { - // ensure locks are acquired in the same order: workspace then cvs - // The scheduling rule is either the project or the resource's parent - ISchedulingRule rule; - if (resource.getType() == IResource.PROJECT || resource.getType() == IResource.ROOT) { - rule = resource; - } else { - rule = resource.getParent(); - } - Platform.getJobManager().beginRule(rule); - lock.acquire(); - - if (lock.getDepth() == 1) { - prepareCache(monitor); - } - } - - /** - * Ends a batch of operations. Pending changes are committed only when - * the number of calls to endOperation() balances those to beginOperation(). - * <p> - * Progress cancellation is ignored while writting the cache to disk. This - * is to ensure cache to disk consistency. - * </p> - * - * @param monitor the progress monitor, may be null - * @exception CVSException with a status with code <code>COMMITTING_SYNC_INFO_FAILED</code> - * if all the CVS sync information could not be written to disk. - */ - public void endOperation(IProgressMonitor monitor) throws CVSException { - try { - IStatus status = SyncInfoCache.STATUS_OK; - if (lock.getDepth() == 1) { - status = commitCache(monitor); - } - if (!status.isOK()) { - throw new CVSException(status); - } - } finally { - // ensure locks are released in the same order: cvs then workspace - lock.release(); - Platform.getJobManager().endRule(); - } - } - - /** - * Flushes unwritten sync information to disk. - * <p> - * Recursively commits unwritten sync information for all resources - * below the root, and optionally purges the cached data from memory - * so that the next time it is accessed it will be retrieved from disk. - * May flush more sync information than strictly needed, but never less. - * </p> - * <p> - * Will throw a CVS Exception with a status with code = CVSStatus.DELETION_FAILED - * if the flush could not perform CVS folder deletions. In this case, all other - * aspects of the operation succeeded. - * </p> - * - * @param root the root of the subtree to flush - * @param purgeCache if true, purges the cache from memory as well - * @param deep purge sync from child folders - * @param monitor the progress monitor, may be null - */ - public void flush(IContainer root, boolean purgeCache, boolean deep, IProgressMonitor monitor) throws CVSException { - // flush unwritten sync info to disk - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 10); - try { - beginOperation(root, Policy.subMonitorFor(monitor, 1)); - - IStatus status = commitCache(Policy.subMonitorFor(monitor, 7)); - - // purge from memory too if we were asked to - if (purgeCache) { - sessionPropertyCache.purgeCache(root, deep); - } - - // prepare for the operation again if we cut the last one short - prepareCache(Policy.subMonitorFor(monitor, 1)); - - if (!status.isOK()) { - throw new CVSException(status); - } - } finally { - endOperation(Policy.subMonitorFor(monitor, 1)); - monitor.done(); - } - } - - public void deconfigure(final IProject project, IProgressMonitor monitor) throws CVSException { - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - flush(project, true, true, monitor); - - // forget about pruned folders however the top level pruned folder will have resource sync (e.g. - // a line in the Entry file). As a result the folder is managed but is not a CVS folder. - synchronizerCache.purgeCache(project, true); - } - }, monitor); - } - - private void purgeCache(IResource resource, boolean deep) throws CVSException { - sessionPropertyCache.purgeResourceSyncCache(resource); - if (resource.getType() != IResource.FILE) { - sessionPropertyCache.purgeCache((IContainer)resource, deep); - } - } - - /** - * Called to notify the synchronizer that meta files have changed on disk, outside - * of the workbench. The cache will be flushed for this folder and it's immediate - * children and appropriate state change events are broadcasts to state change - * listeners. - */ - public void syncFilesChanged(IContainer[] roots) throws CVSException { - try { - for (int i = 0; i < roots.length; i++) { - IContainer root = roots[i]; - flush(root, true, false /*don't flush children*/, null); - List changedPeers = new ArrayList(); - changedPeers.add(root); - changedPeers.addAll(Arrays.asList(root.members())); - IResource[] resources = (IResource[]) changedPeers.toArray(new IResource[changedPeers.size()]); - CVSProviderPlugin.broadcastSyncInfoChanges(resources); - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * The folder is about to be deleted (including its CVS subfolder). - * Take any appropriate action to remember the CVS information. - */ - public void prepareForDeletion(IResource resource) throws CVSException { - if (!resource.exists()) return; - try { - beginOperation(resource, null); - // Flush the dirty info for the resource and it's ancestors. - // Although we could be smarter, we need to do this because the - // deletion may fail. - adjustDirtyStateRecursively(resource, RECOMPUTE_INDICATOR); - if (resource.getType() == IResource.FILE) { - byte[] syncBytes = getSyncBytes(resource); - if (syncBytes != null) { - if (!ResourceSyncInfo.isAddition(syncBytes)) { - syncBytes = convertToDeletion(syncBytes); - synchronizerCache.setCachedSyncBytes(resource, syncBytes); - } - changedResources.add(resource); - } - } else { - IContainer container = (IContainer)resource; - if (container.getType() == IResource.PROJECT) { - synchronizerCache.flush((IProject)container); - } else { - // Move the folder sync info into phantom space - FolderSyncInfo info = getFolderSync(container); - if (info == null) return; - synchronizerCache.setCachedFolderSync(container, info); - changedFolders.add(container); - // move the resource sync as well - byte[] syncBytes = getSyncBytes(resource); - synchronizerCache.setCachedSyncBytes(resource, syncBytes); - } - } - } finally { - endOperation(null); - } - } - - /** - * The resource has been deleted. Make sure any cached state is cleared. - * This is needed because the move/delete hook is not invoked in all situations - * (e.g. external deletion). - * - * @param resource - * @throws CVSException - */ - protected void handleDeleted(IResource resource) throws CVSException { - if (resource.exists()) return; - try { - beginOperation(resource, null); - adjustDirtyStateRecursively(resource, RECOMPUTE_INDICATOR); - } finally { - endOperation(null); - } - } - - /** - * Prepare for a move or delete within the move/delete hook by moving the - * sync info into phantom space and flushing the session properties cache. - * This will allow sync info for deletions to be maintained in the source - * location and sync info at the destination to be preserved as well. - * - * @param resource - * @param monitor - * @throws CVSException - */ - public void prepareForMoveDelete(IResource resource, IProgressMonitor monitor) throws CVSException { - // Move sync info to phantom space for the resource and all it's children - try { - resource.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - try { - prepareForDeletion(resource); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - throw new CoreException(e.getStatus()); - } - return true; - } - }); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - // purge the sync info to clear the session properties - purgeCache(resource, true); - } - - /** - * This method is used to ensure that the sync info for a resource is moved - * from the Phantom cache to the Session property cache. - * - * @param resource - * @throws CVSException - */ - public void created(IResource resource) throws CVSException { - if (resource.getType() == IResource.FILE) { - created((IFile)resource); - } else if (resource.getType() == IResource.FOLDER) { - created((IFolder)resource); - } - } - - /** - * Notify the receiver that a folder has been created. - * Any existing phantom sync info will be moved - * - * @param folder the folder that has been created - */ - private void created(IFolder folder) throws CVSException { - try { - // set the dirty count using what was cached in the phantom it - beginOperation(folder, null); - FolderSyncInfo folderInfo = synchronizerCache.getCachedFolderSync(folder); - byte[] syncBytes = synchronizerCache.getCachedSyncBytes(folder); - if (folderInfo != null && syncBytes != null) { - if (folder.getFolder(SyncFileWriter.CVS_DIRNAME).exists()) { - // There is already a CVS subdirectory which indicates that - // either the folder was recreated by an external tool or that - // a folder with CVS information was copied from another location. - // To know the difference, we need to compare the folder sync info. - // If they are mapped to the same root and repository then just - // purge the phantom info. Otherwise, keep the original sync info. - - // Get the new folder sync info - FolderSyncInfo newFolderInfo = getFolderSync(folder); - if (newFolderInfo.getRoot().equals(folderInfo.getRoot()) - && newFolderInfo.getRepository().equals(folderInfo.getRepository())) { - // The folder is the same so use what is on disk - return; - } - - // The folder is mapped to a different location. - // Purge new resource sync before restoring from phantom - ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor(folder); - ICVSResource[] children = cvsFolder.members(ICVSFolder.MANAGED_MEMBERS); - for (int i = 0; i < children.length; i++) { - ICVSResource resource = children[i]; - deleteResourceSync(resource.getIResource()); - } - } - - // set the sync info using what was cached in the phantom - setFolderSync(folder, folderInfo); - setCachedSyncBytes(folder, syncBytes); - } - } finally { - try { - endOperation(null); - } finally { - synchronizerCache.flush(folder); - } - } - } - - /** - * Notify the receiver that a file has been created. Any existing phantom - * sync info will be moved - * - * @param file the file that has been created - */ - private void created(IFile file) throws CVSException { - try { - // set the dirty count using what was cached in the phantom it - beginOperation(file, null); - byte[] syncBytes = synchronizerCache.getCachedSyncBytes(file); - if (syncBytes == null) return; - byte[] newBytes = getSyncBytes(file); - if (newBytes == null) { - // only move the sync info if there is no new sync info - setSyncBytes(file, convertFromDeletion(syncBytes)); - } - } finally { - try { - endOperation(null); - } finally { - synchronizerCache.setCachedSyncBytes(file, null); - } - } - } - - /** - * If not already cached, loads and caches the resource sync for the children of the container. - * Folder must exist and must not be the workspace root. - * - * @param container the container - */ - private void cacheResourceSyncForChildren(IContainer container) throws CVSException { - // don't try to load if the information is already cached - if (! getSyncInfoCacheFor(container).isResourceSyncInfoCached(container)) { - // load the sync info from disk - byte[][] infos; - // do not load the sync info for resources that are linked - if (isLinkedResource(container)) { - infos = null; - } else { - infos = SyncFileWriter.readAllResourceSync(container); - } - if (infos != null) { - for (int i = 0; i < infos.length; i++) { - byte[] syncBytes = infos[i]; - IPath name = new Path(getName(syncBytes)); - IResource resource; - if (isFolder(syncBytes)) { - resource = container.getFolder(name); - } else { - resource = container.getFile(name); - } - getSyncInfoCacheFor(resource).setCachedSyncBytes(resource, syncBytes); - } - } - getSyncInfoCacheFor(container).setResourceSyncInfoCached(container); - } - } - - /** - * If not already cached, loads and caches the folder sync for the - * container. Folder must exist and must not be the workspace root. - * - * @param container the container - */ - private void cacheFolderSync(IContainer container) throws CVSException { - // don't try to load if the information is already cached - if (! getSyncInfoCacheFor(container).isFolderSyncInfoCached(container)) { - // load the sync info from disk - FolderSyncInfo info; - // do not load the sync info for resources that are linked - if (isLinkedResource(container)) { - info = null; - } else { - info = SyncFileWriter.readFolderSync(container); - } - getSyncInfoCacheFor(container).setCachedFolderSync(container, info); - } - } - - private boolean isLinkedResource(IResource resource) { - return CVSWorkspaceRoot.isLinkedResource(resource); - } - - /** - * Load the sync info for the given resource from disk - * @param resource - * @return byte[] - */ - private byte[] getSyncBytesFromDisk(IResource resource) throws CVSException { - byte[][] infos = SyncFileWriter.readAllResourceSync(resource.getParent()); - if (infos == null) return null; - for (int i = 0; i < infos.length; i++) { - byte[] syncBytes = infos[i]; - if (resource.getName().equals(getName(syncBytes))) { - return syncBytes; - } - } - return null; - } - - /** - * Prepares the cache for a series of operations. - * - * @param monitor the progress monitor, may be null - */ - private void prepareCache(IProgressMonitor monitor) throws CVSException { - } - - /** - * Commits the cache after a series of operations. - * - * Will return STATUS_OK unless there were problems writting sync - * information to disk. If an error occurs a multistatus is returned - * with the list of reasons for the failures. Failures are recovered, - * and all changed resources are given a chance to be written to disk. - * - * @param monitor the progress monitor, may be null - */ - private IStatus commitCache(IProgressMonitor monitor) { - if (changedFolders.isEmpty() && changedResources.isEmpty()) { - return SyncInfoCache.STATUS_OK; - } - List errors = new ArrayList(); - try { - /*** prepare operation ***/ - // find parents of changed resources - Set dirtyParents = new HashSet(); - for(Iterator it = changedResources.iterator(); it.hasNext();) { - IResource resource = (IResource) it.next(); - IContainer folder = resource.getParent(); - dirtyParents.add(folder); - } - - monitor = Policy.monitorFor(monitor); - int numDirty = dirtyParents.size(); - int numResources = changedFolders.size() + numDirty; - monitor.beginTask(null, numResources); - if(monitor.isCanceled()) { - monitor.subTask(Policy.bind("EclipseSynchronizer.UpdatingSyncEndOperationCancelled")); //$NON-NLS-1$ - } else { - monitor.subTask(Policy.bind("EclipseSynchronizer.UpdatingSyncEndOperation")); //$NON-NLS-1$ - } - - /*** write sync info to disk ***/ - // folder sync info changes - for(Iterator it = changedFolders.iterator(); it.hasNext();) { - IContainer folder = (IContainer) it.next(); - if (folder.exists() && folder.getType() != IResource.ROOT) { - try { - FolderSyncInfo info = sessionPropertyCache.getCachedFolderSync(folder); - // Do not write the folder sync for linked resources - if (info == null) { - // deleted folder sync info since we loaded it - // (but don't overwrite the sync info for linked folders - if (!isLinkedResource(folder)) - SyncFileWriter.deleteFolderSync(folder); - dirtyParents.remove(folder); - } else { - // modified or created new folder sync info since we loaded it - SyncFileWriter.writeFolderSync(folder, info); - } - } catch(CVSException e) { - try { - sessionPropertyCache.purgeCache(folder, true /* deep */); - } catch(CVSException pe) { - errors.add(pe.getStatus()); - } - errors.add(e.getStatus()); - } - } - monitor.worked(1); - } - - // update progress for parents we will skip because they were deleted - monitor.worked(numDirty - dirtyParents.size()); - - // resource sync info changes - for (Iterator it = dirtyParents.iterator(); it.hasNext();) { - IContainer folder = (IContainer) it.next(); - if (folder.exists() && folder.getType() != IResource.ROOT) { - // write sync info for all children in one go - try { - List infos = new ArrayList(); - IResource[] children = folder.members(true); - for (int i = 0; i < children.length; i++) { - IResource resource = children[i]; - byte[] syncBytes = getSyncBytes(resource); - if (syncBytes != null) { - infos.add(syncBytes); - } - } - // do not overwrite the sync info for linked resources - if (infos.size() > 0 || !isLinkedResource(folder)) - SyncFileWriter.writeAllResourceSync(folder, - (byte[][]) infos.toArray(new byte[infos.size()][])); - } catch(CVSException e) { - try { - sessionPropertyCache.purgeCache(folder, false /* depth 1 */); - } catch(CVSException pe) { - errors.add(pe.getStatus()); - } - errors.add(e.getStatus()); - } catch (CoreException e) { - try { - sessionPropertyCache.purgeCache(folder, false /* depth 1 */); - } catch(CVSException pe) { - errors.add(pe.getStatus()); - } - errors.add(e.getStatus()); - } - } - monitor.worked(1); - } - - /*** broadcast events ***/ - monitor.subTask(Policy.bind("EclipseSynchronizer.NotifyingListeners")); //$NON-NLS-1$ - changedResources.addAll(changedFolders); - changedResources.addAll(dirtyParents); - IResource[] resources = (IResource[]) changedResources.toArray( - new IResource[changedResources.size()]); - broadcastResourceStateChanges(resources); - changedResources.clear(); - changedFolders.clear(); - if ( ! errors.isEmpty()) { - MultiStatus status = new MultiStatus(CVSProviderPlugin.ID, - CVSStatus.COMMITTING_SYNC_INFO_FAILED, - Policy.bind("EclipseSynchronizer.ErrorCommitting"), //$NON-NLS-1$ - null); - for (int i = 0; i < errors.size(); i++) { - status.merge((IStatus)errors.get(i)); - } - return status; - } - return SyncInfoCache.STATUS_OK; - } finally { - monitor.done(); - } - } - - /** - * Broadcasts the resource state changes for the given resources to CVS Provider Plugin - */ - void broadcastResourceStateChanges(IResource[] resources) { - if (resources.length > 0) { - CVSProviderPlugin.broadcastSyncInfoChanges(resources); - } - } - - /** - * Returns the resource sync info for the resource; null if none. - * Parent must exist and must not be the workspace root. - * The resource sync info for the children of the parent container MUST ALREADY BE CACHED. - * - * @param resource the resource - * @return the resource sync info for the resource, or null - * @see #cacheResourceSyncForChildren - */ - private byte[] getCachedSyncBytes(IResource resource) throws CVSException { - return getSyncInfoCacheFor(resource).getCachedSyncBytes(resource); - } - - /** - * Returns the resource sync info for the resource; null if none. - * Parent must exist and must not be the workspace root. - * The resource sync info for the children of the parent container MUST ALREADY BE CACHED. - * - * @param resource the resource - * @return the resource sync info for the resource, or null - * @see #cacheResourceSyncForChildren - */ - private void setCachedSyncBytes(IResource resource, byte[] syncBytes) throws CVSException { - getSyncInfoCacheFor(resource).setCachedSyncBytes(resource, syncBytes); - changedResources.add(resource); - } - - /** - * Sets the resource sync info for the resource; if null, deletes it. Parent - * must exist and must not be the workspace root. The resource sync info for - * the children of the parent container MUST ALREADY BE CACHED. - * - * @param resource the resource - * @param info the new resource sync info - * @see #cacheResourceSyncForChildren - */ - private void setCachedResourceSync(IResource resource, ResourceSyncInfo info) throws CVSException { - //todo - byte[] syncBytes = null; - if (info != null) syncBytes = info.getBytes(); - getSyncInfoCacheFor(resource).setCachedSyncBytes(resource, syncBytes); - } - - /** - * If not already cached, loads and caches the folder ignores sync for the container. - * Folder must exist and must not be the workspace root. - * - * @param container the container - * @return the folder ignore patterns, or an empty array if none - */ - private FileNameMatcher cacheFolderIgnores(IContainer container) throws CVSException { - return sessionPropertyCache.cacheFolderIgnores(container); - } - - /** - * Sets the array of folder ignore patterns for the container, must not be null. - * Folder must exist and must not be the workspace root. - * - * @param container the container - * @param ignores the array of ignore patterns - */ - private void setCachedFolderIgnores(IContainer container, String[] ignores) throws CVSException { - sessionPropertyCache.setCachedFolderIgnores(container, ignores); - } - - /** - * Recursively adds to the possibleIgnores list all children of the given - * folder that can be ignored. - * - * @param folder the folder to be searched - * @param possibleIgnores the list of IResources that can be ignored - */ - private void accumulateNonManagedChildren(IContainer folder, List possibleIgnores) throws CVSException { - try { - cacheResourceSyncForChildren(folder); - IResource[] children = folder.members(); - List folders = new ArrayList(); - // deal with all files first and then folders to be otimized for caching scheme - for (int i = 0; i < children.length; i++) { - IResource child = children[i]; - if(getCachedSyncBytes(child)==null) { - possibleIgnores.add(child); - } - if(child.getType()!=IResource.FILE) { - folders.add(child); - } - } - for (Iterator iter = folders.iterator(); iter.hasNext();) { - IContainer child = (IContainer) iter.next(); - accumulateNonManagedChildren(child, possibleIgnores); - } - } catch(CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * Add the entry to the CVS/Notify file. We are not initially concerned with efficiency - * since edit/unedit are typically issued on a small set of files. - * - * XXX If there was a previous notify entry for the resource, it is replaced. This is - * probably not the proper behavior (see EclipseFile). - * - * A value of null for info indicates that any entry for the given - * resource is to be removed from the Notify file. - * - * @param resource - * @param info - */ - public void setNotifyInfo(IResource resource, NotifyInfo info) throws CVSException { - NotifyInfo[] infos = SyncFileWriter.readAllNotifyInfo(resource.getParent()); - if (infos == null) { - // if the file is empty and we are removing an entry, just return; - if (info == null) return; - infos = new NotifyInfo[] { info }; - } else { - Map infoMap = new HashMap(); - for (int i = 0; i < infos.length; i++) { - NotifyInfo notifyInfo = infos[i]; - infoMap.put(infos[i].getName(), infos[i]); - } - if (info == null) { - // if the info is null, remove the entry - infoMap.remove(resource.getName()); - } else { - // add the new entry to the list - infoMap.put(info.getName(), info); - } - - NotifyInfo[] newInfos = new NotifyInfo[infoMap.size()]; - int i = 0; - for (Iterator iter = infoMap.values().iterator(); iter.hasNext();) { - newInfos[i++] = (NotifyInfo) iter.next(); - } - infos = newInfos; - } - SyncFileWriter.writeAllNotifyInfo(resource.getParent(), infos); - } - - /** - * Method getNotifyInfo. - * @param resource - * @return NotifyInfo - */ - public NotifyInfo getNotifyInfo(IResource resource) throws CVSException { - NotifyInfo[] infos = SyncFileWriter.readAllNotifyInfo(resource.getParent()); - if (infos == null) return null; - for (int i = 0; i < infos.length; i++) { - NotifyInfo notifyInfo = infos[i]; - if (notifyInfo.getName().equals(resource.getName())) { - return notifyInfo; - } - } - return null; - } - - /** - * Method deleteNotifyInfo. - * @param resource - */ - public void deleteNotifyInfo(IResource resource) throws CVSException { - NotifyInfo[] infos = SyncFileWriter.readAllNotifyInfo(resource.getParent()); - if (infos == null) return; - Map infoMap = new HashMap(); - for (int i = 0; i < infos.length; i++) { - NotifyInfo notifyInfo = infos[i]; - infoMap.put(infos[i].getName(), infos[i]); - } - infoMap.remove(resource.getName()); - NotifyInfo[] newInfos = new NotifyInfo[infoMap.size()]; - int i = 0; - for (Iterator iter = infoMap.values().iterator(); iter.hasNext();) { - newInfos[i++] = (NotifyInfo) iter.next(); - } - SyncFileWriter.writeAllNotifyInfo(resource.getParent(), newInfos); - } - - /** - * Add the entry to the CVS/Baserev file. We are not initially concerned - * with efficiency since edit/unedit are typically issued on a small set of - * files. - * - * XXX If there was a previous notify entry for the resource, it is replaced. This is - * probably not the proper behavior (see EclipseFile). - * - * @param resource - * @param info - */ - public void setBaserevInfo(IResource resource, BaserevInfo info) throws CVSException { - BaserevInfo[] infos = SyncFileWriter.readAllBaserevInfo(resource.getParent()); - if (infos == null) { - infos = new BaserevInfo[] { info }; - } else { - Map infoMap = new HashMap(); - for (int i = 0; i < infos.length; i++) { - infoMap.put(infos[i].getName(), infos[i]); - } - infoMap.put(info.getName(), info); - BaserevInfo[] newInfos = new BaserevInfo[infoMap.size()]; - int i = 0; - for (Iterator iter = infoMap.values().iterator(); iter.hasNext();) { - newInfos[i++] = (BaserevInfo) iter.next(); - } - infos = newInfos; - } - SyncFileWriter.writeAllBaserevInfo(resource.getParent(), infos); - } - - /** - * Method getBaserevInfo. - * @param resource - * @return BaserevInfo - */ - public BaserevInfo getBaserevInfo(IResource resource) throws CVSException { - BaserevInfo[] infos = SyncFileWriter.readAllBaserevInfo(resource.getParent()); - if (infos == null) return null; - for (int i = 0; i < infos.length; i++) { - BaserevInfo info = infos[i]; - if (info.getName().equals(resource.getName())) { - return info; - } - } - return null; - } - - /** - * Method deleteNotifyInfo. - * @param resource - */ - public void deleteBaserevInfo(IResource resource) throws CVSException { - BaserevInfo[] infos = SyncFileWriter.readAllBaserevInfo(resource.getParent()); - if (infos == null) return; - Map infoMap = new HashMap(); - for (int i = 0; i < infos.length; i++) { - infoMap.put(infos[i].getName(), infos[i]); - } - infoMap.remove(resource.getName()); - BaserevInfo[] newInfos = new BaserevInfo[infoMap.size()]; - int i = 0; - for (Iterator iter = infoMap.values().iterator(); iter.hasNext();) { - newInfos[i++] = (BaserevInfo) iter.next(); - } - SyncFileWriter.writeAllBaserevInfo(resource.getParent(), newInfos); - } - - public void copyFileToBaseDirectory(final IFile file, IProgressMonitor monitor) throws CVSException { - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - ResourceSyncInfo info = getResourceSync(file); - // The file must exist remotely and locally - if (info == null || info.isAdded() || info.isDeleted()) - return; - SyncFileWriter.writeFileToBaseDirectory(file, monitor); - changedResources.add(file); - } - }, monitor); - } - - public void restoreFileFromBaseDirectory(final IFile file, IProgressMonitor monitor) throws CVSException { - run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - ResourceSyncInfo info = getResourceSync(file); - // The file must exist remotely - if (info == null || info.isAdded()) - return; - SyncFileWriter.restoreFileFromBaseDirectory(file, monitor); - changedResources.add(file); - } - }, monitor); - } - - public void deleteFileFromBaseDirectory(final IFile file, IProgressMonitor monitor) throws CVSException { - ResourceSyncInfo info = getResourceSync(file); - // The file must exist remotely - if (info == null || info.isAdded()) - return; - SyncFileWriter.deleteFileFromBaseDirectory(file, monitor); - } - - /** - * Method isSyncInfoLoaded returns true if all the sync info for the - * provided resources is loaded into the internal cache. - * - * @param resources - * @param i - * @return boolean - */ - public boolean isSyncInfoLoaded(IResource[] resources, int depth) throws CVSException { - // get the folders involved - IContainer[] folders = getParentFolders(resources, depth); - // for all folders that have a CVS folder, ensure the sync info is cached - for (int i = 0; i < folders.length; i++) { - IContainer parent = folders[i]; - if (!getSyncInfoCacheFor(parent).isSyncInfoLoaded(parent)) { - return false; - } - } - return true; - } - - /** - * Method ensureSyncInfoLoaded loads all the relevent sync info into the cache - * @param resources - * @param i - * @return Object - */ - public void ensureSyncInfoLoaded(IResource[] resources, int depth) throws CVSException { - // get the folders involved - IContainer[] folders = getParentFolders(resources, depth); - // Cache the sync info for all the folders - for (int i = 0; i < folders.length; i++) { - IContainer parent = folders[i]; - try { - beginOperation(parent, null); - cacheResourceSyncForChildren(parent); - cacheFolderSync(parent); - cacheFolderIgnores(parent); - } finally { - endOperation(null); - } - } - } - - /* - * Collect the projects and parent folders of the resources since - * thats were the sync info is kept. - */ - private IContainer[] getParentFolders(IResource[] resources, int depth) throws CVSException { - final Set folders = new HashSet(); - for (int i = 0; i < resources.length; i++) { - IResource resource = resources[i]; - folders.add(resource.getProject()); - if (resource.getType() != IResource.PROJECT) { - folders.add(resource.getParent()); - } - // use the depth to gather child folders when appropriate - if (depth != IResource.DEPTH_ZERO) { - try { - resource.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - if (resource.getType() == IResource.FOLDER) - folders.add(resource); - // let the depth determine who we visit - return true; - } - }, depth, false); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - } - return (IContainer[]) folders.toArray(new IContainer[folders.size()]); - } - - /** - * Obtain the CVS sync lock while running the given ICVSRunnable. - * @param job - * @param monitor - * @throws CVSException - */ - public void run(ICVSRunnable job, IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - try { - IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot(); - beginOperation(root, Policy.subMonitorFor(monitor, 5)); - job.run(Policy.subMonitorFor(monitor, 60)); - } finally { - endOperation(Policy.subMonitorFor(monitor, 35)); - monitor.done(); - } - } - - /** - * Method isEdited returns true if a "cvs edit" was performed on the given - * file and no commit or unedit has yet been performed. - * @param iResource - * @return boolean - */ - public boolean isEdited(IFile resource) throws CVSException { - return SyncFileWriter.isEdited(resource); - } - - private void adjustDirtyStateRecursively(IResource resource, String indicator) throws CVSException { - if (resource.getType() == IResource.ROOT) return; - try { - beginOperation(resource, null); - - if (indicator == getDirtyIndicator(resource)) { - return; - } - - if (Policy.DEBUG_DIRTY_CACHING) { - debug(resource, indicator, "adjusting dirty state"); //$NON-NLS-1$ - } - - getSyncInfoCacheFor(resource).setDirtyIndicator(resource, indicator); - - IContainer parent = resource.getParent(); - if(indicator == NOT_DIRTY_INDICATOR) { - adjustDirtyStateRecursively(parent, RECOMPUTE_INDICATOR); - } - - if(indicator == RECOMPUTE_INDICATOR) { - adjustDirtyStateRecursively(parent, RECOMPUTE_INDICATOR); - } - - if(indicator == IS_DIRTY_INDICATOR) { - adjustDirtyStateRecursively(parent, indicator); - } - } finally { - endOperation(null); - } - } - - protected String getDirtyIndicator(IResource resource) throws CVSException { - try { - beginOperation(resource, null); - return getSyncInfoCacheFor(resource).getDirtyIndicator(resource); - } finally { - endOperation(null); - } - } - - /* - * Mark the given resource as either modified or clean using a persistant - * property. Do nothing if the modified state is already what we want. - * Return true if the modification state was changed. - */ - protected void setDirtyIndicator(IResource resource, boolean modified) throws CVSException { - try { - beginOperation(resource, null); - String indicator = modified ? IS_DIRTY_INDICATOR : NOT_DIRTY_INDICATOR; - // set the dirty indicator and adjust the parent accordingly - adjustDirtyStateRecursively(resource, indicator); - } finally { - endOperation(null); - } - } - - /** - * Method getName. - * @param syncBytes - */ - private String getName(byte[] syncBytes) throws CVSException { - return ResourceSyncInfo.getName(syncBytes); - } - - /** - * Method isFolder. - * @param syncBytes - * @return boolean - */ - private boolean isFolder(byte[] syncBytes) { - return ResourceSyncInfo.isFolder(syncBytes); - } - - /** - * Method convertToDeletion. - * @param syncBytes - * @return byte[] - */ - private byte[] convertToDeletion(byte[] syncBytes) throws CVSException { - return ResourceSyncInfo.convertToDeletion(syncBytes); - } - - /** - * Method convertFromDeletion. - * @param syncBytes - */ - private byte[] convertFromDeletion(byte[] syncBytes) throws CVSException { - return ResourceSyncInfo.convertFromDeletion(syncBytes); - } - - /** - * Method createdByMove clears any session properties on the file so it - * appears as an ADDED file. - * - * @param destination - */ - public void createdByMove(IFile file) throws CVSException { - deleteResourceSync(file); - } - - static public void debug(IResource resource, String indicator, String string) { - String di = EclipseSynchronizer.IS_DIRTY_INDICATOR; - if(indicator == EclipseSynchronizer.IS_DIRTY_INDICATOR) { - di = "dirty"; //$NON-NLS-1$ - } else if(indicator == EclipseSynchronizer.NOT_DIRTY_INDICATOR) { - di = "clean"; //$NON-NLS-1$ - } else { - di = "needs recomputing"; //$NON-NLS-1$ - } - System.out.println("["+string + ":" + di + "] " + resource.getFullPath()); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$ - } - - static public void debug(IResource resource, boolean modified, String string) { - debug(resource, modified ? IS_DIRTY_INDICATOR : NOT_DIRTY_INDICATOR, string); - } - - /** - * @param file - * @return int - */ - public int getModificationState(IResource resource) throws CVSException { - String indicator = getDirtyIndicator(resource); - if (Policy.DEBUG_DIRTY_CACHING) { - debug(resource, indicator, "getModificationState"); //$NON-NLS-1$ - } - if (indicator == null || indicator == RECOMPUTE_INDICATOR) { - return ICVSFile.UNKNOWN; - } else if (indicator == IS_DIRTY_INDICATOR) { - return ICVSFile.DIRTY; - } else if (indicator == NOT_DIRTY_INDICATOR) { - return ICVSFile.CLEAN; - } else { - return ICVSFile.UNKNOWN; - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/FileContentCachingService.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/FileContentCachingService.java deleted file mode 100644 index a1c0d02df..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/FileContentCachingService.java +++ /dev/null @@ -1,116 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; - -/** - * This class can be used to fetch and cache file contents for remote files. - */ -public class FileContentCachingService { - - String[] fileDiffs; - private CVSRepositoryLocation repository; - private ICVSFolder remoteRoot; - - public static RemoteFolderTree buildRemoteTree(CVSRepositoryLocation repository, ICVSFolder root, CVSTag tag, IProgressMonitor monitor) throws CVSException { - monitor.beginTask(null, 100); - try { - RemoteFolderTreeBuilder builder = new RemoteFolderTreeBuilder(repository, root, tag); - RemoteFolderTree tree = builder.buildTree(new ICVSResource[] { root }, Policy.subMonitorFor(monitor, 50)); - FileContentCachingService service = new FileContentCachingService(repository, tree, builder.getFileDiffs()); - service.cacheFileContents(Policy.subMonitorFor(monitor, 50)); - return tree; - } finally { - monitor.done(); - } - } - - public static RemoteFile buildRemoteTree(CVSRepositoryLocation repository, ICVSFile file, CVSTag tag, IProgressMonitor monitor) throws CVSException { - monitor.beginTask(null, 100); - try { - RemoteFolderTreeBuilder builder = new RemoteFolderTreeBuilder(repository, file.getParent(), tag); - RemoteFile remote = builder.buildTree(file, monitor); - if (builder.getFileDiffs().length > 0 && !remote.isContentsCached()) { - remote.fetchContents(Policy.subMonitorFor(monitor, 50)); - } - return remote; - } finally { - monitor.done(); - } - } - - public FileContentCachingService(CVSRepositoryLocation repository, RemoteFolderTree tree, String[] fileDiffs) { - this.repository = repository; - this.remoteRoot = tree; - this.fileDiffs = fileDiffs; - } - - private void cacheFileContents(IProgressMonitor monitor) throws CVSException { - String[] files = getUncachedFiles(); - if (files.length == 0) return; - // Fetch the file contents for all out-of-sync files by running an update - // on the remote tree passing the known changed files as arguments - monitor.beginTask(null, 10 + files.length * 100); - Policy.checkCanceled(monitor); - Session session = new Session(repository, remoteRoot, false); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - Policy.checkCanceled(monitor); - IStatus status = Command.UPDATE.execute(session, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] { Update.IGNORE_LOCAL_CHANGES }, - files, - null, - Policy.subMonitorFor(monitor, files.length * 100)); - } finally { - session.close(); - monitor.done(); - } - } - - /* - * Only return those file in the diff list that exist remotely and whose contents are not already cached - */ - private String[] getUncachedFiles() { - if (fileDiffs.length == 0) return fileDiffs; - List existing = new ArrayList(); - for (int i = 0; i < fileDiffs.length; i++) { - String filePath = fileDiffs[i]; - try { - ICVSFile file = remoteRoot.getFile(filePath); - if (file instanceof RemoteFile) { - if (!((RemoteFile)file).isContentsCached()) { - existing.add(filePath); - } - } - } catch (CVSException e) { - // The child does not exists so exclude it - } - } - return (String[]) existing.toArray(new String[existing.size()]); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/FileModificationManager.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/FileModificationManager.java deleted file mode 100644 index 1250c5b25..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/FileModificationManager.java +++ /dev/null @@ -1,203 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.util.HashSet; -import java.util.Set; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceChangeEvent; -import org.eclipse.core.resources.IResourceChangeListener; -import org.eclipse.core.resources.IResourceDelta; -import org.eclipse.core.resources.IResourceDeltaVisitor; -import org.eclipse.core.resources.ISaveContext; -import org.eclipse.core.resources.ISaveParticipant; -import org.eclipse.core.resources.ISavedState; -import org.eclipse.core.resources.IWorkspace; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSFile; - -/** - * This class performs several functions related to determining the modified - * status of files under CVS control. First, it listens for change delta's for - * files and brodcasts them to all listeners. It also registers as a save - * participant so that deltas generated before the plugin are loaded are not - * missed. Secondly, it listens for CVS resource state change events and uses - * these to properly mark files and folders as modified. - */ -public class FileModificationManager implements IResourceChangeListener, ISaveParticipant { - - private static final QualifiedName UPDATE_TIMESTAMP = new QualifiedName(CVSProviderPlugin.ID, "update-timestamp"); //$NON-NLS-1$ - - private Set modifiedResources = new HashSet(); - - // consider the following changes types and ignore the others (e.g. marker and description changes are ignored) - protected int INTERESTING_CHANGES = IResourceDelta.CONTENT | - IResourceDelta.MOVED_FROM | - IResourceDelta.MOVED_TO | - IResourceDelta.OPEN | - IResourceDelta.REPLACED | - IResourceDelta.TYPE; - - /** - * Listen for file modifications and fire modification state changes - * - * @see org.eclipse.core.resources.IResourceChangeListener#resourceChanged(org.eclipse.core.resources.IResourceChangeEvent) - */ - public void resourceChanged(IResourceChangeEvent event) { - try { - event.getDelta().accept(new IResourceDeltaVisitor() { - public boolean visit(IResourceDelta delta) throws CoreException { - IResource resource = delta.getResource(); - - if (resource.getType()==IResource.PROJECT) { - IProject project = (IProject)resource; - if (!project.isAccessible()) { - return false; - } - if ((delta.getFlags() & IResourceDelta.OPEN) != 0) { - return false; - } - if (RepositoryProvider.getProvider(project, CVSProviderPlugin.getTypeId()) == null) { - return false; - } - } - - if (resource.getType()==IResource.FILE && delta.getKind() == IResourceDelta.CHANGED && resource.exists()) { - int flags = delta.getFlags(); - if((flags & INTERESTING_CHANGES) != 0) { - resourceChanged(resource, false); - } - } else if (delta.getKind() == IResourceDelta.ADDED) { - resourceChanged(resource, true); - } else if (delta.getKind() == IResourceDelta.REMOVED) { - try { - EclipseSynchronizer.getInstance().handleDeleted(resource); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - modifiedResources.add(resource); - } - - return true; - } - }); - if (!modifiedResources.isEmpty()) { - CVSProviderPlugin.broadcastModificationStateChanges( - (IResource[])modifiedResources.toArray(new IResource[modifiedResources.size()])); - modifiedResources.clear(); - } - } catch (CoreException e) { - CVSProviderPlugin.log(e); - } - - } - - /** - * We register a save participant so we can get the delta from workbench - * startup to plugin startup. - * @throws CoreException - */ - public void registerSaveParticipant() throws CoreException { - IWorkspace ws = ResourcesPlugin.getWorkspace(); - ISavedState ss = ws.addSaveParticipant(CVSProviderPlugin.getPlugin(), this); - if (ss != null) { - ss.processResourceChangeEvents(this); - } - ws.removeSaveParticipant(CVSProviderPlugin.getPlugin()); - } - - /** - * @see org.eclipse.core.resources.ISaveParticipant#doneSaving(org.eclipse.core.resources.ISaveContext) - */ - public void doneSaving(ISaveContext context) { - } - /** - * @see org.eclipse.core.resources.ISaveParticipant#prepareToSave(org.eclipse.core.resources.ISaveContext) - */ - public void prepareToSave(ISaveContext context) throws CoreException { - } - /** - * @see org.eclipse.core.resources.ISaveParticipant#rollback(org.eclipse.core.resources.ISaveContext) - */ - public void rollback(ISaveContext context) { - } - /** - * @see org.eclipse.core.resources.ISaveParticipant#saving(org.eclipse.core.resources.ISaveContext) - */ - public void saving(ISaveContext context) throws CoreException { - } - - - /** - * Method updated flags the objetc as having been modfied by the updated - * handler. This flag is read during the resource delta to determine whether - * the modification made the file dirty or not. - * - * @param mFile - */ - public void updated(ICVSFile mFile) { - try { - if (mFile instanceof EclipseFile) { - IFile file = (IFile)mFile.getIResource(); - file.setSessionProperty(UPDATE_TIMESTAMP, new Long(file.getModificationStamp())); - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } catch (CoreException e) { - CVSProviderPlugin.log(CVSException.wrapException(e)); - } - } - - /* - * Handle added and changed resources by signaling the change to the corresponding - * CVS resource and recording the change for broadcast to interested listeners. - */ - private void resourceChanged(IResource resource, boolean addition) throws CoreException { - if (isCleanUpdate(resource)) return; - try { - EclipseResource cvsResource = (EclipseResource)CVSWorkspaceRoot.getCVSResourceFor(resource); - cvsResource.handleModification(addition); - modifiedResources.add(resource); - } catch (CVSException e) { - throw e.toCoreException(); - } - } - - /** - * If the file was the result of a clean update, the cached timestamp will - * be removed. - * - * @param resource - * @return boolean - */ - private boolean isCleanUpdate(IResource resource) { - if(resource.getType() != IResource.FILE) return false; - long modStamp = resource.getModificationStamp(); - Long whenWeWrote; - try { - whenWeWrote = (Long)resource.getSessionProperty(UPDATE_TIMESTAMP); - resource.setSessionProperty(UPDATE_TIMESTAMP, null); - } catch(CoreException e) { - CVSProviderPlugin.log(e); - whenWeWrote = null; - } - return (whenWeWrote!=null && whenWeWrote.longValue() == modStamp); - } -} - 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 deleted file mode 100644 index 46f671413..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFile.java +++ /dev/null @@ -1,592 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.io.ByteArrayInputStream; -import java.io.File; -import java.io.InputStream; -import java.util.ArrayList; -import java.util.Date; -import java.util.List; - -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.core.sync.RemoteContentsCache; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -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.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; -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; -import org.eclipse.team.internal.ccvs.core.client.Log; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.client.Command.QuietOption; -import org.eclipse.team.internal.ccvs.core.client.listeners.LogListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; -import org.eclipse.team.internal.ccvs.core.syncinfo.MutableResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * This class provides the implementation of ICVSRemoteFile and IManagedFile for - * use by the repository and sync view. - */ -public class RemoteFile extends RemoteResource implements ICVSRemoteFile { - - // Contents will be cached to disk when this thrshold is exceeded - private static final int CACHING_THRESHOLD = -1; // don't create a byte array even for files size 0 - - // sync info in byte form - private byte[] syncBytes; - // buffer for file contents received from the server - private byte[] contents; - // cache the log entry for the remote file - private ILogEntry entry; - - /** - * Static method which creates a file as a single child of its parent. - * This should only be used when one is only interested in the file alone. - * - * The returned RemoteFile represents the base of the local resource. - * If the local resource does not have a base, then null is returned - * even if the resource does exists remotely (e.g. created by another party). - */ - public static RemoteFile getBase(RemoteFolder parent, ICVSFile managed) throws CVSException { - byte[] syncBytes = managed.getSyncBytes(); - if ((syncBytes == null) || ResourceSyncInfo.isAddition(syncBytes)) { - // Either the file is unmanaged or has just been added (i.e. doesn't necessarily have a remote) - return null; - } - RemoteFile file = new RemoteFile(parent, syncBytes); - parent.setChildren(new ICVSRemoteResource[] {file}); - return file; - } - - public static RemoteFile fromBytes(IResource local, byte[] bytes, byte[] parentBytes) throws CVSException { - Assert.isNotNull(bytes); - Assert.isTrue(local.getType() == IResource.FILE); - RemoteFolder parent = RemoteFolder.fromBytes(local.getParent(), parentBytes); - RemoteFile file = new RemoteFile(parent, bytes); - parent.setChildren(new ICVSRemoteResource[] {file}); - return file; - } - - public static RemoteFile getRemote(IFile local, byte[] bytes) throws CVSException { - RemoteFolder parent = (RemoteFolder)CVSWorkspaceRoot.getRemoteResourceFor(local.getParent()); - RemoteFile file = new RemoteFile(parent, bytes); - parent.setChildren(new ICVSRemoteResource[] {file}); - return file; - } - - /** - * Constructor for RemoteFile that should be used when nothing is know about the - * file ahead of time. - */ - public RemoteFile(RemoteFolder parent, int workspaceSyncState, String name, CVSTag tag) { - this(parent, workspaceSyncState, name, ResourceSyncInfo.ADDED_REVISION, tag); //$NON-NLS-1$ - } - - public RemoteFile(RemoteFolder parent, int workspaceSyncState, String name, String revision, CVSTag tag) { - super(parent, name); - MutableResourceSyncInfo newInfo = new MutableResourceSyncInfo(name, revision); - newInfo.setKeywordMode(Command.KSUBST_TEXT_EXPAND); - newInfo.setTag(tag); - syncBytes = newInfo.getBytes(); - setWorkspaceSyncState(workspaceSyncState); - } - - public RemoteFile(RemoteFolder parent, byte[] syncBytes) throws CVSException { - this(parent, Update.STATE_NONE, syncBytes); - } - - public RemoteFile(RemoteFolder parent, int workspaceSyncState, byte[] syncBytes) throws CVSException { - super(parent, ResourceSyncInfo.getName(syncBytes)); - this.syncBytes = syncBytes; - setWorkspaceSyncState(workspaceSyncState); - } - - /** - * @see ICVSResource#accept(ICVSResourceVisitor) - */ - public void accept(ICVSResourceVisitor visitor) throws CVSException { - visitor.visitFile(this); - } - - /** - * @see ICVSResource#accept(ICVSResourceVisitor, boolean) - */ - public void accept(ICVSResourceVisitor visitor, boolean recurse) throws CVSException { - visitor.visitFile(this); - } - - /** - * @see ICVSRemoteFile#getContents() - */ - public InputStream getContents(IProgressMonitor monitor) throws CVSException { - if (contents == null) { - // First, check to see if there's a cached contents for the file - InputStream cached = getCachedContents(); - if (cached != null) { - return cached; - } - - // No contents cached so fetch contents from the server. - fetchContents(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 - cached = getCachedContents(); - if (cached != null) { - return cached; - } else { - contents = new byte[0]; - } - } - } - return new ByteArrayInputStream(contents); - } - - /* package*/ void fetchContents(IProgressMonitor monitor) throws CVSException { - monitor.beginTask(Policy.bind("RemoteFile.getContents"), 100);//$NON-NLS-1$ - Session session = new Session(getRepository(), parent, false /* create backups */); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - IStatus status = Command.UPDATE.execute( - session, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] { - Update.makeTagOption(new CVSTag(getRevision(), CVSTag.VERSION)), - Update.IGNORE_LOCAL_CHANGES }, - new ICVSResource[] { this }, - null, - Policy.subMonitorFor(monitor, 90)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - session.close(); - monitor.done(); - } - } - - /* - * @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$ - Session session = new Session(getRepository(), parent, false /* output to console */); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - try { - final List entries = new ArrayList(); - IStatus status = Command.LOG.execute( - session, - Command.NO_GLOBAL_OPTIONS, - new LocalOption[] { - Log.makeRevisionOption(getRevision())}, - new ICVSResource[] { RemoteFile.this }, - new LogListener(RemoteFile.this, entries), - Policy.subMonitorFor(monitor, 90)); - if (entries.size() == 1) { - entry = (ILogEntry)entries.get(0); - } - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - monitor.done(); - } - } finally { - session.close(); - } - } - return entry; - } - - /** - * @see ICVSRemoteFile#getLogEntries() - */ - public ILogEntry[] getLogEntries(IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(Policy.bind("RemoteFile.getLogEntries"), 100); //$NON-NLS-1$ - final List entries = new ArrayList(); - Session session = new Session(getRepository(), parent, false /* output to console */); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness(); - try { - CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE); - IStatus status = Command.LOG.execute( - session, - Command.NO_GLOBAL_OPTIONS, Command.NO_LOCAL_OPTIONS, - new ICVSResource[] { RemoteFile.this }, new LogListener(RemoteFile.this, entries), - Policy.subMonitorFor(monitor, 90)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - CVSProviderPlugin.getPlugin().setQuietness(quietness); - monitor.done(); - } - } finally { - session.close(); - } - return (ILogEntry[])entries.toArray(new ILogEntry[entries.size()]); - } - - /** - * @see ICVSRemoteFile#getRevision() - */ - public String getRevision() { - try { - return ResourceSyncInfo.getRevision(syncBytes); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - return ResourceSyncInfo.ADDED_REVISION; - } - } - - /* - * Get a different revision of the remote file. - * - * We must also create a new parent since the child is accessed through the parent from within CVS commands. - * Therefore, we need a new parent so that we can fecth the contents of the remote file revision - */ - public RemoteFile toRevision(String revision) { - RemoteFolder newParent = new RemoteFolder(null, parent.getRepository(), parent.getRepositoryRelativePath(), parent.getTag()); - RemoteFile file = new RemoteFile(newParent, getWorkspaceSyncState(), getName(), revision, CVSTag.DEFAULT); - newParent.setChildren(new ICVSRemoteResource[] {file}); - return file; - } - - /** - * @see ICVSFile#getSize() - */ - public long getSize() { - if (contents == null) { - File ioFile = getRemoteContentsCache().getFile(getCacheRelativePath()); - if (ioFile.exists()) { - return ioFile.length(); - } - } - return contents == null ? 0 : contents.length; - } - - /** - * @see ICVSFile#getSyncInfo() - */ - public ResourceSyncInfo getSyncInfo() { - try { - return new ResourceSyncInfo(syncBytes); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - return null; - } - } - - /** - * @see ICVSResource#getRemoteLocation(ICVSFolder) - */ - public String getRemoteLocation(ICVSFolder stopSearching) throws CVSException { - return parent.getRemoteLocation(stopSearching) + Session.SERVER_SEPARATOR + getName(); - } - - /** - * Get the remote path for the receiver relative to the repository location path - */ - public String getRepositoryRelativePath() { - String parentPath = parent.getRepositoryRelativePath(); - return parentPath + Session.SERVER_SEPARATOR + getName(); - } - - /** - * Return the server root directory for the repository - */ - public ICVSRepositoryLocation getRepository() { - return parent.getRepository(); - } - - /** - * @see IManagedFile#setFileInfo(FileProperties) - */ - public void setSyncInfo(ResourceSyncInfo fileInfo, int modificationState) { - syncBytes = fileInfo.getBytes(); - } - - /** - * Set the revision for this remote file. - * - * @param revision to associated with this remote file - */ - public void setRevision(String revision) throws CVSException { - syncBytes = ResourceSyncInfo.setRevision(syncBytes, revision); - } - - public InputStream getContents() throws CVSException { - if (contents == null) { - // Check for cached contents for the file - InputStream cached = getCachedContents(); - if (cached != null) { - return cached; - } - } - return new ByteArrayInputStream(contents == null ? new byte[0] : contents); - } - - private InputStream getCachedContents() throws CVSException { - try { - return getRemoteContentsCache().getContents(getCacheRelativePath()); - } catch (TeamException e) { - throw CVSException.wrapException(e); - } - } - - public void setContents(InputStream stream, int responseType, boolean keepLocalHistory, IProgressMonitor monitor) throws CVSException { - try { - getRemoteContentsCache().setContents(getCacheRelativePath(), stream, monitor); - } catch (TeamException e) { - throw CVSException.wrapException(e); - } - } - - private RemoteContentsCache getRemoteContentsCache() { - return RemoteContentsCache.getCache(CVSProviderPlugin.ID); - } - - /* - * Return the cache relative path for the receiver as - * host/cvs/root/module/path/.#filename revision - */ - private String getCacheRelativePath() { - ICVSRepositoryLocation location = getRepository(); - IPath path = new Path(location.getHost()); - path = path.append(location.getRootDirectory()); - path = path.append(parent.getRepositoryRelativePath()); - path = path.append(getName() + ' ' + getRevision()); - return path.toString(); - } - - /* - * Return whether there are already contents cached for the given handle - */ - public boolean isContentsCached() { - return getRemoteContentsCache().hasContents(getCacheRelativePath()); - } - - /* - * @see ICVSFile#setReadOnly(boolean) - */ - public void setReadOnly(boolean readOnly) throws CVSException { - } - - /* - * @see ICVSFile#isReadOnly() - */ - public boolean isReadOnly() throws CVSException { - return true; - } - - /* - * @see ICVSFile#getTimeStamp() - */ - public Date getTimeStamp() { - return getSyncInfo().getTimeStamp(); - } - - /* - * @see ICVSFile#setTimeStamp(Date) - */ - public void setTimeStamp(Date date) throws CVSException { - } - - /** - * @see ICVSFile#moveTo(String) - */ - public void copyTo(String mFile) throws CVSException { - // Do nothing - } - - /* - * @see IRemoteResource#members(IProgressMonitor) - */ - public IRemoteResource[] members(IProgressMonitor progress) throws TeamException { - return new IRemoteResource[0]; - } - - /* - * @see IRemoteResource#isContainer() - */ - public boolean isContainer() { - return false; - } - - /* - * @see ICVSResource#isFolder() - */ - public boolean isFolder() { - return false; - } - - /* - * @see ICVSResource#tag(CVSTag, LocalOption[], IProgressMonitor) - * - * The revision of the remote file is used as the base for the tagging operation - */ - public IStatus tag(final CVSTag tag, final LocalOption[] localOptions, IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - Session session = new Session(getRepository(), getParent(), true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - return Command.RTAG.execute( - session, - Command.NO_GLOBAL_OPTIONS, - localOptions, - new CVSTag(getRevision(), CVSTag.VERSION), - tag, - new ICVSRemoteResource[] { RemoteFile.this }, - Policy.subMonitorFor(monitor, 90)); - } finally { - session.close(); - } - } - - public boolean equals(Object target) { - if (this == target) - return true; - if (!(target instanceof RemoteFile)) - return false; - RemoteFile remote = (RemoteFile) target; - return super.equals(target) && remote.getRevision().equals(getRevision()); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#checkout(int) - */ - public void edit(int notifications, IProgressMonitor monitor) throws CVSException { - // do nothing - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#uncheckout() - */ - public void unedit(IProgressMonitor monitor) throws CVSException { - // do nothing - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#notificationCompleted() - */ - public void notificationCompleted() { - // do nothing - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#getPendingNotification() - */ - public NotifyInfo getPendingNotification() throws CVSException { - return null; - } - - /** - * @see RemoteResource#forTag(ICVSRemoteFolder, CVSTag) - */ - public ICVSRemoteResource forTag(ICVSRemoteFolder parent, CVSTag tagName) { - return new RemoteFile((RemoteFolder)parent, getWorkspaceSyncState(), getName(), tagName); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSRemoteResource#forTag(org.eclipse.team.internal.ccvs.core.CVSTag) - */ - public ICVSRemoteResource forTag(CVSTag tag) { - RemoteFolderTree remoteFolder = new RemoteFolderTree(null, getRepository(), - ((ICVSRemoteFolder)getParent()).getRepositoryRelativePath(), - tag); - RemoteFile remoteFile = (RemoteFile)forTag(remoteFolder, tag); - remoteFolder.setChildren(new ICVSRemoteResource[] { remoteFile }); - return remoteFile; - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#committed(org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo) - */ - public void checkedIn(String info) throws CVSException { - // do nothing - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#isEdited() - */ - public boolean isEdited() throws CVSException { - return false; - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#getSyncBytes() - */ - public byte[] getSyncBytes() { - return syncBytes; - } - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFile#setSyncBytes(byte[]) - */ - public void setSyncBytes(byte[] syncBytes, int modificationState) throws CVSException { - setSyncInfo(new ResourceSyncInfo(syncBytes), ICVSFile.UNKNOWN); - } - - public String toString() { - return super.toString() + " " + getRevision(); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.IRemoteResource#getComment() - */ - public String getComment() throws CVSException { -// ILogEntry entry = getLogEntry(new NullProgressMonitor()); -// return entry.getComment(); - return ""; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.IRemoteResource#getContentIdentifier() - */ - public String getContentIdentifier() throws CVSException { - return getRevision(); - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.IRemoteResource#getCreatorDisplayName() - */ - public String getCreatorDisplayName() throws CVSException { -// ILogEntry entry = getLogEntry(new NullProgressMonitor()); -// return entry.getAuthor(); - return ""; - } -} 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 deleted file mode 100644 index bf10a2259..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolder.java +++ /dev/null @@ -1,819 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import java.io.InputStream; -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.resources.IResource; -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.Path; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder; -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.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.GlobalOption; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.client.Command.QuietOption; -import org.eclipse.team.internal.ccvs.core.client.listeners.IStatusListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.IUpdateMessageListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.StatusListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.UpdateListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * This class provides the implementation of ICVSRemoteFolder - * - * The parent of the RemoteFolder represents the folders parent in a local configuration. - * For instance, the parent may correspond to the remote parent or may be a folder in the - * same repository that has no physical relationship to the RemoteFolder (resulting from the use - * of a module definition, for instance). A RemoteFolder may not have a parent, indicating that it is - * the root of the local configuration it represents. - * - * A RemoteFolder has the following: - * A name in the folder's local configuration - * - */ -public class RemoteFolder extends RemoteResource implements ICVSRemoteFolder, ICVSFolder { - - private final class FolderMembersUpdateListener implements IUpdateMessageListener { - List newRemoteDirectories = new ArrayList(); - List newRemoteFiles = new ArrayList(); - boolean exists = true; - List exceptions = new ArrayList(); - protected List getNewRemoteDirectories() { - return newRemoteDirectories; - } - protected List getNewRemoteFiles() { - return newRemoteFiles; - } - - public void directoryInformation(ICVSFolder commandRoot, String stringPath, boolean newDirectory) { - try { - IPath path = getRelativePathFromRootRelativePath(commandRoot, new Path(stringPath)); - if (newDirectory && path.segmentCount() == 1) { - newRemoteDirectories.add(path.lastSegment()); - } - } catch (CVSException e) { - exceptions.add(e); - } - } - public void directoryDoesNotExist(ICVSFolder parent, String stringPath) { - try { - IPath path = getRelativePathFromRootRelativePath(parent, new Path(stringPath)); - if (path.isEmpty()) { - // the remote folder doesn't exist - exists = false; - } - } catch (CVSException e) { - exceptions.add(e); - } - } - public void fileInformation(int type, ICVSFolder parent, String filename) { - try { - IPath filePath = new Path(filename); - filePath = getRelativePathFromRootRelativePath(parent, filePath); - if( filePath.segmentCount() == 1 ) { - String properFilename = filePath.lastSegment(); - newRemoteFiles.add(properFilename); - } - } catch (CVSException e) { - exceptions.add(e); - } - } - public void fileDoesNotExist(ICVSFolder parent, String filename) { - } - - public void performErrorCheck(IStatus status) throws CVSException { - if (status.getCode() == CVSStatus.SERVER_ERROR) { - // Only throw the exception if no files or folders were found - if (newRemoteDirectories.size() + newRemoteFiles.size() == 0) { - throw new CVSServerException(status); - } else { - CVSProviderPlugin.log(new CVSServerException(status)); - } - - } - if (!exists) { - throw new CVSException(new CVSStatus(CVSStatus.ERROR, CVSStatus.DOES_NOT_EXIST, Policy.bind("RemoteFolder.doesNotExist", getRepositoryRelativePath()))); //$NON-NLS-1$ - } - - // Report any internal 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); - } - } - } - } - - protected FolderSyncInfo folderInfo; - private ICVSRemoteResource[] children; - private ICVSRepositoryLocation repository; - - public static RemoteFolder fromBytes(IResource local, byte[] bytes) throws CVSException { - Assert.isNotNull(bytes); - Assert.isTrue(local.getType() != IResource.FILE); - FolderSyncInfo syncInfo = FolderSyncInfo.getFolderSyncInfo(bytes); - return new RemoteFolder(null, local.getName(), CVSProviderPlugin.getPlugin().getRepository(syncInfo.getRoot()), syncInfo.getRepository(), syncInfo.getTag(), syncInfo.getIsStatic()); - } - - /** - * Constructor for RemoteFolder. - */ - public RemoteFolder(RemoteFolder parent, ICVSRepositoryLocation repository, String repositoryRelativePath, CVSTag tag) { - this(parent, - repositoryRelativePath == null ? "" : Util.getLastSegment(repositoryRelativePath), //$NON-NLS-1$ - repository, - repositoryRelativePath, - tag, - false); - } - - public RemoteFolder(RemoteFolder parent, String name, ICVSRepositoryLocation repository, String repositoryRelativePath, CVSTag tag, boolean isStatic) { - super(parent, name); - this.folderInfo = new FolderSyncInfo(repositoryRelativePath.toString(), repository.getLocation(), tag, isStatic); - this.repository = repository; - } - - // Get the file revisions for the given filenames - protected void updateFileRevisions(final ICVSFile[] files, IProgressMonitor monitor) throws CVSException { - - final int[] count = new int[] {0}; - - // Create a listener for receiving the revision info - final IStatusListener listener = new IStatusListener() { - public void fileStatus(ICVSFolder parent, String path, String remoteRevision) { - if (remoteRevision == IStatusListener.FOLDER_REVISION) - // Ignore any folders - return; - try { - ((RemoteFile)getChild(Util.getLastSegment(path))).setRevision(remoteRevision); - count[0]++; - } catch (CVSException e) { - // The count will be off to indicate an error - } - } - }; - - // Perform a "cvs status..." with a listener - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness(); - try { - CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE); - Session session = new Session(getRepository(), this, false /* output to console */); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - IStatus status = Command.STATUS.execute( - session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - files, - new StatusListener(listener), - Policy.subMonitorFor(monitor, 90)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } finally { - session.close(); - } - } finally { - CVSProviderPlugin.getPlugin().setQuietness(quietness); - } - - if (count[0] != files.length) - throw new CVSException(Policy.bind("RemoteFolder.errorFetchingRevisions")); //$NON-NLS-1$ - } - - /** - * @see ICVSResource#accept(ICVSResourceVisitor) - */ - public void accept(ICVSResourceVisitor visitor) throws CVSException { - visitor.visitFolder(this); - } - - /** - * @see ICVSResource#accept(ICVSResourceVisitor, boolean) - */ - public void accept(ICVSResourceVisitor visitor, boolean recurse) throws CVSException { - visitor.visitFolder(this); - ICVSResource[] resources; - if (recurse) { - resources = members(ICVSFolder.ALL_MEMBERS); - } else { - resources = members(ICVSFolder.FILE_MEMBERS); - } - for (int i = 0; i < resources.length; i++) { - resources[i].accept(visitor, recurse); - } - } - - /* - * @see ICVSRemoteResource#exists(IProgressMonitor) - */ - public boolean exists(IProgressMonitor monitor) throws TeamException { - try { - members(monitor); - return true; - } catch (CVSException e) { - if (e.getStatus().getCode() == CVSStatus.DOES_NOT_EXIST) { - return false; - } else { - throw e; - } - } - } - - /* - * Check whether the given resource is a child of the receiver remotely - */ - protected boolean exists(ICVSRemoteResource child, IProgressMonitor monitor) throws CVSException { - return exists(child, getTag(), monitor); - } - - /* - * Check whether the child exists for the given tag. This additional method is required because - * 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(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}; - final IUpdateMessageListener listener = new IUpdateMessageListener() { - public void directoryInformation(ICVSFolder parent, String path, boolean newDirectory) { - exists[0] = true; - } - public void directoryDoesNotExist(ICVSFolder parent, String path) { - exists[0] = false; - } - 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(ICVSFolder parent, String filename) { - exists[0] = false; - } - }; - - // Build the local options - 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 - boolean retry = false; - Session session = new Session(getRepository(), this, false /* output to console */); - session.open(Policy.subMonitorFor(progress, 10)); - try { - IStatus status = Command.UPDATE.execute( - session, - new GlobalOption[] { Command.DO_NOT_CHANGE }, - (LocalOption[]) localOptions.toArray(new LocalOption[localOptions.size()]), - new ICVSResource[] { child }, new UpdateListener(listener), - Policy.subMonitorFor(progress, 70)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - CVSServerException e = new CVSServerException(status); - if (e.isNoTagException() && child.isContainer()) { - retry = true; - } else { - if (e.containsErrors()) { - throw e; - } - } - } - } finally { - session.close(); - } - - // 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) { - Policy.checkCanceled(progress); - return exists(child, null, Policy.subMonitorFor(progress, 20)); - } - return exists[0]; - } finally { - progress.done(); - } - } - - /** - * @see ICVSRemoteFolder#getMembers() - */ - public ICVSRemoteResource[] getMembers(IProgressMonitor monitor) throws TeamException { - return getMembers(getTag(), monitor); - } - - /** - * This method gets the members for a given tag and returns them. - * During the execution of this method, the instance variable children - * will be used to contain the children. However, the variable is reset - * and the result returned. Thus, instances of RemoteFolder do not - * persist the children. Subclasses (namely RemoteFolderTree) may - * persist the children. - */ - protected ICVSRemoteResource[] getMembers(final CVSTag tag, IProgressMonitor monitor) throws CVSException { - final IProgressMonitor progress = Policy.monitorFor(monitor); - progress.beginTask(Policy.bind("RemoteFolder.getMembers"), 100); //$NON-NLS-1$ - try { - // Forget about any children we used to know about children - children = null; - - // Create the listener for remote files and folders - FolderMembersUpdateListener listener = new FolderMembersUpdateListener(); - - // Perform an update to retrieve the child files and folders - IStatus status = performUpdate(tag, listener, Policy.subMonitorFor(progress, 50)); - Policy.checkCanceled(monitor); - - // Handle any errors that were identified by the listener - listener.performErrorCheck(status); - - // Convert the file names to remote resources - List result = new ArrayList(); - List remoteFiles = new ArrayList(); - for (int i=0;i<listener.getNewRemoteFiles().size();i++) { - RemoteFile newFile = new RemoteFile(RemoteFolder.this, Update.STATE_NONE, (String)listener.getNewRemoteFiles().get(i), tag); - result.add(newFile); - remoteFiles.add(newFile); - } - - // Convert the folder names to remote resources - for (int i=0;i<listener.getNewRemoteDirectories().size();i++) - result.add(new RemoteFolder(RemoteFolder.this, getRepository(), Util.appendPath(getRepositoryRelativePath(), (String)listener.getNewRemoteDirectories().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(progress, 50)); - } else { - progress.worked(50); - } - } catch (CVSServerException e) { - if ( ! e.isNoTagException() && e.containsErrors()) - throw e; - if (tag == null) - 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.checkCanceled(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]; - if(remoteResource.isContainer()) { - ((RemoteFolder)remoteResource).setTag(tag); - } - } - } finally { - progress.done(); - } - - // 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; - } - - private IStatus performUpdate(CVSTag tag, IUpdateMessageListener listener, IProgressMonitor progress) throws CVSException { - progress.beginTask(null, 100); - Session session = new Session(getRepository(), this, false /* output to console */); - session.open(Policy.subMonitorFor(progress, 10)); - try { - // Build the local options - final List localOptions = new ArrayList(); - localOptions.add(Update.RETRIEVE_ABSENT_DIRECTORIES); - if (tag != null) localOptions.add(Update.makeTagOption(tag)); - - return Command.UPDATE.execute( - session, - new GlobalOption[] { Command.DO_NOT_CHANGE }, - (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]), - new ICVSResource[] { RemoteFolder.this }, - new UpdateListener(listener), - Policy.subMonitorFor(progress, 90)); - } finally { - session.close(); - } - } - - /** - * @see ICVSFolder#members(int) - */ - public ICVSResource[] members(int flags) throws CVSException { - final List result = new ArrayList(); - ICVSRemoteResource[] resources = getChildren(); - if (children == null) { - return new ICVSResource[0]; - } - // RemoteFolders never have phantom members - if ((flags & EXISTING_MEMBERS) == 0 && (flags & PHANTOM_MEMBERS) == 1) { - return new ICVSResource[0]; - } - boolean includeFiles = (((flags & FILE_MEMBERS) != 0) || ((flags & (FILE_MEMBERS | FOLDER_MEMBERS)) == 0)); - boolean includeFolders = (((flags & FOLDER_MEMBERS) != 0) || ((flags & (FILE_MEMBERS | FOLDER_MEMBERS)) == 0)); - boolean includeManaged = (((flags & MANAGED_MEMBERS) != 0) || ((flags & (MANAGED_MEMBERS | UNMANAGED_MEMBERS | IGNORED_MEMBERS)) == 0)); - boolean includeUnmanaged = (((flags & UNMANAGED_MEMBERS) != 0) || ((flags & (MANAGED_MEMBERS | UNMANAGED_MEMBERS | IGNORED_MEMBERS)) == 0)); - boolean includeIgnored = ((flags & IGNORED_MEMBERS) != 0); - for (int i = 0; i < resources.length; i++) { - ICVSResource cvsResource = resources[i]; - if ((includeFiles && ( ! cvsResource.isFolder())) - || (includeFolders && (cvsResource.isFolder()))) { - boolean isManaged = cvsResource.isManaged(); - boolean isIgnored = cvsResource.isIgnored(); - if ((isManaged && includeManaged)|| (isIgnored && includeIgnored) - || ( ! isManaged && ! isIgnored && includeUnmanaged)) { - result.add(cvsResource); - } - - } - } - return (ICVSResource[]) result.toArray(new ICVSResource[result.size()]); - } - - /** - * @see ICVSFolder#getFolder(String) - */ - public ICVSFolder getFolder(String name) throws CVSException { - if (name.equals(Session.CURRENT_LOCAL_FOLDER) || name.equals(Session.CURRENT_LOCAL_FOLDER + Session.SERVER_SEPARATOR)) - return this; - ICVSResource child = getChild(name); - if (child.isFolder()) - return (ICVSFolder)child; - throw new CVSException(Policy.bind("RemoteFolder.invalidChild", name, getName())); //$NON-NLS-1$ - } - - /** - * @see ICVSFolder#getFile(String) - */ - public ICVSFile getFile(String name) throws CVSException { - ICVSResource child = getChild(name); - if (!child.isFolder()) - return (ICVSFile)child; - throw new CVSException(Policy.bind("RemoteFolder.invalidChild", name, getName())); //$NON-NLS-1$ - - } - - public LocalOption[] getLocalOptions() { - return Command.NO_LOCAL_OPTIONS; - } - - public String getRepositoryRelativePath() { - // The REPOSITORY property of the folder info is the repository relative path - return getFolderSyncInfo().getRepository(); - } - - /** - * @see ICVSResource#getRelativePath(ICVSFolder) - */ - public String getRelativePath(ICVSFolder ancestor) throws CVSException { - // 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$ - } - return super.getRelativePath(ancestor); - } - - public ICVSRepositoryLocation getRepository() { - return repository; - } - - /** - * @see ICVSRemoteFolder#isExpandable() - */ - public boolean isExpandable() { - return true; - } - - /** - * @see ICVSResource#isFolder() - */ - public boolean isFolder() { - return true; - } - - /** - * @see ICVSFolder#childExists(String) - */ - public boolean childExists(String path) { - try { - return getChild(path) != null; - } catch (CVSException e) { - return false; - } - } - - /** - * @see ICVSFolder#getChild(String) - * - * This getChild is geared to work with the Command hierarchy. Therefore it only returns - * children that were previously fetched by a call to getMembers(). If the request child - * does not exist, an exception is thrown. - */ - public ICVSResource getChild(String path) throws CVSException { - if (path.equals(Session.CURRENT_LOCAL_FOLDER) || path.length() == 0) - return this; - if (path.indexOf(Session.SERVER_SEPARATOR) != -1) { - IPath p = new Path(path); - try { - return ((RemoteFolder)getChild(p.segment(0))).getChild(p.removeFirstSegments(1).toString()); - } catch (CVSException e) { - // regenerate the exception to give as much info as possible - throw new CVSException(Policy.bind("RemoteFolder.invalidChild", path, getName()));//$NON-NLS-1$ - } - } else { - ICVSRemoteResource[] children = getChildren(); - if (children == null) - throw new CVSException(Policy.bind("RemoteFolder.invalidChild", path, getName()));//$NON-NLS-1$ - for (int i=0;i<children.length;i++) { - if (children[i].getName().equals(path)) - return (ICVSResource)children[i]; - } - } - throw new CVSException(Policy.bind("RemoteFolder.invalidChild", path, getName()));//$NON-NLS-1$ - } - - /** - * @see ICVSFolder#mkdir() - */ - public void mkdir() throws CVSException { - throw new CVSException(Policy.bind("RemoteResource.invalidOperation"));//$NON-NLS-1$ - } - - /** - * @see ICVSFolder#flush(boolean) - */ - public void flush(boolean deep) { - } - - /** - * @see ICVSFolder#getFolderInfo() - */ - public FolderSyncInfo getFolderSyncInfo() { - return folderInfo; - } - - /** - * @see ICVSResource#getRemoteLocation(ICVSFolder) - */ - public String getRemoteLocation(ICVSFolder stopSearching) throws CVSException { - return folderInfo.getRemoteLocation(); - } - - /** - * @see ICVSFolder#isCVSFolder() - */ - public boolean isCVSFolder() { - return true; - } - - /** - * @see ICVSFolder#acceptChildren(ICVSResourceVisitor) - */ - public void acceptChildren(ICVSResourceVisitor visitor) throws CVSException { - throw new CVSException(Policy.bind("RemoteResource.invalidOperation"));//$NON-NLS-1$ - } - - /* - * @see IRemoteResource#isContainer() - */ - public boolean isContainer() { - return true; - } - - /* - * @see IRemoteResource#members(IProgressMonitor) - */ - public IRemoteResource[] members(IProgressMonitor progress) throws TeamException { - return getMembers(progress); - } - - /* - * @see IRemoteResource#getContents(IProgressMonitor) - */ - public InputStream getContents(IProgressMonitor progress) throws TeamException { - return null; - } - - /* - * Answers the immediate cached children of this remote folder or null if the remote folder - * handle has not yet queried the server for the its children. - */ - public ICVSRemoteResource[] getChildren() { - return children; - } - /* - * This allows subclass to set the children - */ - protected void setChildren(ICVSRemoteResource[] children) { - this.children = children; - } - /* - * @see ICVSRemoteFolder#setTag(String) - */ - public void setTag(CVSTag tag) { - this.folderInfo = new FolderSyncInfo(folderInfo.getRepository(), folderInfo.getRoot(), tag, folderInfo.getIsStatic()); - } - - /* - * @see ICVSRemoteFolder#getTag() - */ - public CVSTag getTag() { - return folderInfo.getTag(); - } - /* - * @see ICVSFolder#setFolderInfo(FolderSyncInfo) - */ - public void setFolderSyncInfo(FolderSyncInfo folderInfo) throws CVSException { - this.folderInfo = folderInfo; - // Currently not supported - throw new CVSException(Policy.bind("RemoteResource.invalidOperation"));//$NON-NLS-1$ - } - - /* - * @see ICVSFolder#run(ICVSRunnable, IProgressMonitor) - */ - public void run(ICVSRunnable job, IProgressMonitor monitor) throws CVSException { - job.run(monitor); - } - - /* - * @see ICVSFolder#run(ICVSRunnable, int, IProgressMonitor) - */ - public void run(ICVSRunnable job, int flags, IProgressMonitor monitor) throws CVSException { - job.run(monitor); - } - - /* - * @see ICVSFolder#tag(CVSTag, LocalOption[], IProgressMonitor) - */ - public IStatus tag(final CVSTag tag, final LocalOption[] localOptions, IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - Session session = new Session(getRepository(), this, true /* output to console */); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - return Command.RTAG.execute( - session, - Command.NO_GLOBAL_OPTIONS, - localOptions, - folderInfo.getTag(), - tag, - new ICVSRemoteResource[] { RemoteFolder.this }, - Policy.subMonitorFor(monitor, 90)); - } finally { - session.close(); - } - } - - /** - * @see ICVSFolder#fetchChildren(IProgressMonitor) - */ - public ICVSResource[] fetchChildren(IProgressMonitor monitor) throws CVSException { - try { - return getMembers(monitor); - } catch(TeamException e) { - 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); - } - - /** - * @see java.lang.Object#hashCode() - */ - public int hashCode() { - CVSTag tag = getTag(); - if (tag == null) tag = CVSTag.DEFAULT; - return super.hashCode() | tag.getName().hashCode(); - } - - /* - * The given root must be an ancestor of the receiver (or the receiver) - * and the path of the receiver must be a prefix of the provided path. - */ - protected IPath getRelativePathFromRootRelativePath(ICVSFolder root, IPath path) throws CVSException { - // If the root is the receiver, then the path is already relative to the receiver - if (root == this) { - return path; - } - Assert.isTrue( ! path.isEmpty()); - return getRelativePathFromRootRelativePath((ICVSFolder)root.getChild(path.segment(0)), path.removeFirstSegments(1)); - } - - /** - * @see ICVSRemoteFolder#forTag(CVSTag) - */ - public ICVSRemoteResource forTag(ICVSRemoteFolder parent, CVSTag tagName) { - return new RemoteFolder((RemoteFolder)parent, getName(), repository, folderInfo.getRepository(), tagName, folderInfo.getIsStatic()); - } - - /** - * @see ICVSRemoteFolder#forTag(CVSTag) - */ - public ICVSRemoteResource forTag(CVSTag tagName) { - return (ICVSRemoteFolder)forTag(null, tagName); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder#isDefinedModule() - */ - public boolean isDefinedModule() { - return false; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.RemoteResource#getSyncInfo() - */ - public ResourceSyncInfo getSyncInfo() { - return new ResourceSyncInfo(getName()); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.resources.RemoteResource#getSyncBytes() - */ - public byte[] getSyncBytes() { - try { - return folderInfo.getBytes(); - } catch (CVSException e) { - // This shouldn't even happen - return null; - } - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.IRemoteResource#getComment() - */ - public String getComment() throws TeamException { - return null; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.IRemoteResource#getContentIdentifier() - */ - public String getContentIdentifier() throws TeamException { - return null; - } - - /* (non-Javadoc) - * @see org.eclipse.team.core.sync.IRemoteResource#getCreatorDisplayName() - */ - public String getCreatorDisplayName() throws TeamException { - return null; - } -} 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 deleted file mode 100644 index e98a48f8d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTree.java +++ /dev/null @@ -1,65 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSTag; -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; - -/** - * Whereas the RemoteFolder class provides access to a remote hierarchy using - * lazy retrieval via <code>getMembers()</code>, the RemoteFolderTree will force - * a recursive retrieval of the remote hierarchy in one round trip. - */ -public class RemoteFolderTree extends RemoteFolder { - - public RemoteFolderTree(RemoteFolder parent, ICVSRepositoryLocation repository, String repositoryRelativePath, CVSTag tag) { - super(parent, repository, repositoryRelativePath, tag); - } - - public RemoteFolderTree(RemoteFolder parent, String name, ICVSRepositoryLocation repository, String repositoryRelativePath, CVSTag tag) { - super(parent, name, repository, repositoryRelativePath, tag, false); - } - - /* - * Override of inherited method which persists the children - */ - public ICVSRemoteResource[] getMembers(CVSTag tagName, IProgressMonitor monitor) throws CVSException { - if (getChildren() == null) - setChildren(super.getMembers(tagName, monitor)); - return getChildren(); - } - - /* - * This method is public to allow access by the RemoteFolderTreeBuilder utility class. - * No other external classes should use this method. - */ - public void setChildren(ICVSRemoteResource[] children) { - super.setChildren(children); - } - - /* - * @see ICVSFolder#acceptChildren(ICVSResourceVisitor) - */ - public void acceptChildren(ICVSResourceVisitor visitor) throws CVSException { - ICVSRemoteResource[] children = getChildren(); - if (children == null) return; - for (int i=0; i<children.length; i++) { - ((ICVSResource)children[i]).accept(visitor); - } - } -} - diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTreeBuilder.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTreeBuilder.java deleted file mode 100644 index 5dbfd7a30..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteFolderTreeBuilder.java +++ /dev/null @@ -1,781 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.MultiStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.GlobalOption; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.client.Command.QuietOption; -import org.eclipse.team.internal.ccvs.core.client.listeners.IStatusListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.IUpdateMessageListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.StatusListener; -import org.eclipse.team.internal.ccvs.core.client.listeners.UpdateListener; -import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.connection.CVSServerException; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/* - * This class is responsible for building a remote tree that shows the repository - * state of a locally loaded folder tree. - * - * It is used as follows - * - * RemoteFolderTreeBuilder.buildRemoteTree(CVSRepositoryLocation, IManagedFolder, String, IProgressMonitor); - * - * The provider IManagedFolder can be a local resource or a RemoteFolderTree that - * that was previously built. - */ -public class RemoteFolderTreeBuilder { - - private static final int MAX_REVISION_FETCHES_PER_CONNECTION = 1024; - - private Map fileDeltas; - private List changedFiles; - private Map remoteFolderTable; - - private ICVSFolder root; - private RemoteFolderTree remoteRoot; - private CVSRepositoryLocation repository; - - private CVSTag tag; - - private LocalOption[] updateLocalOptions; - - private boolean projectDoesNotExist = false; - - private static String UNKNOWN = ""; //$NON-NLS-1$ - private static String DELETED = "DELETED"; //$NON-NLS-1$ - private static String ADDED = "ADDED"; //$NON-NLS-1$ - private static String FOLDER = "FOLDER"; //$NON-NLS-1$ - - private static Map EMPTY_MAP = new HashMap(); - - private boolean newFolderExist = false; - - static class DeltaNode { - int syncState = Update.STATE_NONE; - String name; - String revision; - - DeltaNode(String name, String revision, int syncState) { - this.name = name; - this.revision = revision; - this.syncState = syncState; - } - - String getName() { - return name; - } - - String getRevision() { - return revision; - } - - int getSyncState() { - return syncState; - } - } - - - /* package */ RemoteFolderTreeBuilder(CVSRepositoryLocation repository, ICVSFolder root, CVSTag tag) { - this.repository = repository; - this.root = root; - this.tag = tag; - this.fileDeltas = new HashMap(); - this.changedFiles = new ArrayList(); - this.remoteFolderTable = new HashMap(); - - // Build the local options - List localOptions = new ArrayList(); - if (tag != null) { - if (tag.getType() == CVSTag.HEAD) { - localOptions.add(Update.CLEAR_STICKY); - } else { - localOptions.add(Update.makeTagOption(tag)); - } - } - updateLocalOptions = (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]); - } - - private LocalOption[] getOptionsWithoutTag() { - // Build the local options - List localOptions = new ArrayList(); - localOptions.add(Update.RETRIEVE_ABSENT_DIRECTORIES); - return (LocalOption[])localOptions.toArray(new LocalOption[localOptions.size()]); - } - - public static RemoteFolderTree buildBaseTree(CVSRepositoryLocation repository, ICVSFolder root, CVSTag tag, IProgressMonitor progress) throws CVSException { - try { - RemoteFolderTreeBuilder builder = new RemoteFolderTreeBuilder(repository, root, tag); - progress.beginTask(null, 100); - IProgressMonitor subProgress = Policy.infiniteSubMonitorFor(progress, 100); - subProgress.beginTask(null, 512); //$NON-NLS-1$ - subProgress.subTask(Policy.bind("RemoteFolderTreeBuilder.buildingBase", root.getName())); //$NON-NLS-1$ - return builder.buildBaseTree(null, root, subProgress); - } finally { - progress.done(); - } - } - - public static RemoteFolderTree buildRemoteTree(CVSRepositoryLocation repository, IContainer root, CVSTag tag, IProgressMonitor monitor) throws CVSException { - return buildRemoteTree(repository, CVSWorkspaceRoot.getCVSFolderFor(root), tag, monitor); - } - - public static RemoteFolderTree buildRemoteTree(CVSRepositoryLocation repository, ICVSFolder root, CVSTag tag, IProgressMonitor monitor) throws CVSException { - RemoteFolderTreeBuilder builder = new RemoteFolderTreeBuilder(repository, root, tag); - return builder.buildTree(new ICVSResource[] { root }, monitor); - } - public static RemoteFile buildRemoteTree(CVSRepositoryLocation repository, ICVSFile file, CVSTag tag, IProgressMonitor monitor) throws CVSException { - RemoteFolderTreeBuilder builder = new RemoteFolderTreeBuilder(repository, file.getParent(), tag); - return builder.buildTree(file, monitor); - } - - /* - * The provided resources must all be children of the same project - */ - public static RemoteFolderTree buildRemoteTree(CVSRepositoryLocation repository, ICVSFolder root, ICVSResource[] resources, CVSTag tag, IProgressMonitor monitor) throws CVSException { - if (resources.length == 0) { - resources = new ICVSResource[] { root }; - } - RemoteFolderTreeBuilder builder = new RemoteFolderTreeBuilder(repository, root, tag); - return builder.buildTree(resources, monitor); - } - - /* package */ RemoteFolderTree buildTree(ICVSResource[] resources, IProgressMonitor monitor) throws CVSException { - - // Make sure that the cvs commands are not quiet during this operations - QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness(); - try { - CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE); - - monitor.beginTask(null, 100); - - // 1st Connection: Use local state to determine delta with server - if (!fetchDelta(resources, Policy.subMonitorFor(monitor, 50))) { - return null; - } - - // 2nd Connection: Build remote tree from above delta using 2nd connection to fetch unknown directories - // NOTE: Multiple commands may be issued over this connection. - fetchNewDirectories(Policy.subMonitorFor(monitor, 20)); - - // 3rd+ Connection: Used to fetch file status in groups of 1024 - fetchFileRevisions(Policy.subMonitorFor(monitor, 30)); - - return remoteRoot; - - } finally { - CVSProviderPlugin.getPlugin().setQuietness(quietness); - monitor.done(); - } - } - - private boolean fetchDelta(ICVSResource[] resources, IProgressMonitor monitor) throws CVSException { - - // Get the arguments from the files - ArrayList arguments = new ArrayList(); - for (int i = 0; i < resources.length; i++) { - ICVSResource resource = resources[i]; - arguments.add(resource.getRelativePath(root)); - } - - // Use local state to determine delta with server - monitor.beginTask(null, 100); - Policy.checkCanceled(monitor); - Session session = new Session(repository, root, false); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - Policy.checkCanceled(monitor); - fetchDelta(session, (String[]) arguments.toArray(new String[arguments.size()]), Policy.subMonitorFor(monitor, 90)); - if (projectDoesNotExist) { - // We cannot handle the case where a project (i.e. the top-most CVS folder) - // has been deleted directly on the sever (i.e. deleted using rm -rf) - if (root.isCVSFolder() && ! root.isManaged()) { - throw new CVSException(Policy.bind("RemoteFolderTreeBuild.folderDeletedFromServer", root.getFolderSyncInfo().getRepository())); //$NON-NLS-1$ - } else { - return false; - } - } - } finally { - session.close(); - monitor.done(); - } - return true; - } - - private void fetchNewDirectories(IProgressMonitor monitor) throws CVSException { - // Build remote tree from the fetched delta using a new connection to fetch unknown directories - // NOTE: Multiple commands may be issued over this connection. - monitor.beginTask(null, 100); - Session session; - remoteRoot = - new RemoteFolderTree(null, root.getName(), repository, - root.getFolderSyncInfo().getRepository(), - tagForRemoteFolder(root, tag)); - if (newFolderExist) { - // New folders will require a connection for fetching their members - session = new Session(repository, remoteRoot, false); - session.open(Policy.subMonitorFor(monitor, 10)); - } else { - session = null; - } - try { - // Set up an infinite progress monitor for the recursive build - IProgressMonitor subProgress = Policy.infiniteSubMonitorFor(monitor, 90); - subProgress.beginTask(null, 512); - // Build the remote tree - buildRemoteTree(session, root, remoteRoot, "", subProgress); //$NON-NLS-1$ - } finally { - if (session != null) { - session.close(); - } - monitor.done(); - } - } - - private void fetchFileRevisions(IProgressMonitor monitor) throws CVSException { - // 3rd+ Connection: Used to fetch file status in groups of 1024 - if (!changedFiles.isEmpty()) { - String[] allChangedFiles = (String[])changedFiles.toArray(new String[changedFiles.size()]); - int iterations = (allChangedFiles.length / MAX_REVISION_FETCHES_PER_CONNECTION) - + (allChangedFiles.length % MAX_REVISION_FETCHES_PER_CONNECTION == 0 ? 0 : 1); - for (int i = 0; i < iterations ; i++) { - int length = Math.min(MAX_REVISION_FETCHES_PER_CONNECTION, - allChangedFiles.length - (MAX_REVISION_FETCHES_PER_CONNECTION * i)); - String buffer[] = new String[length]; - System.arraycopy(allChangedFiles, i * MAX_REVISION_FETCHES_PER_CONNECTION, buffer, 0, length); - Session session = new Session(repository, remoteRoot, false); - session.open(Policy.subMonitorFor(monitor, 1)); - try { - fetchFileRevisions(session, buffer, Policy.subMonitorFor(monitor, 2)); - } finally { - session.close(); - } - } - } - } - - /* package */ RemoteFile buildTree(ICVSFile file, IProgressMonitor monitor) throws CVSException { - QuietOption quietness = CVSProviderPlugin.getPlugin().getQuietness(); - try { - CVSProviderPlugin.getPlugin().setQuietness(Command.VERBOSE); - - monitor.beginTask(null, 100); - - // Query the server to see if there is a delta available - Policy.checkCanceled(monitor); - Session session = new Session(repository, root, false); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - Policy.checkCanceled(monitor); - fetchDelta(session, new String[] { file.getName() }, Policy.subMonitorFor(monitor, 50)); - if (projectDoesNotExist) { - return null; - } - } finally { - session.close(); - } - // Create a parent for the remote resource - remoteRoot = - new RemoteFolderTree(null, root.getName(), repository, - root.getFolderSyncInfo().getRepository(), - tagForRemoteFolder(root, tag)); - // Create the remote resource (using the delta if there is one) - RemoteFile remoteFile; - Map deltas = (Map)fileDeltas.get(""); //$NON-NLS-1$ - if (deltas == null || deltas.isEmpty()) { - // If the file is an addition, return null as the remote - // Note: If there was a conflicting addition, the delta would not be empty - byte[] syncBytes = file.getSyncBytes(); - if ( syncBytes == null || ResourceSyncInfo.isAddition(syncBytes)) { - return null; - } - remoteFile = new RemoteFile(remoteRoot, syncBytes); - } else { - DeltaNode d = (DeltaNode)deltas.get(file.getName()); - if (d.getRevision() == DELETED) { - return null; - } - remoteFile = new RemoteFile(remoteRoot, d.getSyncState(), file.getName(), tagForRemoteFolder(remoteRoot, tag)); - } - // Add the resource to its parent - remoteRoot.setChildren(new ICVSRemoteResource[] {remoteFile}); - // If there was a delta, fetch the new revision - if (!changedFiles.isEmpty()) { - // Add the remote folder to the remote folder lookup table (used to update file revisions) - recordRemoteFolder(remoteRoot); - session = new Session(repository, remoteRoot, false); - session.open(Policy.subMonitorFor(monitor, 10)); - try { - fetchFileRevisions(session, (String[])changedFiles.toArray(new String[changedFiles.size()]), Policy.subMonitorFor(monitor, 20)); - } finally { - session.close(); - } - } - return remoteFile; - - } finally { - CVSProviderPlugin.getPlugin().setQuietness(quietness); - monitor.done(); - } - } - - /* - * Build the base remote tree from the local tree. - * - * The localPath is used to retrieve deltas from the recorded deltas - * - * Does 1 work for each managed file and folder - */ - private RemoteFolderTree buildBaseTree(RemoteFolderTree parent, ICVSFolder local, IProgressMonitor monitor) throws CVSException { - - Policy.checkCanceled(monitor); - - // Create a remote folder tree corresponding to the local resource - RemoteFolderTree remote = new RemoteFolderTree(parent, local.getName(), repository, local.getFolderSyncInfo().getRepository(), local.getFolderSyncInfo().getTag()); - - // Create a List to contain the created children - List children = new ArrayList(); - - // Build the child folders corresponding to local folders base - ICVSResource[] folders = local.members(ICVSFolder.FOLDER_MEMBERS); - for (int i=0;i<folders.length;i++) { - ICVSFolder folder = (ICVSFolder)folders[i]; - if (folder.isManaged() && folder.isCVSFolder()) { - monitor.worked(1); - children.add(buildBaseTree(remote, folder, monitor)); - } - } - - // Build the child files corresponding to local files base - ICVSResource[] files = local.members(ICVSFolder.FILE_MEMBERS); - for (int i=0;i<files.length;i++) { - ICVSFile file = (ICVSFile)files[i]; - byte[] syncBytes = file.getSyncBytes(); - // if there is no sync info then there is no base - if (syncBytes==null) - continue; - // There is no remote if the file was added - if (ResourceSyncInfo.isAddition(syncBytes)) - continue; - // If the file was deleted locally, we need to generate a new sync info without the delete flag - if (ResourceSyncInfo.isDeletion(syncBytes)) { - syncBytes = ResourceSyncInfo.convertFromDeletion(syncBytes); - } - children.add(new RemoteFile(remote, syncBytes)); - monitor.worked(1); - } - - // Add the children to the remote folder tree - remote.setChildren((ICVSRemoteResource[])children.toArray(new ICVSRemoteResource[children.size()])); - - return remote; - } - - /* - * Build the remote tree from the local tree and the recorded deltas. - * - * The localPath is used to retrieve deltas from the recorded deltas - * - * Does 1 work for each file and folder delta processed - */ - private void buildRemoteTree(Session session, ICVSFolder local, RemoteFolderTree remote, String localPath, IProgressMonitor monitor) throws CVSException { - - Policy.checkCanceled(monitor); - - // Add the remote folder to the remote folder lookup table (used to update file revisions) - recordRemoteFolder(remote); - - // Create a map to contain the created children - Map children = new HashMap(); - - // If there's no corresponding local resource then we need to fetch its contents in order to populate the deltas - if (local == null) { - fetchNewDirectory(session, remote, localPath, monitor); - } - - // Fetch the delta's for the folder - Map deltas = (Map)fileDeltas.get(localPath); - if (deltas == null) - deltas = EMPTY_MAP; - - // If there is a local, use the local children to start buidling the remote children - if (local != null) { - // Build the child folders corresponding to local folders - ICVSResource[] folders = local.members(ICVSFolder.FOLDER_MEMBERS); - for (int i=0;i<folders.length;i++) { - ICVSFolder folder = (ICVSFolder)folders[i]; - DeltaNode d = (DeltaNode)deltas.get(folder.getName()); - if (folder.isCVSFolder() && ! isOrphanedSubtree(folder) && (d==null || d.getRevision() != DELETED)) { - children.put(folders[i].getName(), - new RemoteFolderTree(remote, folders[i].getName(), repository, - folder.getFolderSyncInfo().getRepository(), - tagForRemoteFolder(folder,tag))); - } - } - // Build the child files corresponding to local files - ICVSResource[] files = local.members(ICVSFolder.FILE_MEMBERS); - for (int i=0;i<files.length;i++) { - ICVSFile file = (ICVSFile)files[i]; - - DeltaNode d = (DeltaNode)deltas.get(file.getName()); - byte[] syncBytes = file.getSyncBytes(); - // if there is no sync info then there isn't a remote file for this local file on the - // server. - if (syncBytes==null) - continue; - // There is no remote if the file was added and we didn't get a conflict (C) indicator from the server - if (ResourceSyncInfo.isAddition(syncBytes) && d==null) - continue; - // There is no remote if the file was deleted and we didn;t get a remove (R) indicator from the server - if (ResourceSyncInfo.isDeletion(syncBytes) && d==null) - continue; - - int type = d==null ? Update.STATE_NONE : d.getSyncState(); - children.put(file.getName(), new RemoteFile(remote, type, syncBytes)); - } - } - - // Build the children for new or out-of-date resources from the deltas - Iterator i = deltas.keySet().iterator(); - while (i.hasNext()) { - String name = (String)i.next(); - DeltaNode d = (DeltaNode)deltas.get(name); - String revision = d.getRevision(); - if (revision == FOLDER) { - children.put(name, new RemoteFolderTree(remote, repository, - Util.appendPath(remote.getRepositoryRelativePath(), name), - tagForRemoteFolder(remote, tag))); - } else if (revision == ADDED) { - children.put(name, new RemoteFile(remote, d.getSyncState(), name, tagForRemoteFolder(remote, tag))); - } else if (revision == UNKNOWN) { - // The local resource is out of sync with the remote. - // Create a RemoteFile associated with the tag so we are assured of getting the proper revision - // (Note: this will replace the RemoteFile added from the local base) - children.put(name, new RemoteFile(remote, d.getSyncState(), name, tagForRemoteFolder(remote, tag))); - } else if (revision == DELETED) { - // This should have been deleted while creating from the local resources. - // If it wasn't, delete it now. - if (children.containsKey(name)) - children.remove(name); - } else { - // We should never get here - } - monitor.worked(1); - } - - // Add the children to the remote folder tree - remote.setChildren((ICVSRemoteResource[])children.values().toArray(new ICVSRemoteResource[children.size()])); - - // We have to delay building the child folders to support the proper fetching of new directories - // due to the fact that the same CVS home directory (i.e. the same root directory) must - // be used for all requests sent over the same connection - Iterator childIterator = children.entrySet().iterator(); - List emptyChildren = new ArrayList(); - while (childIterator.hasNext()) { - Map.Entry entry = (Map.Entry)childIterator.next(); - if (((RemoteResource)entry.getValue()).isFolder()) { - RemoteFolderTree remoteFolder = (RemoteFolderTree)entry.getValue(); - String name = (String)entry.getKey(); - ICVSFolder localFolder; - DeltaNode d = (DeltaNode)deltas.get(name); - // for directories that are new on the server - if (d!=null && d.getRevision() == FOLDER) - localFolder = null; - else - localFolder = local.getFolder(name); - buildRemoteTree(session, localFolder, remoteFolder, Util.appendPath(localPath, name), monitor); - // Record any children that are empty - if (pruneEmptyDirectories() && remoteFolder.getChildren().length == 0) { - // Prune if the local folder is also empty. - if (localFolder == null || (localFolder.members(ICVSFolder.ALL_EXISTING_MEMBERS).length == 0)) - emptyChildren.add(remoteFolder); - else { - // Also prune if the tag we are fetching is not HEAD and differs from the tag of the local folder - FolderSyncInfo info = localFolder.getFolderSyncInfo(); - if (tag != null && info != null && ! tag.equals(CVSTag.DEFAULT) && ! tag.equals(info.getTag())) - emptyChildren.add(remoteFolder); - } - } - } - } - - // Prune any empty child folders - if (pruneEmptyDirectories() && !emptyChildren.isEmpty()) { - List newChildren = new ArrayList(); - newChildren.addAll(Arrays.asList(remote.getChildren())); - newChildren.removeAll(emptyChildren); - remote.setChildren((ICVSRemoteResource[])newChildren.toArray(new ICVSRemoteResource[newChildren.size()])); - - } - } - - /* - * This method fetches the delta between the local state and the remote state of the resource tree - * and records the deltas in the fileDeltas instance variable - * - * Returns the list of changed files - */ - private List fetchDelta(Session session, String[] arguments, final IProgressMonitor monitor) throws CVSException { - - // Create an listener that will accumulate new and removed files and folders - IUpdateMessageListener listener = new IUpdateMessageListener() { - public void directoryInformation(ICVSFolder root, String path, boolean newDirectory) { - if (newDirectory) { - // Record new directory with parent so it can be retrieved when building the parent - recordDelta(path, FOLDER, Update.STATE_NONE); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingDelta", Util.toTruncatedPath(path, 3))); //$NON-NLS-1$ - } - } - public void directoryDoesNotExist(ICVSFolder root, String path) { - // Record removed directory with parent so it can be removed when building the parent - if (path.length() == 0) { - projectDoesNotExist = true; - } else { - recordDelta(path, DELETED, Update.STATE_NONE); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingDelta", Util.toTruncatedPath(path, 3))); //$NON-NLS-1$ - } - } - public void fileInformation(int type, ICVSFolder root, String filename) { - // Cases that do not require action are: - // case 'A' : = A locally added file that does not exists remotely - // case '?' : = A local file that has not been added and does not exists remotely - // case 'M' : = A locally modified file that has not been modified remotely - switch(type) { - case Update.STATE_MERGEABLE_CONFLICT : - case Update.STATE_CONFLICT : - // We have an remote change to a modified local file - // The change could be a local change conflicting with a remote deletion. - // If so, the deltas may already have a DELETED for the file. - // We shouldn't override this DELETED - Map deltas = deltas = (Map)fileDeltas.get(Util.removeLastSegment(filename)); - DeltaNode d = deltas != null ? (DeltaNode)deltas.get(Util.getLastSegment(filename)) : null; - if ((d!=null) && (d.getRevision() == DELETED)) - break; - case Update.STATE_DELETED : // We have a locally removed file that still exists remotely - case Update.STATE_REMOTE_CHANGES : // We have an remote change to an unmodified local file - changedFiles.add(filename); - recordDelta(filename, UNKNOWN, type); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingDelta", Util.toTruncatedPath(filename, 3))); //$NON-NLS-1$ - break; - } - } - public void fileDoesNotExist(ICVSFolder root, String filename) { - recordDelta(filename, DELETED, Update.STATE_NONE); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingDelta", Util.toTruncatedPath(filename, 3))); //$NON-NLS-1$ - } - }; - - // Perform a "cvs -n update -d [-r tag] ." in order to get the - // messages from the server that will indicate what has changed on the - // server. - IStatus status = Command.SYNCUPDATE.execute(session, - new GlobalOption[] { Command.DO_NOT_CHANGE }, - updateLocalOptions, - arguments, - new UpdateListener(listener), - monitor); - return changedFiles; - } - /* - * Fetch the children of a previously unknown directory. - * - * The fetch may do up to 2 units of work in the provided monitor. - */ - private void fetchNewDirectory(Session session, RemoteFolderTree newFolder, String localPath, final IProgressMonitor monitor) throws CVSException { - - // Create an listener that will accumulate new files and folders - IUpdateMessageListener listener = new IUpdateMessageListener() { - public void directoryInformation(ICVSFolder root, String path, boolean newDirectory) { - if (newDirectory) { - // Record new directory with parent so it can be retrieved when building the parent - // NOTE: Check path prefix - recordDelta(path, FOLDER, Update.STATE_NONE); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingDelta", Util.toTruncatedPath(path, 3))); //$NON-NLS-1$ - } - } - public void directoryDoesNotExist(ICVSFolder root, String path) { - } - public void fileInformation(int type, ICVSFolder root, String filename) { - // NOTE: Check path prefix - changedFiles.add(filename); - recordDelta(filename, ADDED, type); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingDelta", Util.toTruncatedPath(filename, 3))); //$NON-NLS-1$ - } - public void fileDoesNotExist(ICVSFolder root, String filename) { - } - }; - - // NOTE: Should use the path relative to the remoteRoot - IStatus status = Command.UPDATE.execute(session, - new GlobalOption[] { Command.DO_NOT_CHANGE }, - updateLocalOptions, - new String[] { localPath }, - new UpdateListener(listener), - Policy.subMonitorFor(monitor, 1)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - // FIXME: This should be refactored (maybe static methods on CVSException?) - CVSServerException e = new CVSServerException(status); - if ( ! e.isNoTagException() && 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.checkCanceled(monitor); - status = Command.UPDATE.execute(session, - new GlobalOption[] { Command.DO_NOT_CHANGE }, - getOptionsWithoutTag(), - new String[] { localPath }, - new UpdateListener(listener), - Policy.subMonitorFor(monitor, 1)); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - } - } - - // Get the file revisions for the given filenames - private void fetchFileRevisions(Session session, String[] fileNames, final IProgressMonitor monitor) throws CVSException { - - // Create a listener for receiving the revision info - final Map revisions = new HashMap(); - final List exceptions = new ArrayList(); - IStatusListener listener = new IStatusListener() { - public void fileStatus(ICVSFolder root, String path, String remoteRevision) { - try { - updateRevision(path, remoteRevision); - monitor.subTask(Policy.bind("RemoteFolderTreeBuilder.receivingRevision", Util.toTruncatedPath(path, 3))); //$NON-NLS-1$ - } catch (CVSException e) { - exceptions.add(e); - } - } - }; - - // Perform a "cvs status..." with a custom message handler - IStatus status = Command.STATUS.execute(session, - Command.NO_GLOBAL_OPTIONS, - Command.NO_LOCAL_OPTIONS, - fileNames, - new StatusListener(listener), - monitor); - if (status.getCode() == CVSStatus.SERVER_ERROR) { - throw new CVSServerException(status); - } - - // Report any exceptions that occured fecthing the revisions - if ( ! exceptions.isEmpty()) { - if (exceptions.size() == 1) { - throw (CVSException)exceptions.get(0); - } else { - MultiStatus multi = new MultiStatus(CVSProviderPlugin.ID, 0, Policy.bind("RemoteFolder.errorFetchingRevisions"), null); //$NON-NLS-1$ - for (int i = 0; i < exceptions.size(); i++) { - multi.merge(((CVSException)exceptions.get(i)).getStatus()); - } - throw new CVSException(multi); - } - } - } - - private boolean pruneEmptyDirectories() { - return CVSProviderPlugin.getPlugin().getPruneEmptyDirectories(); - } - /* - * Record the deltas in a double map where the outer key is the parent directory - * and the inner key is the file name. The value is the revision of the file or - * DELETED (file or folder). New folders have a revision of FOLDER. - * - * A revison of UNKNOWN indicates that the revision has not been fetched - * from the repository yet. - */ - private void recordDelta(String path, String revision, int syncState) { - if (revision == FOLDER) { - newFolderExist = true; - } - String parent = Util.removeLastSegment(path); - Map deltas = (Map)fileDeltas.get(parent); - if (deltas == null) { - deltas = new HashMap(); - fileDeltas.put(parent, deltas); - } - String name = Util.getLastSegment(path); - deltas.put(name, new DeltaNode(name, revision, syncState)); - } - - private void updateRevision(String path, String revision) throws CVSException { - RemoteFolderTree folder = getRecoredRemoteFolder(Util.removeLastSegment(path)); - if (folder == null) { - throw new CVSException(Policy.bind("RemoteFolderTreeBuilder.missingParent", path.toString(), revision));//$NON-NLS-1$ - } - ((RemoteFile)folder.getFile(Util.getLastSegment(path))).setRevision(revision); - } - - /* - * Return the tag that should be associated with a remote folder. - * - * This method is used to ensure that new directories contain the tag - * derived from the parant local folder when appropriate. For instance, - * - * The tag should be the provided tag. However, if tag is null, the - * tag for the folder should be derived from the provided reference folder - * which could be the local resource corresponding to the remote or the parent - * of the remote. - */ - private CVSTag tagForRemoteFolder(ICVSFolder folder, CVSTag tag) throws CVSException { - return tag == null ? folder.getFolderSyncInfo().getTag() : tag; - } - - private boolean isOrphanedSubtree(ICVSFolder mFolder) throws CVSException { - return mFolder.isCVSFolder() && ! mFolder.isManaged() && ! mFolder.equals(root) && mFolder.getParent().isCVSFolder(); - } - - private void recordRemoteFolder(RemoteFolderTree remote) throws CVSException { - String path = remote.getFolderSyncInfo().getRemoteLocation(); - remoteFolderTable.put(Util.asPath(path), remote); - } - - private RemoteFolderTree getRecoredRemoteFolder(String path) { - return (RemoteFolderTree)remoteFolderTable.get(Util.asPath(path)); - } - - /** - * This method returns an array of the files that differ between the local and remote trees. - * The files are represented as a String that contains the path to the file in the remote or local trees. - * @return an array of differing files - */ - public String[] getFileDiffs() { - return (String[]) changedFiles.toArray(new String[changedFiles.size()]);; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteModule.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteModule.java deleted file mode 100644 index 75119ad26..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteModule.java +++ /dev/null @@ -1,405 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.NoSuchElementException; -import java.util.StringTokenizer; - -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder; -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.Policy; -import org.eclipse.team.internal.ccvs.core.client.Checkout; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; - -public class RemoteModule extends RemoteFolder { - - private String label; - private ICVSRemoteResource[] referencedModules; - private LocalOption[] localOptions; - private boolean expandable; - - public static RemoteModule[] getRemoteModules(ICVSRepositoryLocation repository, CVSTag tag, IProgressMonitor monitor) throws TeamException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(Policy.bind("RemoteModule.getRemoteModules"), 100); //$NON-NLS-1$ - try { - RemoteModule[] modules; - Session s = new Session(repository, (ICVSFolder)CVSWorkspaceRoot.getCVSResourceFor(ResourcesPlugin.getWorkspace().getRoot()), false); - s.open(Policy.subMonitorFor(monitor, 10)); - try { - modules = Command.CHECKOUT.getRemoteModules(s, tag, Policy.subMonitorFor(monitor, 90)); - } finally { - s.close(); - } - return modules; - } finally { - monitor.done(); - } - } - - /** - * Create a set of RemoteModules from the provided module definition strings returned from the server - * - * At the moment, we are very restrictive on the types of modules we support. - */ - public static RemoteModule[] createRemoteModules(String[] moduleDefinitionStrings, ICVSRepositoryLocation repository, CVSTag tag) { - - Map modules = new HashMap(); - Map referencedModulesTable = new HashMap(); - Map moduleAliases = new HashMap(); - List acceptableModules = new ArrayList(); - - // First pass: Create the remote module instances based on remote mapping - for (int i = 0; i < moduleDefinitionStrings.length; i++) { - - // Read the module name - StringTokenizer tokenizer = new StringTokenizer(moduleDefinitionStrings[i]); - String moduleName = tokenizer.nextToken(); - List localOptionsList; - String next; - try { - // Read the options associated with the module - localOptionsList = new ArrayList(); - next = tokenizer.nextToken(); - while (next.charAt(0) == '-') { - switch (next.charAt(1)) { - case 'a': // alias - localOptionsList.add(Checkout.ALIAS); - break; - case 'l': // don't recurse - localOptionsList.add(Checkout.DO_NOT_RECURSE); - break; - case 'd': // directory - localOptionsList.add(Checkout.makeDirectoryNameOption(tokenizer.nextToken())); - break; - case 'e': - case 'i': - case 'o': - case 't': - case 'u': // Ignore any programs - tokenizer.nextToken(); - break; - case 's': // status - localOptionsList.add(Checkout.makeStatusOption(tokenizer.nextToken())); - break; - default: // unanticipated option. Ignore it and go on - } - next = tokenizer.nextToken(); - } - } catch (NoSuchElementException e) { - // There is an invalid entry in the modules file. Log it and continue - CVSProviderPlugin.log(IStatus.WARNING, Policy.bind("RemoteModule.invalidDefinition", moduleDefinitionStrings[i], repository.getLocation()), null); //$NON-NLS-1$ - continue; - } - LocalOption[] localOptions = (LocalOption[]) localOptionsList.toArray(new LocalOption[localOptionsList.size()]); - - if (Checkout.ALIAS.isElementOf(localOptions)) { - - if (localOptions.length > 1) { - // XXX This is an error condition that needs to be reported - } - - // An alias expands to one or more modules or paths - List expansions = new ArrayList(10); - expansions.add(next); - while (tokenizer.hasMoreTokens()) - expansions.add(tokenizer.nextToken()); - - moduleAliases.put(moduleName, (String[]) expansions.toArray(new String[expansions.size()])); - modules.put(moduleName, new RemoteModule(moduleName, null, repository, null, localOptions, tag, true)); - - } else { - - // The module definition may have a leading directory which can be followed by some files - if (!(next.charAt(0) == '&')) { - String directory = next; - List files = new ArrayList(); - while (tokenizer.hasMoreTokens() && (next.charAt(0) != '&')) { - next = tokenizer.nextToken() ; - if ((next.charAt(0) != '&')) - files.add(next); - } - RemoteModule remoteModule = new RemoteModule(moduleName, null, repository, directory, localOptions, tag, ! files.isEmpty()); - modules.put(moduleName, remoteModule); - if ( ! files.isEmpty()) { - ICVSRemoteResource[] children = new ICVSRemoteResource[files.size()]; - for (int j = 0; j < children.length; j++) { - children[j] = new RemoteFile(remoteModule, Update.STATE_NONE, (String)files.get(j), tag); - remoteModule.setChildren(children); - } - } - } else { - modules.put(moduleName, new RemoteModule(moduleName, null, repository, null, localOptions, tag, true)); - } - - // Record any referenced modules so that can be cross-referenced below - if (next.charAt(0) == '&') { - List children = new ArrayList(10); - children.add(next); - while (tokenizer.hasMoreTokens()) - children.add(tokenizer.nextToken()); - referencedModulesTable.put(moduleName, (String[])children.toArray(new String[children.size()])); - } - } - } - - // Second pass: Cross reference aliases to modules - // XXX Aliases can reference other aliases which confuses the expansion! - Iterator iter = moduleAliases.keySet().iterator(); - while (iter.hasNext()) { - String moduleName = (String)iter.next(); - RemoteModule module = (RemoteModule)modules.get(moduleName); - String[] expansion = (String[])moduleAliases.get(moduleName); - List referencedFolders = new ArrayList(); - boolean expandable = true; - for (int i = 0; i < expansion.length; i++) { - if (expansion[i].charAt(0) == '!') { - // XXX Unsupported for now - expandable = false; - } else { - IPath path = new Path(expansion[i]); - if (path.segmentCount() > 1) { - // XXX Unsupported for now - expandable = false; - } else { - RemoteModule child = (RemoteModule)modules.get(expansion[i]); - if (child == null) { - referencedFolders.add(new RemoteFolder(null, repository, path.toString(), tag)); - } else { - // Need to check if the child is a module alias - if (child.isAlias()) { - // XXX Unsupported for now - expandable = false; - } else { - referencedFolders.add(child); - } - } - } - } - } - if (expandable) { - module.setChildren((ICVSRemoteResource[]) referencedFolders.toArray(new ICVSRemoteResource[referencedFolders.size()])); - } else { - module.setExpandable(false); - } - } - - // Third pass: Cross reference remote modules where necessary - iter = modules.keySet().iterator(); - while (iter.hasNext()) { - String moduleName = (String)iter.next(); - String[] children = (String[])referencedModulesTable.get(moduleName); - if (children != null) { - RemoteModule module = (RemoteModule)modules.get(moduleName); - List referencedFolders = new ArrayList(); - boolean expandable = true; - for (int i = 0; i < children.length; i++) { - RemoteModule child = (RemoteModule)modules.get(children[i].substring(1)); - if (child == null) { - // invalid module definition - expandable = false; - } else if (child.isAlias()) { - // Include alias children in-line - expandable = false; -// referencedFolders.addAll(Arrays.asList(child.getChildren())); - } else { - // XXX not expandable if child has local directory option (-d) - if (Command.findOption(child.getLocalOptions(), "-d") != null) { //$NON-NLS-1$ - expandable = false; - } else { - referencedFolders.add(child); - } - } - } - if (expandable) { - module.setReferencedModules((ICVSRemoteResource[]) referencedFolders.toArray(new ICVSRemoteResource[referencedFolders.size()])); - } else { - module.setExpandable(false); - } - } - } - - return (RemoteModule[])modules.values().toArray(new RemoteModule[modules.size()]); - } - - public RemoteModule(String label, RemoteFolder parent, ICVSRepositoryLocation repository, String repositoryRelativePath, LocalOption[] localOptions, CVSTag tag, boolean isStatic) { - super(parent, - label, - repository, - repositoryRelativePath == null ? FolderSyncInfo.VIRTUAL_DIRECTORY : repositoryRelativePath, - tag, - isStatic); - this.localOptions = localOptions; - this.label = label; - this.expandable = true; - } - - public LocalOption[] getLocalOptions() { - return localOptions; - } - /* - * Override of inherited getMembers in order to combine the physical members with any referenced modules - */ - public ICVSRemoteResource[] getMembers(CVSTag tagName, IProgressMonitor monitor) throws CVSException { - - if ( ! expandable) return new ICVSRemoteResource[0]; - - ICVSRemoteResource[] physicalChildren; - if ( folderInfo.getIsStatic()) { - physicalChildren = getChildren(); - } else { - physicalChildren = super.getMembers(tagName, monitor); - } - ICVSRemoteResource[] allChildren; - if (referencedModules != null && referencedModules.length > 0) { - if (physicalChildren == null) { - allChildren = referencedModules; - } else { - // Combine two sets of children - allChildren = new ICVSRemoteResource[physicalChildren.length + referencedModules.length]; - for (int i = 0; i < physicalChildren.length; i++) { - allChildren[i] = physicalChildren[i]; - } - for (int i = 0; i < referencedModules.length; i++) { - allChildren[i + physicalChildren.length] = referencedModules[i]; - } - } - } else if (physicalChildren != null) { - allChildren = physicalChildren; - } else { - allChildren = new ICVSRemoteResource[0]; - } - return allChildren; - } - - /* - * Set the children to a static set of children - */ - protected void setChildren(ICVSRemoteResource[] children) { - super.setChildren(children); - if ( ! folderInfo.getIsStatic()) - this.folderInfo = new FolderSyncInfo(folderInfo.getRepository(), folderInfo.getRoot(), folderInfo.getTag(), true); - } - - private void setReferencedModules(ICVSRemoteResource[] referencedModules) { - this.referencedModules = referencedModules; - } - - public boolean isAlias() { - return Checkout.ALIAS.isElementOf(localOptions); - } - - /** - * @see ICVSRemoteFolder#isExpandable() - */ - public boolean isExpandable() { - return expandable; - } - - private void setExpandable(boolean expandable) { - this.expandable = expandable; - } - - /** - * @see ICVSRemoteFolder#forTag(CVSTag) - */ - public ICVSRemoteResource forTag(ICVSRemoteFolder parent, CVSTag tagName) { - RemoteModule r = new RemoteModule(label, (RemoteFolder)parent, getRepository(), folderInfo.getRepository(), localOptions, tagName, folderInfo.getIsStatic()); - r.setExpandable(expandable); - if (folderInfo.getIsStatic()) { - ICVSRemoteResource[] children = getChildren(); - if (children != null) { - List taggedChildren = new ArrayList(children.length); - for (int i = 0; i < children.length; i++) { - ICVSRemoteResource resource = children[i]; - taggedChildren.add(((RemoteResource)resource).forTag(r, tagName)); - } - r.setChildren((ICVSRemoteResource[]) taggedChildren.toArray(new ICVSRemoteResource[taggedChildren.size()])); - } - } - if (referencedModules != null) { - List taggedModules = new ArrayList(referencedModules.length); - for (int i = 0; i < referencedModules.length; i++) { - RemoteModule module = (RemoteModule)referencedModules[i]; - taggedModules.add(module.forTag(r, tagName)); - } - r.setReferencedModules((ICVSRemoteResource[]) taggedModules.toArray(new ICVSRemoteResource[taggedModules.size()])); - } - return r; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder#isDefinedModule() - */ - public boolean isDefinedModule() { - return true; - } - /** - * @see java.lang.Object#equals(java.lang.Object) - */ - public boolean equals(Object arg0) { - if (arg0 instanceof RemoteModule) { - RemoteModule module = (RemoteModule) arg0; - return (getName().equals(module.getName()) && super.equals(module)); - } - return false; - } - - /** - * @see java.lang.Object#hashCode() - */ - public int hashCode() { - return super.hashCode() | getName().hashCode(); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSFolder#getChild(java.lang.String) - */ - public ICVSResource getChild(String path) throws CVSException { - if (path.equals(Session.CURRENT_LOCAL_FOLDER) || path.length() == 0) - return this; - // If the path is one segment and it's a referenced module, return the module - // Note: the overriden method will extract the first segment from a multi segment - // path and re-invoke this method so we only need to check for one segment here - // and use the inherited method in the other cases - if (referencedModules != null) { - if (path.indexOf(Session.SERVER_SEPARATOR) == -1) { - for (int i=0;i<referencedModules.length;i++) { - if (referencedModules[i].getName().equals(path)) - return (ICVSResource)referencedModules[i]; - } - } - } - return super.getChild(path); - } - -} 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 deleted file mode 100644 index a93fec439..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/RemoteResource.java +++ /dev/null @@ -1,222 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - - -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.PlatformObject; -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.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteFolder; -import org.eclipse.team.internal.ccvs.core.ICVSRemoteResource; -import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * The purpose of this class and its subclasses is to implement the corresponding - * ICVSRemoteResource interfaces for the purpose of communicating information about - * resources that reside in a CVS repository but have not necessarily been loaded - * locally. - */ -public abstract class RemoteResource extends PlatformObject implements ICVSRemoteResource { - - protected RemoteFolder parent; - protected String name; - - // relative synchronization state calculated by server of this remote file compare to the current local - // workspace copy. - private int workspaceSyncState = Update.STATE_NONE; - - /** - * Constructor for RemoteResource. - */ - public RemoteResource(RemoteFolder parent, String name) { - this.parent = parent; - this.name = name; - } - - /* - * @see ICVSRemoteResource#getName() - */ - public String getName() { - return name; - } - - /* - * @see ICVSResource#getRelativePath(ICVSFolder) - */ - public String getRelativePath(ICVSFolder ancestor) throws CVSException { - return Util.appendPath(parent.getRelativePath(ancestor), getName()); - } - - /* - * @see ICVSRemoteResource#getParent() - */ - public ICVSRemoteResource getRemoteParent() { - return parent; - } - - public abstract String getRepositoryRelativePath(); - - public abstract ICVSRepositoryLocation getRepository(); - - public int getWorkspaceSyncState() { - return workspaceSyncState; - } - - public void setWorkspaceSyncState(int workspaceSyncState) { - this.workspaceSyncState = workspaceSyncState; - } - - /* - * @see ICVSResource#delete() - */ - public void delete() { - // For now, do nothing but we could provide this in the future. - } - - /* - * @see ICVSResource#exists() - * - * This method is used by the Command framework so it must return true so that - * the proper information gets sent to the server. (i.e. it is used to fake that - * the file exists locally so cvs commands can be used to retrieve information about - * the remote resource from the server) - */ - public boolean exists() { - return true; - } - - /* - * @see ICVSRemoteResource#exists(IProgressMonitor) - */ - public boolean exists(IProgressMonitor monitor) throws TeamException { - return parent.exists(this, monitor); - } - - /* - * @see ICVSResource#getParent() - */ - public ICVSFolder getParent() { - return parent; - } - - /* - * @see ICVSResource#isIgnored() - */ - public boolean isIgnored() { - return false; - } - - /* - * @see ICVSResource#isManaged() - */ - public boolean isManaged() { - return parent != null; - } - - public boolean isModified(IProgressMonitor monitor) throws CVSException { - // it is safe to always consider a remote file handle as modified. This will cause any - // CVS command to fetch new contents from the server. - return true; - } - - /* - * @see ICVSResource#unmanage() - */ - public void unmanage(IProgressMonitor monitor) throws CVSException { - // do nothing - } - - /* - * @see ICVSResource#getSyncInfo() - */ - public abstract ResourceSyncInfo getSyncInfo(); - - /* - * @see ICVSResource#setSyncInfo(ResourceSyncInfo) - */ - public void setSyncInfo(ResourceSyncInfo info, int modificationState) { - // ensure that clients are not trying to set sync info on remote handles. - Assert.isTrue(false); - } - - public boolean equals(Object target) { - if (this == target) - return true; - if (!(target instanceof RemoteResource)) - return false; - RemoteResource remote = (RemoteResource) target; - return remote.isContainer() == isContainer() && remote.getRepositoryRelativePath().equals(getRepositoryRelativePath()); - } - /* - * @see ICVSResource#setIgnored() - */ - public void setIgnored() throws CVSException { - // ensure that clients are not trying to set sync info on remote handles. - Assert.isTrue(false); - } - - /* - * @see ICVSResource#setIgnoredAs(String) - */ - public void setIgnoredAs(String pattern) throws CVSException { - // ensure that clients are not trying to set sync info on remote handles. - Assert.isTrue(false); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.ICVSResource#getIResource() - */ - public IResource getIResource() throws CVSException { - return null; - } - - /** - * Return a copy of the receiver that is associated with the given tag. The parent - * should be a copy of the receiver's parent which has been copied to the same tag. - * - * @param parent - * @param tagName - * @return ICVSRemoteFolder - */ - public abstract ICVSRemoteResource forTag(ICVSRemoteFolder parent, CVSTag tagName); - - /** - * @see java.lang.Object#hashCode() - */ - public int hashCode() { - return getRepositoryRelativePath().hashCode(); - } - - /** - * Method which returns an array of bytes that can be used to recreate the remote handle. - * To recreate the remote handle, invoke the <code>fromBytes</code> method on either - * RemoteFolder or RemoteFile. - * - * TODO: It would be nice to have a method on RmeoteResource to recreate the handles - * but the file requires the bytes for the parent folder since this folder may not - * exist locally. - * - * @return - */ - abstract public byte[] getSyncBytes(); - - public String toString() { - return "Remote " + (isContainer() ? "Folder: " : "File: ") + getName(); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SessionPropertySyncInfoCache.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SessionPropertySyncInfoCache.java deleted file mode 100644 index 7bcabfd51..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SessionPropertySyncInfoCache.java +++ /dev/null @@ -1,454 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceStatus; -import org.eclipse.core.resources.IResourceVisitor; -import org.eclipse.core.resources.ISaveContext; -import org.eclipse.core.resources.ISaveParticipant; -import org.eclipse.core.resources.ISynchronizer; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSDecoratorEnablementListener; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.FileNameMatcher; -import org.eclipse.team.internal.ccvs.core.util.SyncFileWriter; - -/** - * This cache uses session properties to hold the bytes representing the sync - * info. In addition when the workbench closes or a project is closed, the dirty - * state for all cvs managed folders are persisted using the resource's plugin - * synchronizer. - */ -/*package*/ class SessionPropertySyncInfoCache extends SyncInfoCache - implements ISaveParticipant, ICVSDecoratorEnablementListener { - - // key used on a folder to indicate that the resource sync has been cahced for it's children - private static final QualifiedName RESOURCE_SYNC_CACHED_KEY = new QualifiedName(CVSProviderPlugin.ID, "resource-sync-cached"); //$NON-NLS-1$ - private static final Object RESOURCE_SYNC_CACHED = new Object(); - - /*package*/ static final FileNameMatcher NULL_IGNORES = new FileNameMatcher(); - private static final FolderSyncInfo NULL_FOLDER_SYNC_INFO = new FolderSyncInfo("", "", null, false); //$NON-NLS-1$ //$NON-NLS-2$ - - private QualifiedName FOLDER_DIRTY_STATE_KEY = new QualifiedName(CVSProviderPlugin.ID, "folder-dirty-state-cached"); //$NON-NLS-1$ - private boolean isDecoratorEnabled = true; - private boolean hasBeenSaved = false; - - /*package*/ SessionPropertySyncInfoCache() { - try { - // this save participant is removed when the plugin is shutdown. - ResourcesPlugin.getWorkspace().addSaveParticipant(CVSProviderPlugin.getPlugin(), this); - CVSProviderPlugin.getPlugin().addDecoratorEnablementListener(this); - - final ISynchronizer synchronizer = ResourcesPlugin.getWorkspace().getSynchronizer(); - synchronizer.add(FOLDER_DIRTY_STATE_KEY); - } catch (CoreException e) { - CVSProviderPlugin.log(e); - } - } - - /** - * If not already cached, loads and caches the folder ignores sync for the container. - * Folder must exist and must not be the workspace root. - * - * @param container the container - * @return the folder ignore patterns, or an empty array if none - */ - /*package*/ FileNameMatcher cacheFolderIgnores(IContainer container) throws CVSException { - // don't try to load if the information is already cached - FileNameMatcher matcher = (FileNameMatcher)safeGetSessionProperty(container, IGNORE_SYNC_KEY); - if (matcher == null) { - // read folder ignores and remember it - String[] ignores = SyncFileWriter.readCVSIgnoreEntries(container); - if (ignores == null) { - matcher = NULL_IGNORES; - } else { - matcher = new FileNameMatcher(ignores); - } - safeSetSessionProperty(container, IGNORE_SYNC_KEY, matcher); - } - return matcher; - } - - /*package*/ boolean isFolderSyncInfoCached(IContainer container) throws CVSException { - return safeGetSessionProperty(container, FOLDER_SYNC_KEY) != null; - } - - /*package*/ boolean isResourceSyncInfoCached(IContainer container) throws CVSException { - return safeGetSessionProperty(container, RESOURCE_SYNC_CACHED_KEY) != null; - } - - /*package*/ void setResourceSyncInfoCached(IContainer container) throws CVSException { - safeSetSessionProperty(container, RESOURCE_SYNC_CACHED_KEY, RESOURCE_SYNC_CACHED); - } - - /** - * Returns the folder sync info for the container; null if none. - * Folder must exist and must not be the workspace root. - * The folder sync info for the container MUST ALREADY BE CACHED. - * - * @param container the container - * @return the folder sync info for the folder, or null if none. - * @see #cacheFolderSync - */ - /*package*/ FolderSyncInfo getCachedFolderSync(IContainer container) throws CVSException { - FolderSyncInfo info = (FolderSyncInfo)safeGetSessionProperty(container, FOLDER_SYNC_KEY); - if (info == null) { - // There should be sync info but it was missing. Report the error - throw new CVSException(Policy.bind("EclipseSynchronizer.folderSyncInfoMissing", container.getFullPath().toString())); //$NON-NLS-1$ - } - if (info == NULL_FOLDER_SYNC_INFO) return null; - return info; - } - - /** - * Purges the cache recursively for all resources beneath the container. - * There must not be any pending uncommitted changes. - */ - /*package*/ void purgeCache(IContainer container, boolean deep) throws CVSException { - if (! container.exists()) return; - try { - if (container.getType() != IResource.ROOT) { - safeSetSessionProperty(container, IGNORE_SYNC_KEY, null); - safeSetSessionProperty(container, FOLDER_SYNC_KEY, null); - safeSetSessionProperty(container, RESOURCE_SYNC_CACHED_KEY, null); - } - IResource[] members = container.members(); - for (int i = 0; i < members.length; i++) { - IResource resource = members[i]; - purgeResourceSyncCache(resource); - if (deep && resource.getType() != IResource.FILE) { - purgeCache((IContainer) resource, deep); - } - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /* package*/ void purgeResourceSyncCache(IResource resource) throws CVSException { - safeSetSessionProperty(resource, RESOURCE_SYNC_KEY, null); - } - - /** - * Sets the array of folder ignore patterns for the container, must not be null. - * Folder must exist and must not be the workspace root. - * - * @param container the container - * @param ignores the array of ignore patterns - */ - /*package*/ void setCachedFolderIgnores(IContainer container, String[] ignores) throws CVSException { - safeSetSessionProperty(container, IGNORE_SYNC_KEY, new FileNameMatcher(ignores)); - } - - - /** - * Sets the folder sync info for the container; if null, deletes it. - * Folder must exist and must not be the workspace root. - * The folder sync info for the container need not have previously been cached. - * - * @param container the container - * @param info the new folder sync info - */ - /*package*/ void setCachedFolderSync(IContainer container, FolderSyncInfo info) throws CVSException { - if (!container.exists()) return; - if (info == null) { - info = NULL_FOLDER_SYNC_INFO; - } - safeSetSessionProperty(container, FOLDER_SYNC_KEY, info); - } - - /*package*/ void setDirtyIndicator(IResource resource, String indicator) throws CVSException { - if (resource.getType() == IResource.FILE) { - internalSetDirtyIndicator((IFile)resource, indicator); - } else { - internalSetDirtyIndicator((IContainer)resource, indicator); - } - } - /*package*/ String getDirtyIndicator(IResource resource) throws CVSException { - if (resource.getType() == IResource.FILE) { - return internalGetDirtyIndicator((IFile)resource); - } else { - return internalGetDirtyIndicator((IContainer)resource); - } - } - - private void internalSetDirtyIndicator(IFile file, String indicator) throws CVSException { - safeSetSessionProperty(file, IS_DIRTY, indicator); - } - - private String internalGetDirtyIndicator(IFile file) throws CVSException { - String di = (String)safeGetSessionProperty(file, IS_DIRTY); - if(di == null) { - di = RECOMPUTE_INDICATOR; - } - return di; - } - - private void internalSetDirtyIndicator(IContainer container, String indicator) throws CVSException { - safeSetSessionProperty(container, IS_DIRTY, indicator); - } - - private String internalGetDirtyIndicator(IContainer container) throws CVSException { - try { - String di = (String)safeGetSessionProperty(container, IS_DIRTY); - - // if the session property is not available then restore from persisted sync info. At this - // time the sync info is not flushed because we don't want the workspace to generate - // a delta. - if(di == null) { - byte [] diBytes = ResourcesPlugin.getWorkspace().getSynchronizer().getSyncInfo(FOLDER_DIRTY_STATE_KEY, container); - if(diBytes != null) { - di = new String(diBytes); - if(di.equals(NOT_DIRTY_INDICATOR)) { - di = NOT_DIRTY_INDICATOR; - } else if(di.equals(IS_DIRTY_INDICATOR)) { - di = IS_DIRTY_INDICATOR; - } else { - di = RECOMPUTE_INDICATOR; - } - } else { - di = RECOMPUTE_INDICATOR; - } - setDirtyIndicator(container, di); - } - return di; - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /* - * Flush dirty cache for the resource - */ - /*package*/ void flushDirtyCache(IResource resource) throws CVSException { - if (resource.exists()) { - if (resource.getType() == IResource.FILE) { - safeSetSessionProperty(resource, IS_DIRTY, null); - } else { - safeSetSessionProperty(resource, IS_DIRTY, null); - flushDirtyStateFromDisk((IContainer)resource); - } - } - } - - /** - * Method isSyncInfoLoaded returns true if all the sync info for the - * provided resources is loaded into the internal cache. - * - * @param resources - * @param i - * @return boolean - */ - /*package*/ boolean isSyncInfoLoaded(IContainer parent) throws CVSException { - if (parent.getFolder(new Path(SyncFileWriter.CVS_DIRNAME)).exists()) { - if (safeGetSessionProperty(parent, RESOURCE_SYNC_CACHED_KEY) == null) - return false; - if (safeGetSessionProperty(parent, FOLDER_SYNC_KEY) == null) - return false; -// if (parent.getSessionProperty(IGNORE_SYNC_KEY) == null) -// return false; - } - return true; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#getCachedSyncBytes(org.eclipse.core.resources.IResource) - */ - /*package*/ byte[] getCachedSyncBytes(IResource resource) throws CVSException { - return (byte[])safeGetSessionProperty(resource, RESOURCE_SYNC_KEY); - } - - Object safeGetSessionProperty(IResource resource, QualifiedName key) throws CVSException { - try { - return resource.getSessionProperty(key); - } catch (CoreException e) { - IStatus status = e.getStatus(); - if(status != null) { - int code = e.getStatus().getCode(); - if(code != IResourceStatus.RESOURCE_NOT_LOCAL || - code != IResourceStatus.RESOURCE_NOT_FOUND) { - // ignore error since a phantom would of been created - // and we can safely ignore these cases - return null; - } - } - // some other error we did not expect - throw CVSException.wrapException(e); - } - } - - void safeSetSessionProperty(IResource resource, QualifiedName key, Object value) throws CVSException { - try { - resource.setSessionProperty(key, value); - } catch (CoreException e) { - IStatus status = e.getStatus(); - if(status != null) { - int code = e.getStatus().getCode(); - if(code == IResourceStatus.RESOURCE_NOT_LOCAL || - code == IResourceStatus.RESOURCE_NOT_FOUND) { - // ignore error since a phantom would of been created - // and we can safely ignore these cases - } - // some other error we did not expect - throw CVSException.wrapException(e); - } - } - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#setCachedSyncBytes(org.eclipse.core.resources.IResource, byte[]) - */ - /*package*/ void setCachedSyncBytes(IResource resource, byte[] syncBytes) throws CVSException { - safeSetSessionProperty(resource, RESOURCE_SYNC_KEY, syncBytes); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#isDirtyCacheFlushed(org.eclipse.core.resources.IContainer) - */ - boolean isDirtyCacheFlushed(IContainer resource) throws CVSException { - if (resource.exists()) { - return getDirtyIndicator(resource) == RECOMPUTE_INDICATOR; - } - return false; - } - - /* (non-Javadoc) - * @see org.eclipse.core.resources.ISaveParticipant#doneSaving(org.eclipse.core.resources.ISaveContext) - */ - public void doneSaving(ISaveContext context) { - } - - /* (non-Javadoc) - * @see org.eclipse.core.resources.ISaveParticipant#prepareToSave(org.eclipse.core.resources.ISaveContext) - */ - public void prepareToSave(ISaveContext context) throws CoreException { - } - - /* (non-Javadoc) - * @see org.eclipse.core.resources.ISaveParticipant#rollback(org.eclipse.core.resources.ISaveContext) - */ - public void rollback(ISaveContext context) { - } - - /* Called when the workbench is shutdown or projects are closed. The dirty state - * of folders is persisted, using sync info, so that at startup or project open - * the folder state can be quickly calculated. This is mainly for improving decorator - * performance. - * @see org.eclipse.core.resources.ISaveParticipant#saving(org.eclipse.core.resources.ISaveContext) - */ - public void saving(ISaveContext context) throws CoreException { - boolean fullSave = (context.getKind() == ISaveContext.FULL_SAVE); - boolean projectSave = (context.getKind() == ISaveContext.PROJECT_SAVE); - - if(isDecoratorEnabled && (projectSave || fullSave)) { - // persist all session properties for folders into sync info. - final ISynchronizer synchronizer = ResourcesPlugin.getWorkspace().getSynchronizer(); - - // traverse the workspace looking for CVS managed projects or just the - // specific projects being closed - IProject[] projects; - if(projectSave) { - projects = new IProject[1]; - projects[0] = context.getProject(); - } else { - projects = ResourcesPlugin.getWorkspace().getRoot().getProjects(); - } - for (int i = 0; i < projects.length; i++) { - IProject project = projects[i]; - RepositoryProvider provider = RepositoryProvider.getProvider( - project, - CVSProviderPlugin.getTypeId()); - - // found a project managed by CVS, convert each session property on a - // folder to a sync object. - if (provider != null) { - project.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - if(resource.getType() != IResource.FILE) { - String di = null; - try { - di = getDirtyIndicator(resource); - } catch (CVSException e) { - // continue traversal - CVSProviderPlugin.log(e); - } - if(di != null) { - synchronizer.setSyncInfo(FOLDER_DIRTY_STATE_KEY, resource, di.getBytes()); - } - } - return true; - } - }); - } - } - hasBeenSaved = true; - } - } - - /* (non-Javadoc) - * @see ICVSDecoratorEnablementListener#decoratorEnablementChanged(boolean) - */ - public void decoratorEnablementChanged(boolean enabled) { - isDecoratorEnabled = enabled; - if(!enabled && !hasBeenSaved) { - // flush the dirty state cache for all managed resources - IProject[] projects = ResourcesPlugin.getWorkspace().getRoot().getProjects(); - for (int i = 0; i < projects.length; i++) { - IProject project = projects[i]; - RepositoryProvider provider = RepositoryProvider.getProvider( - project, - CVSProviderPlugin.getTypeId()); - - if (provider != null) { - try { - project.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - try { - flushDirtyCache(resource); - } catch(CVSException e) { - throw new CoreException(e.getStatus()); - } - return true; - } - }); - } catch (CoreException e) { - CVSProviderPlugin.log(e); - } - } - } - } - } - - /* - * Called to clear the folder dirty state from the resource sync tree and stop persisting - * these values to disk. - */ - private void flushDirtyStateFromDisk(IContainer container) { - final ISynchronizer synchronizer = ResourcesPlugin.getWorkspace().getSynchronizer(); - try { - synchronizer.flushSyncInfo(FOLDER_DIRTY_STATE_KEY, container, IResource.DEPTH_INFINITE); - } catch (CoreException e) { - CVSProviderPlugin.log(e); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SyncInfoCache.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SyncInfoCache.java deleted file mode 100644 index f639cc532..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SyncInfoCache.java +++ /dev/null @@ -1,126 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.core.runtime.Status; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; - -/** - * The low level cache provides the sync info as bytes - */ -/*package*/ abstract class SyncInfoCache { - - // the resources plugin synchronizer is used to cache and possibly persist. These - // are keys for storing the sync info. - /*package*/ static final QualifiedName FOLDER_SYNC_KEY = new QualifiedName(CVSProviderPlugin.ID, "folder-sync"); //$NON-NLS-1$ - /*package*/ static final QualifiedName RESOURCE_SYNC_KEY = new QualifiedName(CVSProviderPlugin.ID, "resource-sync"); //$NON-NLS-1$ - /*package*/ static final QualifiedName IGNORE_SYNC_KEY = new QualifiedName(CVSProviderPlugin.ID, "folder-ignore"); //$NON-NLS-1$ - - /*package*/ static final byte[][] EMPTY_RESOURCE_SYNC_INFOS = new byte[0][0]; - - /*package*/ static final QualifiedName IS_DIRTY = new QualifiedName(CVSProviderPlugin.ID, "is-dirty"); //$NON-NLS-1$ - /*package*/ static final String IS_DIRTY_INDICATOR = "d"; //$NON-NLS-1$ - /*package*/ static final String NOT_DIRTY_INDICATOR = "c"; //$NON-NLS-1$ - /*package*/ static final String RECOMPUTE_INDICATOR = "r"; //$NON-NLS-1$ - - /*package*/ static final IStatus STATUS_OK = new Status(IStatus.OK, CVSProviderPlugin.ID, 0, Policy.bind("ok"), null); //$NON-NLS-1$ - - /** - * Returns the folder sync info for the container; null if none. - * Folder must exist and must not be the workspace root. - * The folder sync info for the container MUST ALREADY BE CACHED. - * - * @param container the container - * @return the folder sync info for the folder, or null if none. - * @see #cacheFolderSync - */ - /*package*/ abstract FolderSyncInfo getCachedFolderSync(IContainer container) throws CVSException; - - /** - * Sets the folder sync info for the container; if null, deletes it. - * Folder must exist and must not be the workspace root. - * The folder sync info for the container need not have previously been - * cached. - * - * @param container the container - * @param info the new folder sync info - */ - /*package*/ abstract void setCachedFolderSync(IContainer container, FolderSyncInfo info) throws CVSException; - - /** - * Returns the resource sync info for the given resource. The resource sync - * info for the resource MUST ALREADY BE CACHED. - * - * @param resource the resource - * @return the bytes containing the resource's sync info - * @see #cacheResourceSyncForChildren - */ - /*package*/ abstract byte[] getCachedSyncBytes(IResource resource) throws CVSException; - - /** - * Sets the resource sync info for the resource; if null, deletes it. Parent - * must exist and must not be the workspace root. The resource sync info for - * the resource MUST ALREADY BE CACHED. - * - * @param resource the resource - * @param syncBytes the bytes containing the new resource sync info - * @see #cacheResourceSyncForChildren - */ - /*package*/ abstract void setCachedSyncBytes(IResource resource, byte[] syncBytes) throws CVSException; - - /*package*/ abstract String getDirtyIndicator(IResource resource) throws CVSException; - - /*package*/ abstract void setDirtyIndicator(IResource resource, String indicator) throws CVSException; - - /*package*/ abstract void flushDirtyCache(IResource resource) throws CVSException; - - /*package*/ abstract boolean isSyncInfoLoaded(IContainer parent) throws CVSException; - - /** - * Query the low level cache to see if the sync info for the provided - * container is loaded. - * - * @param container - * @return boolean - * @throws CVSException - */ - /*package*/ abstract boolean isFolderSyncInfoCached(IContainer container) throws CVSException; - - /** - * Query the low level cache to see if the sync info for the direct children - * of the provided container is loaded. - * - * @param container - * @return boolean - */ - /*package*/ abstract boolean isResourceSyncInfoCached(IContainer container) throws CVSException; - - /** - * Indicate to the low level cache that the sync info for all it's direct - * children have been set so they match what is on disk. - * - * @param container - */ - /*package*/ abstract void setResourceSyncInfoCached(IContainer container) throws CVSException; - - /** - * @param resource - * @return boolean - */ - /*package*/ abstract boolean isDirtyCacheFlushed(IContainer resource) throws CVSException; -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SynchronizerSyncInfoCache.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SynchronizerSyncInfoCache.java deleted file mode 100644 index 42640195f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/resources/SynchronizerSyncInfoCache.java +++ /dev/null @@ -1,291 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.resources; - -import java.io.ByteArrayInputStream; -import java.io.DataInputStream; -import java.io.IOException; -import java.util.HashMap; -import java.util.Iterator; -import java.util.Map; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.ISynchronizer; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; -import org.eclipse.team.internal.ccvs.core.util.SyncFileWriter; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * This cache uses session properties to hold the bytes representing the sync - * info - */ -/*package*/ class SynchronizerSyncInfoCache extends SyncInfoCache { - - public SynchronizerSyncInfoCache() { - getWorkspaceSynchronizer().add(FOLDER_SYNC_KEY); - getWorkspaceSynchronizer().add(RESOURCE_SYNC_KEY); - } - /** - * Return the Eclipse Workspace Synchronizer (from org.eclipse.core.resources) - */ - private ISynchronizer getWorkspaceSynchronizer() { - return ResourcesPlugin.getWorkspace().getSynchronizer(); - } - - /** - * Convert a byte array that was created using getBytes(Map) - * into a Map of ResourceSyncInfo - */ - private byte[][] getResourceSyncInfo(byte[] bytes) throws CVSException { - byte[][] infos = SyncFileWriter.readLines(new ByteArrayInputStream(bytes)); - // check to make sure the info is not stored in the old format - if (infos.length != 0) { - byte[] firstLine = infos[0]; - if (firstLine.length != 0 && (firstLine[0] != (byte)'/' && firstLine[0] != (byte)'D')) { - Map oldInfos = getResourceSyncInfoMap(bytes); - infos = new byte[oldInfos.size()][]; - int i = 0; - for (Iterator iter = oldInfos.values().iterator(); iter.hasNext();) { - ResourceSyncInfo element = (ResourceSyncInfo) iter.next(); - infos[i++] = element.getBytes(); - } - // We can't convert the info to the new format because the caller - // may either not be in a workspace runnable or the resource tree - // may be closed for modification - } - } - return infos; - } - - /** - * ResourceSyncInfo used to be stored as a Map of ResourceSyncInfo. - * We need to be able to retrieve that info the way it was and - * convert it to the new way. - * - * Convert a byte array that was created using - * getBytes(Map) into a Map of ResourceSyncInfo - */ - private Map getResourceSyncInfoMap(byte[] bytes) throws CVSException { - ByteArrayInputStream in = new ByteArrayInputStream(bytes); - DataInputStream dis = new DataInputStream(in); - Map result = new HashMap(); - try { - int size = dis.readInt(); - for (int i = 0; i < size; i++) { - ResourceSyncInfo info = new ResourceSyncInfo(dis.readUTF(), null, null); - result.put(info.getName(), info); - } - } catch (IOException e) { - throw CVSException.wrapException(e); - } - return result; - } - - /*package*/ void flush(IProject project) throws CVSException { - purgeCache(project, true); - } - - /** - * Method flush. - * @param folder - */ - /*package*/ void flush(IFolder folder) throws CVSException { - purgeCache(folder, false); - } - - /** - * Returns the folder sync info for the container; null if none. - * Folder must exist and must not be the workspace root. - * The folder sync info for the container MUST ALREADY BE CACHED. - * - * @param container the container - * @return the folder sync info for the folder, or null if none. - * @see #cacheFolderSync - */ - /*package*/ FolderSyncInfo getCachedFolderSync(IContainer container) throws CVSException { - try { - byte[] bytes = getWorkspaceSynchronizer().getSyncInfo(FOLDER_SYNC_KEY, container); - if (bytes == null) return null; - return FolderSyncInfo.getFolderSyncInfo(bytes); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * Sets the folder sync info for the container; if null, deletes it. - * Folder must exist and must not be the workspace root. - * The folder sync info for the container need not have previously been - * cached. - * - * @param container the container - * @param info the new folder sync info - */ - /*package*/ void setCachedFolderSync(IContainer container, FolderSyncInfo info) throws CVSException { - try { - if (info == null) { - if (container.exists() || container.isPhantom()) { - getWorkspaceSynchronizer().flushSyncInfo(FOLDER_SYNC_KEY, container, IResource.DEPTH_ZERO); - } - } else { - getWorkspaceSynchronizer().setSyncInfo(FOLDER_SYNC_KEY, container, info.getBytes()); - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#getCachedSyncBytes(org.eclipse.core.resources.IResource) - */ - /*package*/ byte[] getCachedSyncBytes(IResource resource) throws CVSException { - try { - return getWorkspaceSynchronizer().getSyncInfo(RESOURCE_SYNC_KEY, resource); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#setCachedSyncBytes(org.eclipse.core.resources.IResource, byte[]) - */ - /*package*/ void setCachedSyncBytes(IResource resource, byte[] syncBytes) throws CVSException { - byte[] oldBytes = getCachedSyncBytes(resource); - try { - if (syncBytes == null) { - if (oldBytes != null && (resource.exists() || resource.isPhantom())) { - getWorkspaceSynchronizer().flushSyncInfo(RESOURCE_SYNC_KEY, resource, IResource.DEPTH_ZERO); - } - } else { - // ensure that the sync info is not already set to the same thing. - // We do this to avoid causing a resource delta when the sync info is - // initially loaded (i.e. the synchronizer has it and so does the Entries file - if (oldBytes == null || !Util.equals(syncBytes, oldBytes)) { - getWorkspaceSynchronizer().setSyncInfo(RESOURCE_SYNC_KEY, resource, syncBytes); - } - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#getDirtyIndicator(org.eclipse.core.resources.IResource) - */ - String getDirtyIndicator(IResource resource) throws CVSException { - if (resource.getType() == IResource.FILE) { - // a phantom file is dirty if it was managed before it was deleted - return getCachedSyncBytes(resource) != null ? - IS_DIRTY_INDICATOR : - NOT_DIRTY_INDICATOR; - } else { - return calculateDirtyCountForPhantomFolder((IContainer)resource); - } - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#setDirtyIndicator(org.eclipse.core.resources.IResource, java.lang.String) - */ - void setDirtyIndicator(IResource resource, String indicator) throws CVSException { - // We don't cache the dirty count for folders because it would cause - // resource delta's in the decorator thread and possible deadlock. - } - - /*package*/ void flushDirtyCache(IResource container) throws CVSException { - } - - /*package*/ boolean isSyncInfoLoaded(IContainer parent) throws CVSException { - return true; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#isResourceSyncInfoCached(org.eclipse.core.resources.IContainer) - */ - boolean isResourceSyncInfoCached(IContainer container) throws CVSException { - // the sync info is always cahced when using the synchronizer - return true; - } - - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#setResourceSyncInfoCached(org.eclipse.core.resources.IContainer) - */ - void setResourceSyncInfoCached(IContainer container) throws CVSException { - // do nothing - } - /** - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#isFolderSyncInfoCached(org.eclipse.core.resources.IContainer) - */ - boolean isFolderSyncInfoCached(IContainer container) throws CVSException { - return true; - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.resources.SyncInfoCache#isDirtyCacheFlushed(org.eclipse.core.resources.IContainer) - */ - boolean isDirtyCacheFlushed(IContainer resource) throws CVSException { - return false; - } - - /* - * Calculate the dirty count for the given phantom folder, performing any - * necessary calculations on the childen as well - */ - private String calculateDirtyCountForPhantomFolder(IContainer parent) throws CVSException { - ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor(parent); - if(getCachedFolderSync(parent) == null) { - return NOT_DIRTY_INDICATOR; - } - - String indicator = NOT_DIRTY_INDICATOR; - ICVSResource[] children = cvsFolder.members(ICVSFolder.MANAGED_MEMBERS | ICVSFolder.PHANTOM_MEMBERS); - for (int i = 0; i < children.length; i++) { - ICVSResource resource = children[i]; - // keep looking into phantom folders until a managed phantom file - // is found. - if (resource.isFolder()) { - indicator = calculateDirtyCountForPhantomFolder((IContainer)resource.getIResource()); - } else { - // Any non-existant managed files are dirty (outgoing deletion) - indicator = IS_DIRTY_INDICATOR; - break; - } - } - return indicator; - } - - /** - * @param root - * @param deep - */ - public void purgeCache(IContainer root, boolean deep) throws CVSException { - int depth = deep ? IResource.DEPTH_INFINITE : IResource.DEPTH_ZERO; - try { - if (root.exists() || root.isPhantom()) { - getWorkspaceSynchronizer().flushSyncInfo(RESOURCE_SYNC_KEY, root, depth); - } - if (root.exists() || root.isPhantom()) { - getWorkspaceSynchronizer().flushSyncInfo(FOLDER_SYNC_KEY, root, depth); - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/BaseSynchronizer.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/BaseSynchronizer.java deleted file mode 100644 index 0328f4b33..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/BaseSynchronizer.java +++ /dev/null @@ -1,72 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.resources.EclipseSynchronizer; - -/** - * A base sychronizer provides access to the base sync bytes for the - * resources in the local workspace - */ -public class BaseSynchronizer extends ResourceSynchronizer { - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer#getSyncBytes(org.eclipse.core.resources.IResource) - */ - public byte[] getSyncBytes(IResource resource) throws CVSException { - if (resource.getType() == IResource.FILE) { - // For a file, return the entry line - byte[] bytes = EclipseSynchronizer.getInstance().getSyncBytes(resource); - if (bytes != null) { - // Use the base sync info (i.e. no deletion or addition) - if (ResourceSyncInfo.isDeletion(bytes)) { - bytes = ResourceSyncInfo.convertFromDeletion(bytes); - } else if (ResourceSyncInfo.isAddition(bytes)) { - bytes = null; - } - } - return bytes; - } else { - // For a folder, return the folder sync info bytes - FolderSyncInfo info = EclipseSynchronizer.getInstance().getFolderSync((IContainer)resource); - if (info == null) return null; - return info.getBytes(); - } - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer#getSyncName() - */ - protected QualifiedName getSyncName() { - return new QualifiedName(CVSProviderPlugin.ID, "workspace"); // $NON-NLS-1$ - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer#refresh(org.eclipse.core.resources.IResource[], int, boolean, org.eclipse.core.runtime.IProgressMonitor) - */ - public IResource[] refresh( - IResource[] resources, - int depth, - boolean cacheFileContentsHint, - IProgressMonitor monitor) - throws TeamException { - - // TODO Ensure that file contents are cached for modified local files - return super.refresh(resources, depth, cacheFileContentsHint, monitor); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/BaserevInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/BaserevInfo.java deleted file mode 100644 index 3166344a3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/BaserevInfo.java +++ /dev/null @@ -1,83 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * This class represents the information in the CVS/Baserev file - */ -public class BaserevInfo { - private static final String BASEREV_PREFIX = "B"; //$NON-NLS-1$ - - private String name; - private String revision; - - public BaserevInfo(String entryLine) throws CVSException { - setEntryLine(entryLine); - } - - public BaserevInfo(String name, String revision) { - this.name = name; - this.revision = revision; - } - /** - * Return the entry line as it appears in the CVS/Baserev file - * @return String - */ - public String getEntryLine() { - StringBuffer result = new StringBuffer(); - result.append(BASEREV_PREFIX); - result.append(name); - result.append(ResourceSyncInfo.SEPARATOR); - result.append(revision); - return result.toString(); - } - private void setEntryLine(String entryLine) throws CVSException { - if(entryLine.startsWith(BASEREV_PREFIX)) { - entryLine = entryLine.substring(1); - } - String[] strings = Util.parseIntoSubstrings(entryLine, ResourceSyncInfo.SEPARATOR); - if(strings.length != 2) { - throw new CVSException(Policy.bind("BaseRevInfo.malformedEntryLine", entryLine)); //$NON-NLS-1$ - } - - name = strings[0]; - - if(name.length()==0) { - throw new CVSException(Policy.bind("BaseRevInfo.malformedEntryLine", entryLine)); //$NON-NLS-1$ - } - - revision = strings[1]; - - if(revision.length()==0) { - throw new CVSException(Policy.bind("BaseRevInfo.malformedEntryLine", entryLine)); //$NON-NLS-1$ - } - } - /** - * Returns the name. - * @return String - */ - public String getName() { - return name; - } - - /** - * Returns the revision. - * @return String - */ - public String getRevision() { - return revision; - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/FolderSyncInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/FolderSyncInfo.java deleted file mode 100644 index 544ee08b0..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/FolderSyncInfo.java +++ /dev/null @@ -1,304 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - - -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.DataInputStream; -import java.io.DataOutputStream; -import java.io.IOException; - -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSEntryLineTag; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Value (immutable) object that represents workspace state information about the contents of a - * folder that was retreived from a CVS repository. It is a specialized representation of the files from - * the CVS sub-directory that contain folder specific connection information (e.g. Root, Repository, Tag). - * - * @see ICVSFolder#getFolderSyncInfo() - */ -public class FolderSyncInfo { - - // The Repository value for virtual directories (i.e. local with no corresponding remote) - public static final String VIRTUAL_DIRECTORY = "CVSROOT/Emptydir"; //$NON-NLS-1$ - - // relative path of this folder in the repository, project1/folder1/folder2 - protected String repository; - - // :pserver:user@host:/home/user/repo - private String root; - - // sticky tag (e.g. version, date, or branch tag applied to folder) - private CVSEntryLineTag tag; - - // if true then it means only part of the folder was fetched from the repository, and CVS will not create - // additional files in that folder. - private boolean isStatic; - - /** - * Construct a folder sync object. - * - * @param repo the relative path of this folder in the repository, cannot be <code>null</code>. - * @param root the location of the repository, cannot be <code>null</code>. - * @param tag the tag set for the folder or <code>null</code> if there is no tag applied. - * @param isStatic to indicate is only part of the folder was fetched from the server. - */ - public FolderSyncInfo(String repo, String root, CVSTag tag, boolean isStatic) { - Assert.isNotNull(repo); - Assert.isNotNull(root); - this.repository = repo; - // intern the root so that caching of FolderSyncInfos for folders will use less space - this.root = root.intern(); - ensureRepositoryRelativeToRoot(); - this.isStatic = isStatic; - setTag(tag); - } - - /** - * Method ensureRepositoryRelativeToRoot. - */ - private void ensureRepositoryRelativeToRoot() { - String rootDir; - try { - rootDir = getRootDirectory(); - } catch (CVSException e) { - // Ignore the for now. Using the root will show the error to the user. - return; - } - if (repository.startsWith(rootDir)) { - repository = repository.substring(rootDir.length()); - if (repository.startsWith(ResourceSyncInfo.SEPARATOR)) { - repository = repository.substring(ResourceSyncInfo.SEPARATOR.length()); - } - } - } - - public boolean equals(Object other) { - if(other == this) return true; - if (!(other instanceof FolderSyncInfo)) return false; - - FolderSyncInfo syncInfo = ((FolderSyncInfo)other); - if (!getRoot().equals(syncInfo.getRoot())) return false; - if (!getRepository().equals(syncInfo.getRepository())) return false; - if (getIsStatic() != syncInfo.getIsStatic()) return false; - if ((getTag() == null) || (syncInfo.getTag() == null)) { - if ((getTag() == null) && (syncInfo.getTag() != null) && (syncInfo.getTag().getType() != CVSTag.HEAD)) { - return false; - } else if ((syncInfo.getTag() == null) && (getTag() != null) && (getTag().getType() != CVSTag.HEAD)) { - return false; - } - } else if (!getTag().equals(syncInfo.getTag())) { - return false; - } - return true; - } - /** - * Gets the root, cannot be <code>null. - * - * @return Returns a String - */ - public String getRoot() { - return root; - } - - /** - * Answer the directory portion of the root. For example, if - * root = :pserver:user@host:/home/user/repo - * then /home/user/repo is return. - * <p> - * The root does not neccesarily contain a user name, in which cas the format is - * :pserver:host:/home/user/repo. - * - * - * @return String - */ - private String getRootDirectory() throws CVSException { - try { - String root = getRoot(); - int index = root.indexOf('@'); - if (index == -1) { - // If the username is mising, we have to find the third ':'. - index = root.indexOf(':'); - if (index == 0) { - // The method is optional so if it's not there, there is only one ':' - index = root.indexOf(':', index + 1); - index = root.indexOf(':', index + 1); - } - } else { - // If the username was there, we find the first ':' past the '@' - index = root.indexOf(':', index + 1); - } - index++; - // strip off a leading port if there is one - char c = root.charAt(index); - while (Character.isDigit(c)) { - c = root.charAt(++index); - } - return root.substring(index); - } catch (IndexOutOfBoundsException e) { - throw new CVSException(Policy.bind("FolderSyncInfo_Maleformed_root_4")); //$NON-NLS-1$ - } - } - - /** - * Gets the tag, may be <code>null</code>. - * - * @return Returns a String - */ - public CVSEntryLineTag getTag() { - return tag; - } - - /** - * Gets the repository, may be <code>null</code>. - * - * @return Returns a String - */ - public String getRepository() { - return repository; - } - - /** - * Gets the isStatic. - * - * @return Returns a boolean - */ - public boolean getIsStatic() { - return isStatic; - } - - /** - * Answers a full path to the folder on the remote server. This by appending the repository to the - * repository location speficied in the root. - * - * Example: - * root = :pserver:user@host:/home/user/repo - * repository = folder1/folder2 - * - * Returns: - * /home/users/repo/folder1/folder2 - * - * Note: CVS supports repository root directories that end in a slash (/). - * For these directories, the remote location must contain two slashes (//) - * between the root directory and the rest of the path. For example: - * root = :pserver:user@host:/home/user/repo/ - * repository = folder1/folder2 - * must return: - * /home/users/repo//folder1/folder2 - * - * @return the full path of this folder on the server. - * @throws a CVSException if the root or repository is malformed. - */ - public String getRemoteLocation() throws CVSException { - return getRootDirectory() + ResourceSyncInfo.SEPARATOR + getRepository(); //$NON-NLS-1$ - } - - /* - * Provide a hashCode() method that gaurentees that equal object will have the - * same hashCode - */ - public int hashCode() { - return getRoot().hashCode() | getRepository().hashCode(); - } - - /** - * Sets the tag for the folder. - * - * @param tag The tag to set - */ - protected void setTag(CVSTag tag) { - if (tag == null || tag.equals(CVSTag.DEFAULT)) { - this.tag = null; - } else { - this.tag = new CVSEntryLineTag(tag); - } - } - /* - * @see Object#toString() - */ - public String toString() { - return getRoot() + "/" + getRepository() + "/" + getTag(); //$NON-NLS-1$ //$NON-NLS-2$ - } - - public MutableFolderSyncInfo cloneMutable() { - MutableFolderSyncInfo newSync = new MutableFolderSyncInfo(this); - return newSync; - } - - /** - * Return true if this FolderSyncInfo is mapped to the same remote directory - * as the other FolderSyncInfo passed as a parameter. - * - * @param remoteInfo - * @return - */ - public boolean isSameMapping(FolderSyncInfo other) { - if (other == null) return false; - return (this.getRoot().equals(other.getRoot()) - && this.getRepository().equals(other.getRepository())) ; - } - -/** - * Convert a FolderSyncInfo into a byte array that can be stored - * in the workspace synchronizer - */ - public byte[] getBytes() throws CVSException { - ByteArrayOutputStream out = new ByteArrayOutputStream(); - DataOutputStream dos = new DataOutputStream(out); - try { - dos.writeUTF(getRoot()); - dos.writeUTF(getRepository()); - CVSEntryLineTag t = getTag(); - if (t == null) { - dos.writeUTF(""); //$NON-NLS-1$ - } else { - dos.writeUTF(t.toString()); - } - dos.writeBoolean(getIsStatic()); - dos.close(); - } catch (IOException e) { - throw CVSException.wrapException(e); - } - return out.toByteArray(); - } - - /** - * Convert a byte array that was created using getBytes(FolderSyncInfo) - * into a FolderSyncInfo - */ - public static FolderSyncInfo getFolderSyncInfo(byte[] bytes) throws CVSException { - ByteArrayInputStream in = new ByteArrayInputStream(bytes); - DataInputStream dis = new DataInputStream(in); - String root; - String repository; - CVSEntryLineTag tag; - boolean isStatic; - try { - root = dis.readUTF(); - repository = dis.readUTF(); - String tagName = dis.readUTF(); - if (tagName.length() == 0) { - tag = null; - } else { - tag = new CVSEntryLineTag(tagName); - } - isStatic = dis.readBoolean(); - } catch (IOException e) { - throw CVSException.wrapException(e); - } - return new FolderSyncInfo(repository, root, tag, isStatic); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/MutableFolderSyncInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/MutableFolderSyncInfo.java deleted file mode 100644 index 9eadb57b7..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/MutableFolderSyncInfo.java +++ /dev/null @@ -1,63 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import org.eclipse.team.internal.ccvs.core.CVSTag; - -/** - * Mutable version of FolderSyncInfo. Can be used when either creating a - * folder sync object from scratch or when modifying an existing - * <code>FolderSyncInfo</code> instance. Example usage: - * <pre> - * FolderSyncInfo info = folder.getFolderSyncInfo(); - * if(info!=null) { - * MutableFolderSyncInfo newInfo = info.cloneMutable(); - * newInfo.setTag(CVSTag.DEFAULT); - * folder.setFolderSyncInfo(newInfo); - * } - * </pre> - * @see FolderSyncInfo - */ -public class MutableFolderSyncInfo extends FolderSyncInfo { - - /** - * Constructor MutableFolderSyncInfo. - * @param folderSyncInfo - */ - public MutableFolderSyncInfo(FolderSyncInfo info) { - this(info.getRepository(), info.getRoot(), info.getTag(), info.getIsStatic()); - } - - /** - * Constructor for MutableFolderSyncInfo. - * @param repo - * @param root - * @param tag - * @param isStatic - */ - public MutableFolderSyncInfo(String repo, String root, CVSTag tag, boolean isStatic) { - super(repo, root, tag, isStatic); - } - - /** - * @see org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo#setTag(org.eclipse.team.internal.ccvs.core.CVSTag) - */ - public void setTag(CVSTag tag) { - super.setTag(tag); - } - /** - * Method setRepository. - * @param string - */ - public void setRepository(String repository) { - this.repository = repository; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/MutableResourceSyncInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/MutableResourceSyncInfo.java deleted file mode 100644 index caf694892..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/MutableResourceSyncInfo.java +++ /dev/null @@ -1,166 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import java.util.Date; - -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.client.Command.KSubstOption; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Mutable version of ResourceSyncInfo. Can be used when either creating a resource sync - * object from scratch (e.g. without an entry line) or want to modify an existing - * <code>ResourceSyncInfo</code> instance. Example usage: - * <pre> - * ResourceSyncInfo info = resource.getSyncInfo(); - * if(info!=null) { - * MutableResourceSyncInfo newInfo = info.cloneMutable(); - * newInfo.setRevision("1.22"); - * resource.setSyncInfo(newInfo); - * } - * </pre> - * @see ResourceSyncInfo - */ -public class MutableResourceSyncInfo extends ResourceSyncInfo { - - boolean reported; - boolean changed; - - protected MutableResourceSyncInfo(ResourceSyncInfo info) { - this.name = info.getName(); - setRevision(info.getRevision()); - setTag(info.getTag()); - this.permissions = info.getPermissions(); - this.timeStamp = info.getTimeStamp(); - this.isDirectory = info.isDirectory(); - this.keywordMode = info.getKeywordMode(); - this.isDeleted = info.isDeleted(); - if(info.isMergedWithConflicts()) { - setSyncType(TYPE_MERGED_WITH_CONFLICTS); - } else if(info.isMerged()) { - setSyncType(TYPE_MERGED); - } else { - setSyncType(TYPE_REGULAR); - } - } - - /** - * Creates a default sync info, if revision is <code>null</code> then - * the sync info will be considered in the newly added state. - */ - public MutableResourceSyncInfo(String name, String revision) { - Assert.isNotNull(name); - this.name = name; - setRevision(revision); - this.reported = false; - this.changed = false; - } - - void setResourceInfoType(int type) { - this.syncType = type; - } - - /** - * Sets the revision. - * @param revision The revision to set - */ - public void setRevision(String revision) { - super.setRevision(revision); - } - - /** - * Sets the timeStamp. - * @param timeStamp The timeStamp to set - */ - public void setTimeStamp(Date timeStamp) { - this.timeStamp = timeStamp; - this.changed = true; - } - - /** - * Sets the timeStamp. - * @param timeStamp The timeStamp to set - */ - public void setTimeStamp(Date timeStamp, boolean clearMerged) { - setTimeStamp(timeStamp); - if (clearMerged) setSyncType(TYPE_REGULAR); - } - - /** - * Sets the keywordMode. - * @param keywordMode The keywordMode to set - */ - public void setKeywordMode(KSubstOption keywordMode) { - this.keywordMode = keywordMode; - this.changed = true; - } - - /** - * Sets the tag. - * @param tag The tag to set - */ - public void setTag(CVSTag tag) { - super.setTag(tag); - } - - /** - * Sets the permissions. - * @param permissions The permissions to set - */ - public void setPermissions(String permissions) { - this.permissions = permissions; - } - - /** - * Sets the deleted state. - * @param isDeleted The deleted state of this resource sync - */ - public void setDeleted(boolean isDeleted) { - this.isDeleted = isDeleted; - this.changed = true; - } - - /** - * Sets to the added state. The timestamp and other are cleared. - */ - public void setAdded() { - setRevision(ADDED_REVISION); - this.changed = true; - } - - /** - * Sets that this resource sync is a result of a non-conflicting merge - */ - public void setMerged() { - // if already merged state then ignore - if(syncType==TYPE_REGULAR) { - this.syncType = TYPE_MERGED; - this.changed = true; - } - } - - public boolean needsReporting() { - return changed && !reported; - } - - public void reported() { - this.reported = true; - } - /** - * @see org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo#setEntryLine(java.lang.String) - */ - public void setEntryLine(String entryLine) throws CVSException { - super.setEntryLine(entryLine); - this.changed = true; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/NotifyInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/NotifyInfo.java deleted file mode 100644 index 6d387579d..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/NotifyInfo.java +++ /dev/null @@ -1,185 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import java.net.InetAddress; -import java.net.UnknownHostException; -import java.text.ParseException; -import java.util.Date; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.util.CVSDateFormatter; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * This class contains the information required by the server for edit/unedit. - */ -public class NotifyInfo { - - // constants for the notifiation type and watches - public static final char EDIT = 'E'; - public static final char UNEDIT = 'U'; - public static final char COMMIT = 'C'; - public static final char[] ALL = new char[] {EDIT, UNEDIT, COMMIT}; - - protected static final String TAB_SEPARATOR = "\t"; //$NON-NLS-1$ - - private String filename; - private char notificationType; - private Date timeStamp; - private char[] watches; - - /** - * Constructor for setting all variables - */ - public NotifyInfo(String filename, char notificationType, Date timeStamp, char[] watches) { - - this.filename = filename; - this.notificationType = notificationType; - this.timeStamp = timeStamp; - this.watches = watches; - } - - /** - * Constructor for a line from the CVS/Notify file - * @param line - */ - public NotifyInfo(IContainer parent, String line) throws CVSException { - ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor(parent); - String[] strings = Util.parseIntoSubstrings(line, ResourceSyncInfo.SEPARATOR); - if(strings.length != 4) { - throw new CVSException(Policy.bind("NotifyInfo.MalformedLine", line)); //$NON-NLS-1$ - } - this.filename = strings[0]; - - String type = strings[1]; - if (type.length() != 1) { - throw new CVSException(Policy.bind("NotifyInfo.MalformedNotificationType", line)); //$NON-NLS-1$ - } - this.notificationType = type.charAt(0); - - String date = strings[2]; - try { - this.timeStamp = CVSDateFormatter.entryLineToDate(date); - } catch(ParseException e) { - throw new CVSException(Policy.bind("NotifyInfo.MalformedNotifyDate", line)); //$NON-NLS-1$ - } - - String watchesString = strings[3]; - if (watchesString.length() > 0) { - this.watches = new char[watchesString.length()]; - for (int i = 0; i < watchesString.length(); i++) { - watches[i] = watchesString.charAt(i); - } - } else { - this.watches = null; - } - } - - /** - * Answer a Sting formatted to be written to the CVS/Notify file. - * - * XXX NOTE: This is a guess at the local format. Need to obtain proper format - * - * @return String - */ - public String getNotifyLine() { - StringBuffer buffer = new StringBuffer(); - buffer.append(getName()); - buffer.append(ResourceSyncInfo.SEPARATOR); - buffer.append(notificationType); - buffer.append(ResourceSyncInfo.SEPARATOR); - buffer.append(CVSDateFormatter.dateToEntryLine(timeStamp)); - buffer.append(ResourceSyncInfo.SEPARATOR); - if (watches != null) { - for (int i = 0; i < watches.length; i++) { - char c = watches[i]; - buffer.append(c); - } - } - return buffer.toString(); - } - - /** - * Answer a Sting formatted to be sent to the server. - * - * @return String - */ - public String getServerLine(ICVSFolder parent) throws CVSException { - StringBuffer buffer = new StringBuffer(); - buffer.append(notificationType); - buffer.append(TAB_SEPARATOR); - buffer.append(getServerTimestamp()); - buffer.append(TAB_SEPARATOR); - buffer.append(getHost()); - buffer.append(TAB_SEPARATOR); - buffer.append(getWorkingDirectory(parent)); - buffer.append(TAB_SEPARATOR); - if (watches != null) { - for (int i = 0; i < watches.length; i++) { - char c = watches[i]; - buffer.append(c); - } - } - return buffer.toString(); - } - - /** - * Answer the timestamp in GMT format. - * @return String - */ - private String getServerTimestamp() { - return CVSDateFormatter.dateToNotifyServer(timeStamp); - } - - /** - * Answer the working directory for the receiver's file. The format - * is NOT device dependant (i.e. /'s are used as the path separator). - * - * @return String - */ - private String getWorkingDirectory(ICVSFolder parent) throws CVSException { - return parent.getIResource().getLocation().toString(); - } - - /** - * Answer the host name of the client machine. - * @return String - */ - private String getHost() throws CVSException { - try { - return InetAddress.getLocalHost().getHostName(); - } catch (UnknownHostException e) { - throw CVSException.wrapException(e); - } - } - - /** - * Answer the name of the file associated with the notification - * @return String - */ - public String getName() { - return filename; - } - - /** - * Answer the notification type associated with the notification - * @return char - */ - public char getNotificationType() { - return notificationType; - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/OptimizedRemoteSynchronizer.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/OptimizedRemoteSynchronizer.java deleted file mode 100644 index 0013d1879..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/OptimizedRemoteSynchronizer.java +++ /dev/null @@ -1,76 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import org.eclipse.core.resources.IResource; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * The optimized remote synchronizer uses the base sync info when the remote - * is unknown - */ -public class OptimizedRemoteSynchronizer extends RemoteTagSynchronizer { - - // The local synchronizer is used for cases where the remote is unknown - private BaseSynchronizer baseSynchronizer = new BaseSynchronizer(); - - /** - * @param id - */ - public OptimizedRemoteSynchronizer(String id) { - super(id, null /* use the tag in the local workspace resources */); - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSynchronizer#getSyncBytes(org.eclipse.core.resources.IResource) - */ - public byte[] getSyncBytes(IResource resource) throws CVSException { - byte[] bytes = getRemoteBytes(resource); - if ((bytes == null) && !hasRemoteBytesFor(resource)) { - // The remote was never known so use the base - bytes = baseSynchronizer.getSyncBytes(resource); - } - return bytes; - } - - /* (non-Javadoc) - * @see org.eclipse.team.internal.ccvs.core.syncinfo.RemoteSynchronizer#setSyncBytes(org.eclipse.core.resources.IResource, byte[]) - */ - public void setSyncBytes(IResource resource, byte[] bytes) throws CVSException { - byte[] baseBytes = baseSynchronizer.getSyncBytes(resource); - if (baseBytes != null && Util.equals(baseBytes, bytes)) { - // Remove the existing bytes so the base will be used (thus saving space) - removeSyncBytes(resource, IResource.DEPTH_ZERO, true /* silent */); - } else { - super.setSyncBytes(resource, bytes); - } - } - - /** - * @return - */ - public BaseSynchronizer getBaseSynchronizer() { - return baseSynchronizer; - } - - /** - * Return the bytes for the remote resource if there is a remote that differs - * from the local. - * - * @param resource - * @return - * @throws CVSException - */ - public byte[] getRemoteBytes(IResource resource) throws CVSException { - return super.getSyncBytes(resource); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ReentrantLock.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ReentrantLock.java deleted file mode 100644 index acf453df3..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ReentrantLock.java +++ /dev/null @@ -1,84 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import java.util.HashSet; -import java.util.Set; - -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.util.Assert; - -/** - * Provides a per-thread nested locking mechanism. A thread can acquire a - * lock and then call acquire() multiple times. Other threads that try - * and acquire the lock will be blocked until the first thread releases all - * it's nested locks. - */ -public class ReentrantLock { - - private final static boolean DEBUG = Policy.DEBUG_THREADING; - private Thread thread; - private int nestingCount; - - private Set readOnlyThreads = new HashSet(); - - public ReentrantLock() { - this.thread = null; - this.nestingCount = 0; - } - - public synchronized void acquire() { - // stop early if we've been interrupted -- don't enter the lock anew - Thread thisThread = Thread.currentThread(); - - // race for access to the lock -- does not guarantee fairness - if (thread != thisThread) { - while (nestingCount != 0) { - try { - if(DEBUG) System.out.println("["+ thisThread.getName() + "] waiting for CVS synchronizer lock"); //$NON-NLS-1$ //$NON-NLS-2$ - wait(); - } catch(InterruptedException e) { - // keep waiting for the lock - if(DEBUG) System.out.println("["+ thisThread.getName() + "] interrupted in CVS synchronizer lock"); //$NON-NLS-1$ //$NON-NLS-2$ - } - } - thread = thisThread; - if(DEBUG) System.out.println("[" + thisThread.getName() + "] acquired CVS synchronizer lock"); //$NON-NLS-1$ //$NON-NLS-2$ - } - nestingCount++; - } - - public synchronized void release() { - Thread thisThread = Thread.currentThread(); - Assert.isLegal(thread == thisThread, - "Thread attempted to release a lock it did not own"); //$NON-NLS-1$ - if (--nestingCount == 0) { - if(DEBUG) System.out.println("[" + thread.getName() + "] released CVS synchronizer lock"); //$NON-NLS-1$ //$NON-NLS-2$ - thread = null; - notifyAll(); - } - } - - public int getNestingCount() { - Thread thisThread = Thread.currentThread(); - Assert.isLegal(thread == thisThread, - "Thread attempted to read nesting count of a lock it did not own"); //$NON-NLS-1$ - return nestingCount; - } - - public boolean isReadOnly() { - return readOnlyThreads.contains(thread); - } - - public void addReadOnlyThread(Thread thread) { - readOnlyThreads.add(thread); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteResourceFactory.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteResourceFactory.java deleted file mode 100644 index 21518f888..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteResourceFactory.java +++ /dev/null @@ -1,21 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -/** - * @author Administrator - * - * To change the template for this generated type comment go to - * Window>Preferences>Java>Code Generation>Code and Comments - */ -public class RemoteResourceFactory { - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteSynchronizer.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteSynchronizer.java deleted file mode 100644 index c4d97a4ae..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteSynchronizer.java +++ /dev/null @@ -1,85 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import java.util.HashSet; -import java.util.Set; - -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.ISynchronizer; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * A remote resource sychronizer caches the remote sync bytes that can be - * used to create remote handles - */ -public class RemoteSynchronizer extends ResourceSynchronizer { - - public static final String SYNC_KEY_QUALIFIER = "org.eclipse.team.cvs"; //$NON-NLS-1$ - protected QualifiedName syncName; - protected Set changedResources = new HashSet(); - - public RemoteSynchronizer(String id) { - syncName = new QualifiedName(SYNC_KEY_QUALIFIER, id); - getSynchronizer().add(syncName); - } - - /** - * Dispose of any cached remote sync info. - */ - public void dispose() { - getSynchronizer().remove(getSyncName()); - } - - protected ISynchronizer getSynchronizer() { - return ResourcesPlugin.getWorkspace().getSynchronizer(); - } - - protected QualifiedName getSyncName() { - return syncName; - } - - public byte[] getSyncBytes(IResource resource) throws CVSException { - try { - return getSynchronizer().getSyncInfo(getSyncName(), resource); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - public void setSyncBytes(IResource resource, byte[] bytes) throws CVSException { - byte[] oldBytes = getSyncBytes(resource); - if (oldBytes != null && Util.equals(oldBytes, bytes)) return; - try { - getSynchronizer().setSyncInfo(getSyncName(), resource, bytes); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - changedResources.add(resource); - } - - public void removeSyncBytes(IResource resource, int depth, boolean silent) throws CVSException { - if (resource.exists() || resource.isPhantom()) { - try { - getSynchronizer().flushSyncInfo(getSyncName(), resource, depth); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - if(silent == false) { - changedResources.add(resource); - } - } - } -}
\ No newline at end of file diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteTagSynchronizer.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteTagSynchronizer.java deleted file mode 100644 index 8fd648781..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/RemoteTagSynchronizer.java +++ /dev/null @@ -1,262 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ - -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.HashSet; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.Set; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.OperationCanceledException; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteResource; -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.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.RemoteResource; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * This RemoteSynchronizr uses a CVS Tag to fetch the remote tree - */ -public class RemoteTagSynchronizer extends RemoteSynchronizer { - - private static final byte[] NO_REMOTE = new byte[0]; - private CVSTag tag; - - public RemoteTagSynchronizer(String id, CVSTag tag) { - super(id); - this.tag = tag; - } - - public void collectChanges(IResource local, ICVSRemoteResource remote, int depth, IProgressMonitor monitor) throws TeamException { - byte[] remoteBytes; - if (remote != null) { - remoteBytes = ((RemoteResource)remote).getSyncBytes(); - } else { - remoteBytes = NO_REMOTE; - } - setSyncBytes(local, remoteBytes); - if (depth == IResource.DEPTH_ZERO) return; - Map children = mergedMembers(local, remote, monitor); - for (Iterator it = children.keySet().iterator(); it.hasNext();) { - IResource localChild = (IResource) it.next(); - ICVSRemoteResource remoteChild = (ICVSRemoteResource)children.get(localChild); - collectChanges(localChild, remoteChild, - depth == IResource.DEPTH_INFINITE ? IResource.DEPTH_INFINITE : IResource.DEPTH_ZERO, - monitor); - } - } - - protected Map mergedMembers(IResource local, IRemoteResource remote, IProgressMonitor progress) throws TeamException { - - // {IResource -> IRemoteResource} - Map mergedResources = new HashMap(); - - IRemoteResource[] remoteChildren = getRemoteChildren(remote, progress); - - IResource[] localChildren = getLocalChildren(local); - - if (remoteChildren.length > 0 || localChildren.length > 0) { - List syncChildren = new ArrayList(10); - Set allSet = new HashSet(20); - Map localSet = null; - Map remoteSet = null; - - if (localChildren.length > 0) { - localSet = new HashMap(10); - for (int i = 0; i < localChildren.length; i++) { - IResource localChild = localChildren[i]; - String name = localChild.getName(); - localSet.put(name, localChild); - allSet.add(name); - } - } - - if (remoteChildren.length > 0) { - remoteSet = new HashMap(10); - for (int i = 0; i < remoteChildren.length; i++) { - IRemoteResource remoteChild = remoteChildren[i]; - String name = remoteChild.getName(); - remoteSet.put(name, remoteChild); - allSet.add(name); - } - } - - Iterator e = allSet.iterator(); - while (e.hasNext()) { - String keyChildName = (String) e.next(); - - if (progress != null) { - if (progress.isCanceled()) { - throw new OperationCanceledException(); - } - // XXX show some progress? - } - - IResource localChild = - localSet != null ? (IResource) localSet.get(keyChildName) : null; - - IRemoteResource remoteChild = - remoteSet != null ? (IRemoteResource) remoteSet.get(keyChildName) : null; - - if (localChild == null) { - // there has to be a remote resource available if we got this far - Assert.isTrue(remoteChild != null); - boolean isContainer = remoteChild.isContainer(); - localChild = getResourceChild(local /* parent */, keyChildName, isContainer); - } - mergedResources.put(localChild, remoteChild); - } - } - return mergedResources; - } - - private IRemoteResource[] getRemoteChildren(IRemoteResource remote, IProgressMonitor progress) throws TeamException { - return remote != null ? remote.members(progress) : new IRemoteResource[0]; - } - - private IResource[] getLocalChildren(IResource local) throws TeamException { - IResource[] localChildren = null; - if( local.getType() != IResource.FILE && (local.exists() || local.isPhantom())) { - // Include all non-ignored resources including outgoing deletions - ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor((IContainer)local); - // Look inside existing folders and phantoms that are CVS folders - if (local.exists() || cvsFolder.isCVSFolder()) { - ICVSResource[] cvsChildren = cvsFolder.members(ICVSFolder.MANAGED_MEMBERS | ICVSFolder.UNMANAGED_MEMBERS); - List resourceChildren = new ArrayList(); - for (int i = 0; i < cvsChildren.length; i++) { - ICVSResource cvsResource = cvsChildren[i]; - resourceChildren.add(cvsResource.getIResource()); - } - localChildren = (IResource[]) resourceChildren.toArray(new IResource[resourceChildren.size()]); - } - } - if (localChildren == null) { - localChildren = new IResource[0]; - } - return localChildren; - } - - /* - * Returns a handle to a non-existing resource. - */ - private IResource getResourceChild(IResource parent, String childName, boolean isContainer) { - if (parent.getType() == IResource.FILE) { - return null; - } - if (isContainer) { - return ((IContainer) parent).getFolder(new Path(childName)); - } else { - return ((IContainer) parent).getFile(new Path(childName)); - } - } - - /** - * Return true if remote bytes for the resource have been fetched during - * a refresh. This will also return true for remote resources that do not exist - * (i.e. they have no sync bytes but did not exist remotely at the time of the - * last refresh. - * - * @param resource - * @return - */ - public boolean hasRemoteBytesFor(IResource resource) throws CVSException { - return super.getSyncBytes(resource) != null; - } - - /** - * This method will return null in both cases when the remote has never been fetched - * or when the remote does not exist. Use <code>hasRemoteBytesFor</code> to - * differentiate these cases. - */ - public byte[] getSyncBytes(IResource resource) throws CVSException { - byte[] syncBytes = super.getSyncBytes(resource); - if (syncBytes != null && Util.equals(syncBytes, NO_REMOTE)) { - // If it is known that there is no remote, return null - return null; - } - return syncBytes; - } - - /** - * @return - */ - public IResource[] getChangedResources() { - return (IResource[]) changedResources.toArray(new IResource[changedResources.size()]); - } - - public void resetChanges() { - changedResources.clear(); - } - - /** - * Refreshes the contents of the remote synchronizer and returns the list - * of resources whose remote sync state changed. - * - * @param resources - * @param depth - * @param monitor - * @return - * @throws TeamException - */ - public IResource[] refresh(IResource[] resources, int depth, boolean cacheFileContentsHint, IProgressMonitor monitor) throws TeamException { - int work = 100 * resources.length; - monitor.beginTask(null, work); - resetChanges(); - try { - for (int i = 0; i < resources.length; i++) { - IResource resource = resources[i]; - - // build the remote tree only if an initial tree hasn't been provided - ICVSRemoteResource tree = buildRemoteTree(resource, depth, cacheFileContentsHint, Policy.subMonitorFor(monitor, 70)); - - // update the known remote handles - IProgressMonitor sub = Policy.infiniteSubMonitorFor(monitor, 30); - try { - sub.beginTask(null, 512); - //removeSyncBytes(resource, IResource.DEPTH_INFINITE); - collectChanges(resource, tree, depth, sub); - } finally { - sub.done(); - } - } - } finally { - monitor.done(); - } - IResource[] changes = getChangedResources(); - resetChanges(); - return changes; - } - - /** - * Build a remote tree for the given parameters. - */ - protected ICVSRemoteResource buildRemoteTree(IResource resource, int depth, boolean cacheFileContentsHint, IProgressMonitor monitor) throws TeamException { - // TODO: we are currently ignoring the depth parameter because the build remote tree is - // by default deep! - return CVSWorkspaceRoot.getRemoteTree(resource, tag, cacheFileContentsHint, monitor); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ResourceSyncInfo.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ResourceSyncInfo.java deleted file mode 100644 index 25eae8468..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ResourceSyncInfo.java +++ /dev/null @@ -1,890 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - - -import java.text.ParseException; -import java.util.Date; - -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command.KSubstOption; -import org.eclipse.team.internal.ccvs.core.resources.CVSEntryLineTag; -import org.eclipse.team.internal.ccvs.core.util.Assert; -import org.eclipse.team.internal.ccvs.core.util.CVSDateFormatter; -import org.eclipse.team.internal.ccvs.core.util.Util; - -/** - * Value (immutable) object that represents workspace state information about a resource contained in - * a CVS repository. It is a specialized representation of a line in the CVS/Entry file with the addition of - * file permissions. - * <p> - * ResourceSyncInfo instances are created from entry lines from the CVS server and from the CVS/Entries - * file. Although both entry lines have slightly different formats (e.g. timestamps) they can safely be passed - * to the constructor.</p> - * <p> - * A class named <code>MutableResourceSyncInfo</code> can be used to modify an existing resource - * sync or create sync info without an entry line.</p> - * - * Example entry line from the CVS/Entry file: - * - * /new.java/1.2/Fri Dec 7 00:17:52 2001/-kb/ - * D/src//// - * - * @see MutableResourceSyncInfo - * @see ICVSResource#getSyncInfo() - */ -public class ResourceSyncInfo { - - // [Note: permissions aren't honoured in this current implementation] - // safe default permissions. Permissions are saved separately so that the correct permissions - // can be sent back to the server on systems that don't save execute bits (e.g. windows). - private static final String DEFAULT_PERMISSIONS = "u=rw,g=rw,o=r"; //$NON-NLS-1$ - - // file sync information can be associated with a local resource that has been deleted. This is - // noted by prefixing the revision with this character. - private static final String DELETED_PREFIX = "-"; //$NON-NLS-1$ - private static final byte DELETED_PREFIX_BYTE = '-'; - - // a sync element with a revision of '0' is considered a new file that has - // not been comitted to the repo. Is visible so that clients can create sync infos - // for new files. - public static final String ADDED_REVISION = "0"; //$NON-NLS-1$ - - // Timestamp constants used to identify special cases - protected static final int TYPE_REGULAR = 1; - protected static final int TYPE_MERGED = 2; - protected static final int TYPE_MERGED_WITH_CONFLICTS = 3; - - protected static final String TIMESTAMP_DUMMY = "dummy timestamp"; //$NON-NLS-1$ - protected static final String TIMESTAMP_MERGED = "Result of merge"; //$NON-NLS-1$ - protected static final String TIMESTAMP_MERGED_WITH_CONFLICT = TIMESTAMP_MERGED + "+"; //$NON-NLS-1$ - - protected static final String TIMESTAMP_SERVER_MERGED = "+modified"; //$NON-NLS-1$ - protected static final String TIMESTAMP_SERVER_MERGED_WITH_CONFLICT = "+="; //$NON-NLS-1$ - - // a directory sync info will have nothing more than a name - protected boolean isDirectory = false; - protected boolean isDeleted = false; - - // utility constants - protected static final String DIRECTORY_PREFIX = "D"; //$NON-NLS-1$ - protected static final String SEPARATOR = "/"; //$NON-NLS-1$ - protected static final byte SEPARATOR_BYTE = (byte)'/'; - - // fields describing the synchronization of a resource in CVS parlance - protected String name; - protected String revision; - protected Date timeStamp; - protected KSubstOption keywordMode; - protected CVSEntryLineTag tag; - protected String permissions; - - // type of sync - protected int syncType = TYPE_REGULAR; - protected ResourceSyncInfo() { - } - - public ResourceSyncInfo(byte[] entryLine) throws CVSException { - this(new String(entryLine), null, null); - } - - /** - * Constructor to create a sync object from entry line formats. The entry lines are parsed by this class. - * The constructor can handle parsing entry lines from the server or from an entry file. - * - * @param entryLine the entry line (e.g. /new.java/1.2/Fri Dec 07 00:17:52 2001/-kb/) - * @param permissions the file permission (e.g. u=rw,g=rw,o=r). May be <code>null</code>. - * @param timestamp if not included in the entry line. May be <code>null</code>. - * - * @exception CVSException is thrown if the entry cannot be parsed. - */ - public ResourceSyncInfo(String entryLine, String permissions, Date timestamp) throws CVSException { - Assert.isNotNull(entryLine); - setEntryLine(entryLine); - - if (permissions != null) { - this.permissions = permissions; - } - // override the timestamp that may of been in entryLine. In some cases the timestamp is not in the - // entry line (e.g. receiving entry lines from the server versus reading them from the Entry file). - if(timestamp!=null) { - this.timeStamp = timestamp; - } - } - - /** - * Constructor to create a resource sync object for a folder. - * - * @param name of the resource for which this sync state is associatied, cannot be <code>null</code>. - */ - public ResourceSyncInfo(String name) { - Assert.isNotNull(name); - this.name = name; - this.isDirectory = true; - } - /** - * Answers if this sync information is for a folder in which case only a name is - * available. - * - * @return <code>true</code> if the sync information is for a folder and <code>false</code> - * if it is for a file. - */ - public boolean isDirectory() { - return isDirectory; - } - - /** - * Answers if this sync information is for a resource that has been merged by the cvs server with - * conflicts and has not been modified yet relative to the given timestamp. - * - * @param otherTimestamp is the timestamp of the file associated with this resource sync - * @return <code>true</code> if the sync information is for a file that has been merged and - * <code>false</code> for folders and for files that have not been merged. - */ - public boolean isNeedsMerge(Date otherTimestamp) { - return syncType == TYPE_MERGED_WITH_CONFLICTS && timeStamp.equals(otherTimestamp); - } - - /** - * Answers if this sync information is for a resource that has been merged with conflicts by the - * cvs server. - * - * @return <code>true</code> if the sync information is for a file that has been merged and - * <code>false</code> for folders and for files that have not been merged. - */ - public boolean isMergedWithConflicts() { - return syncType == TYPE_MERGED_WITH_CONFLICTS; - } - - /** - * Answers if this sync information is for a resource that has been merged by the cvs server. - * - * @return <code>true</code> if the sync information is for a file that has been merged and - * <code>false</code> for folders and for files that have not been merged. - */ - public boolean isMerged() { - return syncType == TYPE_MERGED || isMergedWithConflicts(); - } - - /** - * Answers if this sync information is for a file that has been added but not comitted - * to the CVS repository yet. - * - * @return <code>true</code> if the sync information is new or <code>false</code> if - * the sync is for an file that exists remotely. For folder sync info this returns - * <code>false</code>. - */ - public boolean isAdded() { - if(!isDirectory) { - return getRevision().equals(ADDED_REVISION); - } else { - return false; - } - } - - /** - * Answers if this sync information is for a file that is scheduled to be deleted - * from the repository but the deletion has not yet been comitted. - * - * @return <code>true</code> if the sync information is deleted or <code>false</code> if - * the sync is for an file that exists remotely. - */ - public boolean isDeleted() { - return isDeleted; - } - - /** - * Returns an entry line that can be saved in the CVS/Entries file. For sending entry lines to the - * server use <code>getServerEntryLine</code>. - * - * @return a file or folder entry line reflecting the state of this sync object. - */ - public String getEntryLine() { - return getEntryLine(true /*include timestamps*/, null /*no timestamp override*/); - } - - /** - * Same as <code>getEntryLine</code> except it considers merged files in entry line timestamp format. - * This is only valid for sending the file to the server. - * - * @param fileTimestamp is timestamp of the resource associated with this sync info. - * @return a file or folder entry line reflecting the state of this sync object. - */ - public String getServerEntryLine(Date fileTimestamp) { - String serverTimestamp; - if(fileTimestamp != null && (isMerged() || isMergedWithConflicts())) { - if(isNeedsMerge(fileTimestamp)) { - serverTimestamp = TIMESTAMP_SERVER_MERGED_WITH_CONFLICT; - } else { - serverTimestamp = TIMESTAMP_SERVER_MERGED; - } - return getEntryLine(true, serverTimestamp); - } else { - return getEntryLine(false, null); - } - } - - /** - * Anwsers a compatible permissions line for files. - * - * @return a permission line for files and <code>null</code> if this sync object is - * a directory. - */ - public String getPermissionLine() { - if(isDirectory) { - return null; - } else { - String permissions = this.permissions; - if (permissions == null) - permissions = DEFAULT_PERMISSIONS; - return SEPARATOR + name + SEPARATOR + permissions; - } - } - - /** - * Gets the permissions. Returns <code>null</code> for directories and - * a non-null permission for files. - * - * @return a string of the format "u=rw,g=rw,o=r" - */ - public String getPermissions() { - if(isDirectory) { - return null; - } else { - if(permissions==null) { - return DEFAULT_PERMISSIONS; - } else { - return permissions; - } - } - } - /** - * Gets the tag or <code>null</code> if a tag is not available. - * - * @return Returns a String - */ - public CVSTag getTag() { - return tag; - } - /** - * Gets the timeStamp or <code>null</code> if a timestamp is not available. - * - * @return a date instance representing the timestamp - */ - public Date getTimeStamp() { - return timeStamp; - } - /** - * Gets the version or <code>null</code> if this is a folder sync info. The returned - * revision will never include the DELETED_PREFIX. To found out if this sync info is - * for a deleted resource call isDeleted(). - * - * @return Returns a String - */ - public String getRevision() { - return revision; - } - - /** - * Gets the name. - * - * @return Returns a String - */ - public String getName() { - return name; - } - /** - * Gets the keyword mode. - * @return the keyword substitution option - */ - public KSubstOption getKeywordMode() { - return keywordMode; - } - - /** - * Answers the default permissions string. - */ - public static String getDefaultPermissions() { - return DEFAULT_PERMISSIONS; - } - - /** - * Name equality between resource sync info objects. - */ - public boolean equals(Object other) { - if(other instanceof ResourceSyncInfo) { - ResourceSyncInfo syncInfo = ((ResourceSyncInfo)other); - if(other == this) return true; - if(getName() == syncInfo.getName()) return true; - return getName().equals(syncInfo.getName()); - } else { - return false; - } - } - - public int hashCode() { - return getName().hashCode(); - } - - /* - * @see Object#toString() - */ - public String toString() { - return getEntryLine(true, null /*no timestamp override*/); - } - public MutableResourceSyncInfo cloneMutable() { - MutableResourceSyncInfo newSync = new MutableResourceSyncInfo(this); - return newSync; - } - /** - * Sets the tag for the resource. - */ - protected void setTag(CVSTag tag) { - if(tag!=null) { - this.tag = new CVSEntryLineTag(tag); - } else { - this.tag = null; - } - } - - - /* - * Sets the sync type - */ - protected void setSyncType(int syncType) { - this.syncType = syncType; - } - /** - * Sets the version and decides if the revision is for a deleted resource the revision field - * will not include the deleted prefix '-'. - * - * @param version the version to set - */ - protected void setRevision(String revision) { - if(revision==null || revision.equals(ADDED_REVISION)) { - this.revision = ADDED_REVISION; - timeStamp = null; - syncType = TYPE_REGULAR; - isDeleted = false; - } else if(revision.startsWith(DELETED_PREFIX)) { - this.revision = revision.substring(DELETED_PREFIX.length()); - isDeleted = true; - } else { - this.revision = revision; - isDeleted = false; - } - } - - /** - * Set the entry line - * - * @throws CVSException if the entryLine is malformed - */ - protected void setEntryLine(String entryLine) throws CVSException { - - String[] strings = Util.parseIntoSubstrings(entryLine, SEPARATOR); - if(strings.length < 6) { - throw new CVSException(Policy.bind("Malformed_entry_line___11") + entryLine); //$NON-NLS-1$ - } - - isDirectory = (strings[0].equals(DIRECTORY_PREFIX)); - - name = strings[1]; - - if(name.length()==0) { - throw new CVSException(Policy.bind("Malformed_entry_line,_missing_name___12") + entryLine); //$NON-NLS-1$ - } - - String rev = strings[2]; - - if(rev.length()==0 && !isDirectory()) { - throw new CVSException(Policy.bind("Malformed_entry_line,_missing_revision___13") + entryLine); //$NON-NLS-1$ - } else { - setRevision(rev); - } - - String date = strings[3]; - - // possible timestamps are: - // from server: "+=" and "+modified" - // from entry line: "Result of Merge+Thu May 25 12:33:33 2002" - // "Result of Merge" - // "Thu May 25 12:33:33 2002" - // - // The server will send a timestamp of "+=" if - // the file was merged with conflicts. The '+' indicates that there are conflicts and the - // '=' indicate that the timestamp for the file should be used. If the merge does not - // have conflicts, simply add a text only timestamp and the file will be regarded as - // having outgoing changes. - // The purpose for having the two different timestamp options for merges is to - // dissallow commit of files that have conflicts until they have been manually edited. - if(date.indexOf(ResourceSyncInfo.TIMESTAMP_SERVER_MERGED) != -1) { - syncType = TYPE_MERGED; - date = null; - } else if(date.indexOf(ResourceSyncInfo.TIMESTAMP_SERVER_MERGED_WITH_CONFLICT) != -1) { - syncType = TYPE_MERGED_WITH_CONFLICTS; - date = null; - } else if(date.indexOf(TIMESTAMP_MERGED_WITH_CONFLICT)!=-1) { - date = date.substring(date.indexOf("+") + 1); //$NON-NLS-1$ - syncType = TYPE_MERGED_WITH_CONFLICTS; - } else if(date.indexOf(TIMESTAMP_MERGED)!=-1) { - syncType = TYPE_MERGED; - date = null; - } - - if(date==null || "".equals(date)) { //$NON-NLS-1$ - timeStamp = null; - } else { - try { - timeStamp = CVSDateFormatter.entryLineToDate(date); - } catch(ParseException e) { - // something we don't understand, just make this sync have no timestamp and - // never be in sync with the server. - timeStamp = null; - } - } - keywordMode = KSubstOption.fromMode(strings[4]); - String tagEntry; - if (strings.length == 6) { - tagEntry = strings[5]; - } else { - // It turns out that CVS supports slashes (/) in the tag even though this breaks the spec - // See http://dev.eclipse.org/bugs/show_bug.cgi?id=26717 - StringBuffer buffer = new StringBuffer(); - for (int i = 5; i < strings.length; i++) { - buffer.append(strings[i]); - if (i < strings.length - 1) { - buffer.append(SEPARATOR); - } - } - tagEntry = buffer.toString(); - } - - if(tagEntry.length()>0) { - tag = new CVSEntryLineTag(tagEntry); - } else { - tag = null; - } - } - - private String getEntryLine(boolean includeTimeStamp, String timestampOverride) { - StringBuffer result = new StringBuffer(); - - if(isDirectory) { - result.append(DIRECTORY_PREFIX); - result.append(SEPARATOR); - result.append(name); - for (int i = 0; i < 4; i++) { - result.append(SEPARATOR); - } - } else { - result.append(SEPARATOR); - result.append(name); - result.append(SEPARATOR); - - if(isDeleted){ - result.append(DELETED_PREFIX); - } - result.append(revision); - result.append(SEPARATOR); - if(includeTimeStamp) { - String entryLineTimestamp = ""; //$NON-NLS-1$ - if(timestampOverride!=null) { - entryLineTimestamp = timestampOverride; - } else { - switch(syncType) { - case TYPE_REGULAR: - if(timeStamp==null) { - entryLineTimestamp = TIMESTAMP_DUMMY; - } else { - entryLineTimestamp = CVSDateFormatter.dateToEntryLine(timeStamp); - } break; - case TYPE_MERGED: - entryLineTimestamp = TIMESTAMP_MERGED; break; - case TYPE_MERGED_WITH_CONFLICTS: - entryLineTimestamp = TIMESTAMP_MERGED_WITH_CONFLICT + CVSDateFormatter.dateToEntryLine(timeStamp); break; - } - } - result.append(entryLineTimestamp); - } - result.append(SEPARATOR); - if (keywordMode != null) result.append(keywordMode.toMode()); - result.append(SEPARATOR); - if (tag != null) { - result.append(tag.toEntryLineFormat(true)); - } - } - return result.toString(); - } - - public boolean needsReporting() { - return false; - } - - public void reported() { - // do nothing - } - - /** - * Method getBytes. - * @return byte[] - */ - public byte[] getBytes() { - return getEntryLine().getBytes(); - } - - /** - * Method getName. - * @param syncBytes - * @return String - */ - public static String getName(byte[] syncBytes) throws CVSException { - String name = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 1, false); - if (name == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - return name; - } - - /** - * Method getKeywordMode. - * @param syncBytes - * @return String - */ - public static KSubstOption getKeywordMode(byte[] syncBytes) throws CVSException { - String mode = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 4, false); - if (mode == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - return KSubstOption.fromMode(mode); - } - - /** - * Method getKeywordMode. - * @param syncBytes - * @return String - */ - public static byte[] setKeywordMode(byte[] syncBytes, KSubstOption mode) throws CVSException { - return setKeywordMode(syncBytes, mode.toMode().getBytes()); - } - - /** - * Method getKeywordMode. - * @param syncBytes - * @return String - */ - public static byte[] setKeywordMode(byte[] syncBytes, byte[] modeBytes) throws CVSException { - return setSlot(syncBytes, 4, modeBytes); - } - - /** - * Return whether the provided syncBytes represent a binary file. - * @param syncBytes - * @return boolean - * @throws CVSException - */ - public static boolean isBinary(byte[] syncBytes) throws CVSException { - if (syncBytes == null) return false; - String mode = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 4, false); - if (mode == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - return "-kb".equals(mode); //$NON-NLS-1$ - } - - /** - * Method isFolder. - * @param syncBytes - * @return boolean - */ - public static boolean isFolder(byte[] syncBytes) { - return syncBytes.length > 0 && syncBytes[0] == 'D'; - } - - /** - * Method isAddition. - * @param syncBytes - * @return boolean - */ - public static boolean isAddition(byte[] syncBytes) throws CVSException { - int start = startOfSlot(syncBytes, 2); - if (start == -1 || start >= syncBytes.length) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - return syncBytes[start + 1] == '0'; - } - - /** - * Method isDeleted. - * @param syncBytes - * @return boolean - */ - public static boolean isDeletion(byte[] syncBytes) throws CVSException { - int start = startOfSlot(syncBytes, 2); - if (start == -1 || start >= syncBytes.length) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - return syncBytes[start + 1] == DELETED_PREFIX_BYTE; - } - - /** - * Method convertToDeletion. - * @param syncBytes - * @return byte[] - */ - public static byte[] convertToDeletion(byte[] syncBytes) throws CVSException { - int index = startOfSlot(syncBytes, 2); - if (index == -1) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - if (syncBytes.length > index && syncBytes[index+1] != DELETED_PREFIX_BYTE) { - byte[] newSyncBytes = new byte[syncBytes.length + 1]; - System.arraycopy(syncBytes, 0, newSyncBytes, 0, index + 1); - newSyncBytes[index + 1] = DELETED_PREFIX_BYTE; - System.arraycopy(syncBytes, index + 1, newSyncBytes, index + 2, syncBytes.length - index - 1); - return newSyncBytes; - } - return syncBytes; - } - - /** - * Method convertFromDeletion. - * @param syncBytes - * @return byte[] - */ - public static byte[] convertFromDeletion(byte[] syncBytes) throws CVSException { - int index = startOfSlot(syncBytes, 2); - if (index == -1) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - if (syncBytes.length > index && syncBytes[index+1] == DELETED_PREFIX_BYTE) { - byte[] newSyncBytes = new byte[syncBytes.length - 1]; - System.arraycopy(syncBytes, 0, newSyncBytes, 0, index + 1); - System.arraycopy(syncBytes, index + 2, newSyncBytes, index + 1, newSyncBytes.length - index - 1); - return newSyncBytes; - } - return syncBytes; - } - /** - * Method startOfSlot returns the index of the slash that occurs before the - * given slot index. The provided index should be >= 1 which assumes that - * slot zero occurs before the first slash. - * - * @param syncBytes - * @param i - * @return int - */ - private static int startOfSlot(byte[] syncBytes, int slot) { - int count = 0; - for (int j = 0; j < syncBytes.length; j++) { - byte b = syncBytes[j]; - if (syncBytes[j] == SEPARATOR_BYTE) { - count++; - if (count == slot) return j; - } - } - return -1; - } - - /** - * Method setSlot. - * @param syncBytes - * @param i - * @param b - * @return byte[] - */ - private static byte[] setSlot(byte[] syncBytes, int slot, byte[] newBytes) throws CVSException { - int start = startOfSlot(syncBytes, slot); - if (start == -1) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - int end = startOfSlot(syncBytes, slot + 1); - int totalLength = start + 1 + newBytes.length; - if (end != -1) { - totalLength += syncBytes.length - end; - } - byte[] result = new byte[totalLength]; - System.arraycopy(syncBytes, 0, result, 0, start + 1); - System.arraycopy(newBytes, 0, result, start + 1, newBytes.length); - if (end != -1) { - System.arraycopy(syncBytes, end, result, start + 1 + newBytes.length, syncBytes.length - end); - } - return result; - } - - /** - * Return the timestamp portion of the sync info that is to be sent to the - * server. - * - * @param syncBytes - * @param fileTimestamp - * @return String - */ - public static String getTimestampToServer(byte[] syncBytes, Date fileTimestamp) throws CVSException { - if(fileTimestamp != null) { - String syncTimestamp = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 3, false); - if (syncTimestamp == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - int syncType = getSyncType(syncTimestamp); - if (syncType != TYPE_REGULAR) { - if (syncType == TYPE_MERGED_WITH_CONFLICTS && fileTimestamp.equals(getTimestamp(syncTimestamp))) { - return TIMESTAMP_SERVER_MERGED_WITH_CONFLICT; - } else { - return TIMESTAMP_SERVER_MERGED; - } - } - } - return null; - } - /** - * Method getTimestamp. - * @param syncTimestamp - * @return Object - */ - private static Date getTimestamp(String syncTimestamp) { - String dateString= syncTimestamp; - if(syncTimestamp.indexOf(ResourceSyncInfo.TIMESTAMP_SERVER_MERGED) != -1) { - dateString = null; - } else if(syncTimestamp.indexOf(ResourceSyncInfo.TIMESTAMP_SERVER_MERGED_WITH_CONFLICT) != -1) { - dateString = null; - } else if(syncTimestamp.indexOf(TIMESTAMP_MERGED_WITH_CONFLICT)!=-1) { - dateString = syncTimestamp.substring(syncTimestamp.indexOf("+") + 1); //$NON-NLS-1$ - } else if(syncTimestamp.indexOf(TIMESTAMP_MERGED)!=-1) { - dateString = null; - } - - if(dateString==null || "".equals(dateString)) { //$NON-NLS-1$ - return null; - } else { - try { - return CVSDateFormatter.entryLineToDate(dateString); - } catch(ParseException e) { - // something we don't understand, just make this sync have no timestamp and - // never be in sync with the server. - return null; - } - } - } - - /** - * Method getSyncType. - * @param syncTimestamp - * @return int - */ - private static int getSyncType(String date) { - if(date.indexOf(ResourceSyncInfo.TIMESTAMP_SERVER_MERGED) != -1) { - return TYPE_MERGED; - } else if(date.indexOf(ResourceSyncInfo.TIMESTAMP_SERVER_MERGED_WITH_CONFLICT) != -1) { - return TYPE_MERGED_WITH_CONFLICTS; - } else if(date.indexOf(TIMESTAMP_MERGED_WITH_CONFLICT)!=-1) { - return TYPE_MERGED_WITH_CONFLICTS; - } else if(date.indexOf(TIMESTAMP_MERGED)!=-1) { - return TYPE_MERGED; - } - return TYPE_REGULAR; - } - - /** - * Method getTag. - * @param syncBytes - * @return String - */ - public static byte[] getTagBytes(byte[] syncBytes) throws CVSException { - byte[] tag = Util.getBytesForSlot(syncBytes, SEPARATOR_BYTE, 5, true); - if (tag == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - return tag; - } - - /** - * Method setTag. - * @param syncBytes - * @param tagString - * @return byte[] - */ - public static byte[] setTag(byte[] syncBytes, byte[] tagBytes) throws CVSException { - return setSlot(syncBytes, 5, tagBytes); - } - - /** - * Method setTag. - * @param syncBytes - * @param tag - * @return ResourceSyncInfo - */ - public static byte[] setTag(byte[] syncBytes, CVSTag tag) throws CVSException { - CVSEntryLineTag entryTag; - if (tag instanceof CVSEntryLineTag) { - entryTag = (CVSEntryLineTag)tag; - } else { - entryTag = new CVSEntryLineTag(tag); - } - return setTag(syncBytes, entryTag.toEntryLineFormat(true).getBytes()); - } - - /** - * Method getRevision. - * @param syncBytes - */ - public static String getRevision(byte[] syncBytes) throws CVSException { - String revision = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 2, false); - if (revision == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - if(revision.startsWith(DELETED_PREFIX)) { - revision = revision.substring(DELETED_PREFIX.length()); - } - return revision; - } - - /** - * Method setRevision. - * @param syncBytes - * @param revision - * @return byte[] - */ - public static byte[] setRevision(byte[] syncBytes, String revision) throws CVSException { - return setSlot(syncBytes, 2, revision.getBytes()); - } - - /** - * Method isMerge. - * @param syncBytes1 - * @return boolean - */ - public static boolean isMerge(byte[] syncBytes) throws CVSException { - String timestamp = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 3, false); - if (timestamp == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - int syncType = getSyncType(timestamp); - return syncType == TYPE_MERGED || syncType == TYPE_MERGED_WITH_CONFLICTS; - } - - /** - * Method isMerge. - * @param syncBytes1 - * @return boolean - */ - public static boolean isMergedWithConflicts(byte[] syncBytes) throws CVSException { - String timestamp = Util.getSubstring(syncBytes, SEPARATOR_BYTE, 3, false); - if (timestamp == null) { - throw new CVSException(Policy.bind("ResourceSyncInfo.malformedSyncBytes", new String(syncBytes))); //$NON-NLS-1$ - } - int syncType = getSyncType(timestamp); - return syncType == TYPE_MERGED_WITH_CONFLICTS; - } - -}
\ No newline at end of file diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ResourceSynchronizer.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ResourceSynchronizer.java deleted file mode 100644 index e3b936a08..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/syncinfo/ResourceSynchronizer.java +++ /dev/null @@ -1,76 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.syncinfo; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.core.sync.IRemoteResource; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSStatus; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFile; -import org.eclipse.team.internal.ccvs.core.resources.RemoteFolder; - -/** - * A resource synchronizer is responsible for managing synchronization information for - * CVS resources. - */ -public abstract class ResourceSynchronizer { - - protected abstract QualifiedName getSyncName(); - - public IRemoteResource getRemoteResource(IResource resource) throws TeamException { - byte[] remoteBytes = getSyncBytes(resource); - if (remoteBytes == null) { - // There is no remote handle for this resource - return null; - } else { - // TODO: This code assumes that the type of the remote resource - // matches that of the local resource. This may not be true. - // TODO: This is rather complicated. There must be a better way! - if (resource.getType() == IResource.FILE) { - byte[] parentBytes = getSyncBytes(resource.getParent()); - if (parentBytes == null) { - CVSProviderPlugin.log(new CVSStatus(IStatus.ERROR, - Policy.bind("ResourceSynchronizer.missingBytes", getSyncName().toString(), resource.getParent().getFullPath().toString()))); - throw new TeamException(Policy.bind("internal")); - } - return RemoteFile.fromBytes(resource, remoteBytes, parentBytes); - } else { - return RemoteFolder.fromBytes((IContainer)resource, remoteBytes); - } - } - } - - public abstract byte[] getSyncBytes(IResource resource) throws CVSException; - - /** - * Refreshes the contents of the resource synchronizer and returns the list - * of resources whose remote sync state changed. The <code>cacheFileContentsHint</code> - * indicates that the user of this synchronizer will be using the file contents. Subclasses can decide - * whether to cache file contents during the refresh or to allow them to be fetched when request. - * @param resources - * @param depth - * @param cacheFileContentsHint a hint which indicates whether file contents will be used - * @param monitor - * @return - * @throws TeamException - */ - public IResource[] refresh(IResource[] resources, int depth, boolean cacheFileContentsHint, IProgressMonitor monitor) throws TeamException { - return new IResource[0]; - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/AddDeleteMoveListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/AddDeleteMoveListener.java deleted file mode 100644 index 36532a5b9..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/AddDeleteMoveListener.java +++ /dev/null @@ -1,237 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceChangeEvent; -import org.eclipse.core.resources.IResourceChangeListener; -import org.eclipse.core.resources.IResourceDelta; -import org.eclipse.core.resources.IResourceDeltaVisitor; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSRunnable; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.EclipseSynchronizer; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * Listen for the addition of orphaned subtrees as a result of a copy or move. - */ -public class AddDeleteMoveListener implements IResourceDeltaVisitor, IResourceChangeListener { - - public static IResource getResourceFor(IProject container, IResource destination, IPath originating) { - switch(destination.getType()) { - case IResource.FILE : return container.getFile(originating); - case IResource.FOLDER: return container.getFolder(originating); - case IResource.PROJECT: return ResourcesPlugin.getWorkspace().getRoot().getProject(originating.toString()); - } - return destination; - } - - /** - * @see IResourceDeltaVisitor#visit(IResourceDelta) - */ - public boolean visit(IResourceDelta delta) throws CoreException { - IResource resource = delta.getResource(); - IProject project = resource.getProject(); - boolean movedTo = (delta.getFlags() & IResourceDelta.MOVED_TO) > 0; - boolean movedFrom = (delta.getFlags() & IResourceDelta.MOVED_FROM) > 0; - switch (delta.getKind()) { - case IResourceDelta.ADDED : - // make sure the added resource isn't a phantom - if (resource.exists()) { - if (resource.getType() == IResource.FOLDER) { - handleOrphanedSubtree((IContainer)resource); - handleAddedFolder((IFolder) resource); - } else if (resource.getType() == IResource.FILE) { - handleAddedFile((IFile)resource); - } - } - break; - case IResourceDelta.REMOVED : - if (resource.getType() == IResource.FILE) { - handleDeletedFile((IFile)resource); - } - break; - case IResourceDelta.CHANGED : - // This state means there is a resource before and after but changes were made by deleting and moving. - // For files, we shouldn'd do anything. - // For folders, we should purge the CVS info - if (resource.getType() == IResource.FOLDER && resource.exists()) { - // When folders are moved, purge the CVS folders - if (movedFrom) - return ! handleOrphanedSubtree((IContainer)resource); - if ((delta.getFlags() & IResourceDelta.REPLACED) > 0) { - handleAddedFolder((IFolder)resource); - return true; - } - } - break; - } - return true; - } - - /* - * Determine if the container is an orphaned subtree. - * If it is, handle it and return true. - * Otherwise, return false - */ - private boolean handleOrphanedSubtree(IContainer resource) { - try { - ICVSFolder mFolder = CVSWorkspaceRoot.getCVSFolderFor((IContainer)resource); - if (mFolder.isCVSFolder() && ! mFolder.isManaged() && mFolder.getIResource().getParent().getType() != IResource.ROOT) { - // linked resources are not considered orphans even if they have CVS folders in them - if (isLinkedResource(mFolder)) return false; - mFolder.unmanage(null); - return true; - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - return false; - } - - private boolean isLinkedResource(ICVSResource cvsResource) throws CVSException { - IResource iResource = cvsResource.getIResource(); - if (iResource != null) - return CVSWorkspaceRoot.isLinkedResource(iResource); - return false; - } - /* - * Mark deleted managed files as outgoing deletions - */ - private void handleDeletedFile(IFile resource) { - try { - ICVSFile mFile = CVSWorkspaceRoot.getCVSFileFor((IFile)resource); - byte[] syncBytes = mFile.getSyncBytes(); - if (syncBytes != null) { - if (ResourceSyncInfo.isAddition(syncBytes)) { - mFile.unmanage(null); - } else if ( ! ResourceSyncInfo.isDeletion(syncBytes)) { - mFile.setSyncBytes(ResourceSyncInfo.convertToDeletion(syncBytes), ICVSFile.UNKNOWN); - } - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - } - - /* - * Handle the case where an added file has the same name as a "cvs removed" file - * by restoring the sync info to what it was before the delete - */ - private void handleAddedFile(IFile resource) { - try { - EclipseSynchronizer.getInstance().created(resource); - ICVSFile mFile = CVSWorkspaceRoot.getCVSFileFor((IFile)resource); - byte[] syncBytes = mFile.getSyncBytes(); - if (syncBytes != null) { - if (ResourceSyncInfo.isDeletion(syncBytes)) { - // Handle a replaced deletion - mFile.setSyncBytes(ResourceSyncInfo.convertFromDeletion(syncBytes), ICVSFile.UNKNOWN); - } else if (ResourceSyncInfo.isFolder(syncBytes)) { - // This is a gender change against the server! - // We will allow it but the user will get an error if they try to commit - mFile.unmanage(null); - } - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - } - - private void handleAddedFolder(IFolder resource) { - try { - EclipseSynchronizer.getInstance().created(resource); - ICVSFolder mFolder = CVSWorkspaceRoot.getCVSFolderFor(resource); - if (mFolder.isManaged()) { - ResourceSyncInfo info = mFolder.getSyncInfo(); - if ( ! info.isDirectory()) { - // This is a gender change against the server! - // Operation failure will notify the user of this situation - mFolder.unmanage(null); - } - } - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - } - - public void resourceChanged(IResourceChangeEvent event) { - try { - IResourceDelta root = event.getDelta(); - IResourceDelta[] projectDeltas = root.getAffectedChildren(); - for (int i = 0; i < projectDeltas.length; i++) { - final IResourceDelta delta = projectDeltas[i]; - IResource resource = delta.getResource(); - - if (resource.getType() == IResource.PROJECT) { - // If the project is not accessible, don't process it - if (!resource.isAccessible()) continue; - if ((delta.getFlags() & IResourceDelta.OPEN) != 0) continue; - } - - RepositoryProvider provider = RepositoryProvider.getProvider(resource.getProject(), CVSProviderPlugin.getTypeId()); - - // Make sure that the project is a CVS folder. - ICVSFolder folder = CVSWorkspaceRoot.getCVSFolderFor(resource.getProject()); - if (provider != null) { - try { - if (! folder.isCVSFolder()) { - RepositoryProvider.unmap(resource.getProject()); - provider = null; - } - } catch (TeamException e) { - CVSProviderPlugin.log(e); - } - } - - // if a project is moved the originating project will not be associated with the CVS provider - // however listeners will probably still be interested in the move delta. - if ((delta.getFlags() & IResourceDelta.MOVED_TO) > 0) { - IResource destination = getResourceFor(resource.getProject(), resource, delta.getMovedToPath()); - provider = RepositoryProvider.getProvider(destination.getProject()); - } - - if(provider!=null) { - // Traverse the delta is a runnable so that files are only written at the end - folder.run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - try { - delta.accept(AddDeleteMoveListener.this); - } catch (CoreException e) { - Util.logError(Policy.bind("ResourceDeltaVisitor.visitError"), e);//$NON-NLS-1$ - } - } - }, Policy.monitorFor(null)); - } - } - } catch (CVSException e) { - Util.logError(Policy.bind("ResourceDeltaVisitor.visitError"), e);//$NON-NLS-1$ - } - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/Assert.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/Assert.java deleted file mode 100644 index f24cb6720..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/Assert.java +++ /dev/null @@ -1,104 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -/** - * <code>Assert</code> is useful for for embedding runtime sanity checks - * in code. - * The predicate methods all test a condition and throw some - * type of unchecked exception if the condition does not hold. - * <p> - * Assertion failure exceptions, like most runtime exceptions, are - * thrown when something is misbehaving. Assertion failures are invariably - * unspecified behavior; consequently, clients should never rely on - * these being thrown (and certainly should not being catching them - * specifically). - * </p> - */ -public final class Assert { - /* This class is not intended to be instantiated. */ - private Assert() { - } - /** Asserts that an argument is legal. If the given boolean is - * not <code>true</code>, an <code>IllegalArgumentException</code> - * is thrown. - * - * @param expression the outcode of the check - * @return <code>true</code> if the check passes (does not return - * if the check fails) - * @exception IllegalArgumentException if the legality test failed - */ - public static boolean isLegal(boolean expression) { - return isLegal(expression, ""); //$NON-NLS-1$ - } - /** Asserts that an argument is legal. If the given boolean is - * not <code>true</code>, an <code>IllegalArgumentException</code> - * is thrown. - * The given message is included in that exception, to aid debugging. - * - * @param expression the outcode of the check - * @param message the message to include in the exception - * @return <code>true</code> if the check passes (does not return - * if the check fails) - * @exception IllegalArgumentException if the legality test failed - */ - public static boolean isLegal(boolean expression, String message) { - if (!expression) - throw new IllegalArgumentException(message); - return expression; - } - /** Asserts that the given object is not <code>null</code>. If this - * is not the case, some kind of unchecked exception is thrown. - * - * @param object the value to test - * @exception IllegalArgumentException if the object is <code>null</code> - */ - public static void isNotNull(Object object) { - isNotNull(object, ""); //$NON-NLS-1$ - } - /** Asserts that the given object is not <code>null</code>. If this - * is not the case, some kind of unchecked exception is thrown. - * The given message is included in that exception, to aid debugging. - * - * @param object the value to test - * @param message the message to include in the exception - * @exception IllegalArgumentException if the object is <code>null</code> - */ - public static void isNotNull(Object object, String message) { - if (object == null) - throw new AssertionFailedException("null argument:" + message); //$NON-NLS-1$ - } - /** Asserts that the given boolean is <code>true</code>. If this - * is not the case, some kind of unchecked exception is thrown. - * - * @param expression the outcode of the check - * @return <code>true</code> if the check passes (does not return - * if the check fails) - */ - public static boolean isTrue(boolean expression) { - return isTrue(expression, ""); //$NON-NLS-1$ - } - /** Asserts that the given boolean is <code>true</code>. If this - * is not the case, some kind of unchecked exception is thrown. - * The given message is included in that exception, to aid debugging. - * - * @param expression the outcode of the check - * @param message the message to include in the exception - * @return <code>true</code> if the check passes (does not return - * if the check fails) - */ - public static boolean isTrue(boolean expression, String message) { - if (!expression) - throw new AssertionFailedException("assertion failed: " + message); //$NON-NLS-1$ - return expression; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/AssertionFailedException.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/AssertionFailedException.java deleted file mode 100644 index 97bf4f022..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/AssertionFailedException.java +++ /dev/null @@ -1,34 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -/** - * <code>AssertionFailedException</code> is a runtime exception thrown - * by some of the methods in <code>Assert</code>. - * <p> - * This class is not declared public to prevent some misuses; programs that catch - * or otherwise depend on assertion failures are susceptible to unexpected - * breakage when assertions in the code are added or removed. - * </p> - */ -/* package */ -class AssertionFailedException extends RuntimeException { -/** Constructs a new exception. - */ -public AssertionFailedException() { -} -/** Constructs a new exception with the given message. - */ -public AssertionFailedException(String detail) { - super(detail); -} -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/CVSDateFormatter.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/CVSDateFormatter.java deleted file mode 100644 index e952b9cb9..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/CVSDateFormatter.java +++ /dev/null @@ -1,104 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import java.text.ParseException; -import java.text.SimpleDateFormat; -import java.util.Date; -import java.util.Locale; -import java.util.TimeZone; - -/** - * Utility class for converting timestamps used in Entry file lines. The format - * required in the Entry file is ISO C asctime() function (Sun Apr 7 01:29:26 1996). - * <p> - * To be compatible with asctime(), the day field in the entryline format is - * padded with a space and not a zero. Most other CVS clients use string comparison - * for timestamps based on the result of the C function asctime(). - * </p> - */ -public class CVSDateFormatter { - - private static final String ENTRYLINE_FORMAT = "E MMM dd HH:mm:ss yyyy"; //$NON-NLS-1$ - private static final String SERVER_FORMAT = "dd MMM yyyy HH:mm:ss";//$NON-NLS-1$ - private static final int ENTRYLINE_TENS_DAY_OFFSET = 8; - - private static final SimpleDateFormat serverFormat = new SimpleDateFormat(SERVER_FORMAT, Locale.US); - private static SimpleDateFormat entryLineFormat = new SimpleDateFormat(ENTRYLINE_FORMAT, Locale.US); - - static { - entryLineFormat.setTimeZone(TimeZone.getTimeZone("GMT")); //$NON-NLS-1$ - } - static public Date serverStampToDate(String text) throws ParseException { - serverFormat.setTimeZone(getTimeZone(text)); - Date date = serverFormat.parse(text); - return date; - } - - static public String dateToServerStamp(Date date) { - serverFormat.setTimeZone(TimeZone.getTimeZone("GMT"));//$NON-NLS-1$ - return serverFormat.format(date) + " -0000"; //$NON-NLS-1$ - } - - static public Date entryLineToDate(String text) throws ParseException { - try { - if (text.charAt(ENTRYLINE_TENS_DAY_OFFSET) == ' ') { - StringBuffer buf = new StringBuffer(text); - buf.setCharAt(ENTRYLINE_TENS_DAY_OFFSET, '0'); - text = buf.toString(); - } - } catch (StringIndexOutOfBoundsException e) { - throw new ParseException(e.getMessage(), ENTRYLINE_TENS_DAY_OFFSET); - } - return entryLineFormat.parse(text); - } - - static public String dateToEntryLine(Date date) { - if (date == null) return ""; //$NON-NLS-1$ - String passOne = entryLineFormat.format(date); - if (passOne.charAt(ENTRYLINE_TENS_DAY_OFFSET) != '0') return passOne; - StringBuffer passTwo = new StringBuffer(passOne); - passTwo.setCharAt(ENTRYLINE_TENS_DAY_OFFSET, ' '); - return passTwo.toString(); - } - - static public String dateToNotifyServer(Date date) { - serverFormat.setTimeZone(TimeZone.getTimeZone("GMT"));//$NON-NLS-1$ - return serverFormat.format(date) + " GMT"; //$NON-NLS-1$ - } - - /* - * Converts timezone text from date string from CVS server and - * returns a timezone representing the received timezone. - * Timezone string is of the following format: [-|+]MMSS - */ - static private TimeZone getTimeZone(String dateFromServer) { - String tz = null; - StringBuffer resultTz = new StringBuffer("GMT");//$NON-NLS-1$ - if (dateFromServer.indexOf("-") != -1) {//$NON-NLS-1$ - resultTz.append("-");//$NON-NLS-1$ - tz = dateFromServer.substring(dateFromServer.indexOf("-"));//$NON-NLS-1$ - } else if (dateFromServer.indexOf("+") != -1) {//$NON-NLS-1$ - resultTz.append('+'); - tz = dateFromServer.substring(dateFromServer.indexOf("+"));//$NON-NLS-1$ - } - try { - if(tz!=null) { - resultTz.append(tz.substring(1, 3) /*hours*/ + ":" + tz.substring(3, 5) /*minutes*/);//$NON-NLS-1$ - return TimeZone.getTimeZone(resultTz.toString()); - } - } catch(IndexOutOfBoundsException e) { - return TimeZone.getTimeZone("GMT");//$NON-NLS-1$ - } - return TimeZone.getTimeZone("GMT");//$NON-NLS-1$ - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/FileNameMatcher.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/FileNameMatcher.java deleted file mode 100644 index 2447dacf1..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/FileNameMatcher.java +++ /dev/null @@ -1,72 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import java.util.ArrayList; -import java.util.List; - -/** - * A FileNameMatcher associates a String with a String pattern. - */ -public class FileNameMatcher { - - private List matchers = new ArrayList(); - private List results = new ArrayList(); - private static final String TRUE = "true"; //$NON-NLS-1$ - - public FileNameMatcher() { - } - - public FileNameMatcher(String[] patterns) { - register(patterns); - } - - void register(String[] patterns) { - for (int i = 0; i < patterns.length; i++) { - register(patterns[i],TRUE); - } - } - - public void register(String pattern, String result) { - - Assert.isTrue(matchers.size() == results.size()); - - pattern = pattern.trim(); - - // The empty pattern matches everything, but we want to match - // nothing with it, so we just do not register anything - if (pattern.length() == 0) { - return; - } - - matchers.add(new StringMatcher(pattern,false,false)); - results.add(result); - - } - - public String getMatch(String name) { - StringMatcher stringMatcher; - - for (int i = 0; i < matchers.size(); i++) { - stringMatcher = (StringMatcher) matchers.get(i); - if (stringMatcher.match(name)) { - return (String)results.get(i); - } - } - - return null; - } - - public boolean match(String name) { - return getMatch(name) != null; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/MoveDeleteHook.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/MoveDeleteHook.java deleted file mode 100644 index 11edd41eb..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/MoveDeleteHook.java +++ /dev/null @@ -1,332 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFileModificationValidator; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IProjectDescription; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceVisitor; -import org.eclipse.core.resources.team.IMoveDeleteHook; -import org.eclipse.core.resources.team.IResourceTree; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSTeamProvider; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFileModificationValidator; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSRunnable; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.EclipseSynchronizer; - -/** - * This hook exists to ensure that folders deletions will be recorded so that outgoing file - * deletions can be properly communicated to the server. - */ -public class MoveDeleteHook implements IMoveDeleteHook { - - /** - * @see IMoveDeleteHook#deleteFile(IResourceTree, IFile, int, IProgressMonitor) - */ - public boolean deleteFile( - final IResourceTree tree, - final IFile file, - final int updateFlags, - IProgressMonitor monitor) { - - try { - // No special handling required for team-private members - if (file.isTeamPrivateMember()) return false; - // If the file is ignored by CVS then we can just delete it. - ICVSFile cvsFile = CVSWorkspaceRoot.getCVSFileFor(file); - if (cvsFile.isIgnored()) return false; - // Otherwise, we need to prepare properly for the delete - EclipseSynchronizer.getInstance().run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - try { - monitor.beginTask(null, 100); - if (checkOutFiles(tree, new IFile[] {file}, Policy.subMonitorFor(monitor, 35))) { - EclipseSynchronizer.getInstance().prepareForMoveDelete(file, Policy.subMonitorFor(monitor, 30)); - tree.standardDeleteFile(file, updateFlags, Policy.subMonitorFor(monitor, 35)); - } - } finally { - monitor.done(); - } - } - }, monitor); - } catch (CVSException e) { - tree.failed(e.getStatus()); - } - return true; - } - - /** - * @see IMoveDeleteHook#deleteFolder(IResourceTree, IFolder, int, IProgressMonitor) - */ - public boolean deleteFolder( - final IResourceTree tree, - final IFolder folder, - final int updateFlags, - IProgressMonitor monitor) { - - // No special handling required for team-private members - if (folder.isTeamPrivateMember()) return false; - monitor.beginTask(null, 100); - try { - final ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor(folder); - if (cvsFolder.isManaged() && ensureCheckedOut(new IFolder[] {folder}, tree, Policy.subMonitorFor(monitor, 30))) { - EclipseSynchronizer.getInstance().run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - try { - monitor.beginTask(null, 100); - EclipseSynchronizer.getInstance().prepareForMoveDelete(folder, Policy.subMonitorFor(monitor, 50)); - tree.standardDeleteFolder(folder, updateFlags, Policy.subMonitorFor(monitor, 50)); - } finally { - monitor.done(); - } - } - }, Policy.subMonitorFor(monitor, 70)); - return true; - } else if (!cvsFolder.isIgnored()) { - prepareToDelete(cvsFolder); - } - } catch (CVSException e) { - tree.failed(e.getStatus()); - } finally { - monitor.done(); - } - return false; - } - - /** - * @see IMoveDeleteHook#deleteProject(IResourceTree, IProject, int, IProgressMonitor) - */ - public boolean deleteProject( - IResourceTree tree, - IProject project, - int updateFlags, - IProgressMonitor monitor) { - - // We need to flush any remembered folder deletions for the deleted project. - // All other sync info is stored in session and persistant properties, which - // are deleted when the associated resources are deleted - try { - EclipseSynchronizer.getInstance().prepareForDeletion(project); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - // todo: Perform a "cvs release" if there are any edits on the project - return false; - } - - /** - * @see IMoveDeleteHook#moveFile(IResourceTree, IFile, IFile, int, IProgressMonitor) - */ - public boolean moveFile( - final IResourceTree tree, - final IFile source, - final IFile destination, - final int updateFlags, - IProgressMonitor monitor) { - - try { - EclipseSynchronizer.getInstance().run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - try { - monitor.beginTask(null, 100); - // ensure we can write to both the source and the destination - IFile[] filesToCheckOut; - if (destination.exists()) { - filesToCheckOut = new IFile[] {source, destination}; - } else { - filesToCheckOut = new IFile[] {source}; - } - if (checkOutFiles(tree, filesToCheckOut, Policy.subMonitorFor(monitor, 30))) { - EclipseSynchronizer.getInstance().prepareForMoveDelete(source, Policy.subMonitorFor(monitor, 20)); - if (destination.exists()) { - EclipseSynchronizer.getInstance().prepareForMoveDelete(destination, Policy.subMonitorFor(monitor, 20)); - } - tree.standardMoveFile(source, destination, updateFlags, Policy.subMonitorFor(monitor, 30)); - EclipseSynchronizer.getInstance().created(destination); - } - } finally { - monitor.done(); - } - } - }, monitor); - } catch (CVSException e) { - tree.failed(e.getStatus()); - } - return true; - } - - /** - * @see IMoveDeleteHook#moveFolder(IResourceTree, IFolder, IFolder, int, IProgressMonitor) - */ - public boolean moveFolder( - final IResourceTree tree, - final IFolder source, - final IFolder destination, - final int updateFlags, - IProgressMonitor monitor) { - - monitor.beginTask(null, 100); - try { - final ICVSFolder cvsFolder = CVSWorkspaceRoot.getCVSFolderFor(source); - if (cvsFolder.isManaged()) { - if (!ensureCheckedOut(new IFolder[] {source, destination}, tree, Policy.subMonitorFor(monitor, 20))) return true; - EclipseSynchronizer.getInstance().run(new ICVSRunnable() { - public void run(IProgressMonitor monitor) throws CVSException { - EclipseSynchronizer.getInstance().prepareForMoveDelete(source, Policy.subMonitorFor(monitor, 20)); - if (destination.exists()) { - EclipseSynchronizer.getInstance().prepareForMoveDelete(destination, Policy.subMonitorFor(monitor, 20)); - } - tree.standardMoveFolder(source, destination, updateFlags, Policy.subMonitorFor(monitor, 30)); - purgeCVSFolders(destination, Policy.subMonitorFor(monitor, 20)); - } - private void purgeCVSFolders(IFolder destination, final IProgressMonitor monitor) throws CVSException { - // Delete any CVS folders - try { - destination.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - if (resource.getType() == IResource.FOLDER && resource.getName().equals(SyncFileWriter.CVS_DIRNAME)) { - tree.standardDeleteFolder((IFolder)resource, updateFlags, monitor); - return false; - } - return true; - } - }, IResource.DEPTH_INFINITE, IContainer.INCLUDE_TEAM_PRIVATE_MEMBERS); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - // Signal that the destination has been created so any previous - // sync info will be restored - EclipseSynchronizer.getInstance().created(destination); - } - }, Policy.subMonitorFor(monitor, 60)); - return true; - } else if (!cvsFolder.isIgnored()) { - // XXX Should be inside cvs runnable - prepareToDelete(cvsFolder); - } - } catch (CVSException e) { - tree.failed(e.getStatus()); - return true; - } finally { - monitor.done(); - } - - return false; - } - - /** - * @see IMoveDeleteHook#moveProject(IResourceTree, IProject, IProjectDescription, int, IProgressMonitor) - */ - public boolean moveProject( - IResourceTree tree, - IProject source, - IProjectDescription description, - int updateFlags, - IProgressMonitor monitor) { - - // We need to move (or flush) any remembered folder deletions for the deleted project - // XXX We flush for now. This means that deleting a managed folder and then moving the - // project will mean that the file deletions will be lost. It also means that phantom - // folders are lost. - try { - EclipseSynchronizer.getInstance().prepareForDeletion(source); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - } - return false; - } - - /** - * Ensure that the given file is checked out (i.e. not read only). Return - * true if it is OK to procede and false otherwise. - * - * @param tree - * @param file - * @return boolean - */ - private boolean checkOutFiles(IResourceTree tree, IFile[] files, IProgressMonitor monitor) { - // Ensure that the file is "checked out" (i.e. not read-only - IFileModificationValidator validator = getFileModificationValidator(files); - if (validator instanceof ICVSFileModificationValidator) { - IStatus status = ((ICVSFileModificationValidator)validator).validateMoveDelete(files, monitor); - if (status.isOK()) { - return true; - } else { - tree.failed(status); - return false; - } - } - return true; - } - - private boolean ensureCheckedOut(IFolder[] folders, IResourceTree tree, IProgressMonitor monitor) { - final List readOnlyFiles = new ArrayList(); - try { - // Find any read-only files - for (int i = 0; i < folders.length; i++) { - IFolder folder = folders[i]; - if (folder.exists()) { - folder.accept(new IResourceVisitor() { - public boolean visit(IResource resource) throws CoreException { - if (resource.getType() == IResource.FILE) { - IFile file = (IFile) resource; - if (file.isReadOnly()) { - readOnlyFiles.add(file); - } - } - return true; - } - }); - } - } - if (readOnlyFiles.isEmpty()) return true; - // Ensure read-only files are checked out - return checkOutFiles(tree, (IFile[]) readOnlyFiles.toArray(new IFile[readOnlyFiles.size()]), monitor); - } catch (CoreException e) { - tree.failed(e.getStatus()); - return false; - } - } - - private IFileModificationValidator getFileModificationValidator(IFile[] files) { - return getProvider(files).getFileModificationValidator(); - } - - private CVSTeamProvider getProvider(IFile[] files) { - CVSTeamProvider provider = (CVSTeamProvider)RepositoryProvider.getProvider(files[0].getProject(), CVSProviderPlugin.getTypeId()); - return provider; - } - - /* - * Signal that the unmanaged resource is about to be deleted so that the - * dirty count of it's parent can be reduced if appropriate. - */ - private void prepareToDelete(ICVSResource resource) throws CVSException { - EclipseSynchronizer.getInstance().prepareForDeletion(resource.getIResource()); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/PrepareForReplaceVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/PrepareForReplaceVisitor.java deleted file mode 100644 index 4fef8987f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/PrepareForReplaceVisitor.java +++ /dev/null @@ -1,111 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -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.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * This class is used to prepare a local CVS workspace for replacement by - * the corresponding remote resources. More specifically, this class will - * unmanage added and deleted resources so that, after the operation, the - * resources in the local workspace will either correspond to the remote - * counterparts or be unmanaged. - */ -public class PrepareForReplaceVisitor implements ICVSResourceVisitor { - - private IProgressMonitor monitor; - private int depth; - - /** - * @see ICVSResourceVisitor#visitFile(ICVSFile) - */ - public void visitFile(ICVSFile file) throws CVSException { - byte[] syncBytes = file.getSyncBytes(); - if (syncBytes == null) { - // Delete unmanaged files if the user wants them deleted - if (CVSProviderPlugin.getPlugin().isReplaceUnmanaged()) { - file.delete(); - } - } else if (ResourceSyncInfo.isAddition(syncBytes)) { - file.delete(); - file.unmanage(null); - } else if (ResourceSyncInfo.isDeletion(syncBytes)) { - // If deleted, null the sync info so the file will be refetched - file.unmanage(null); - } else if (file.isModified(null)) { - // If the file is modified, delee and unmanage it and allow the - // replace operaton to fetch it again. This isrequired because "update -C" - // will fail for locally modified resources that have been deleted remotely. - file.unmanage(null); - file.delete(); - } - monitor.worked(1); - } - - /** - * @see ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder folder) throws CVSException { - // Delete unmanaged folders if the user wants them deleted - if (!folder.isCVSFolder() && CVSProviderPlugin.getPlugin().isReplaceUnmanaged()) { - folder.delete(); - } else { - // Visit the children of the folder as appropriate - if (depth == IResource.DEPTH_INFINITE) { - folder.acceptChildren(this); - } else if (depth == IResource.DEPTH_ONE) { - ICVSResource[] files = folder.members(ICVSFolder.FILE_MEMBERS); - for (int i = 0; i < files.length; i++) { - files[i].accept(this); - } - } - // Also delete ignored child files that start with .# - ICVSResource[] ignoredFiles = folder.members(ICVSFolder.FILE_MEMBERS | ICVSFolder.IGNORED_MEMBERS); - for (int i = 0; i < ignoredFiles.length; i++) { - ICVSResource cvsResource = ignoredFiles[i]; - if (cvsResource.getName().startsWith(".#")) { //$NON-NLS-1$ - cvsResource.delete(); - } - } - } - monitor.worked(1); - } - - public void visitResources(IProject project, final IResource[] resources, final String key, int depth, IProgressMonitor pm) throws CVSException { - this.depth = depth; - CVSWorkspaceRoot.getCVSFolderFor(project).run(new ICVSRunnable() { - public void run(IProgressMonitor pm) throws CVSException { - monitor = Policy.infiniteSubMonitorFor(pm, 100); - monitor.beginTask(null, 512); - for (int i = 0; i < resources.length; i++) { - if (key != null) { - monitor.subTask(Policy.bind(key, resources[i].getFullPath().toString())); //$NON-NLS-1$ - } - IResource resource = resources[i]; - CVSWorkspaceRoot.getCVSResourceFor(resource).accept(PrepareForReplaceVisitor.this); - } - monitor.done(); - } - }, pm); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionContentHandler.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionContentHandler.java deleted file mode 100644 index 4d412a8eb..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionContentHandler.java +++ /dev/null @@ -1,166 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Stack; - -import org.eclipse.core.resources.ICommand; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IProjectDescription; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.xml.sax.Attributes; -import org.xml.sax.ContentHandler; -import org.xml.sax.Locator; -import org.xml.sax.SAXException; - -public class ProjectDescriptionContentHandler implements ContentHandler { - - IProjectDescription desc; - boolean inProjectDescription = false; - - boolean inComment = false; - StringBuffer buffer = new StringBuffer(); - - boolean inBuilder = false; - List builders = new ArrayList(); - ICommand currentBuilder = null; - Map args = new HashMap(); - - List natures = new ArrayList(); - - List references = new ArrayList(); - - Stack tagStack = new Stack(); - - ProjectDescriptionContentHandler(IProjectDescription desc) { - this.desc = desc; - } - /** - * @see ContentHandler#characters(char[], int, int) - */ - public void characters(char[] chars, int startIndex, int length) - throws SAXException { - buffer.append(chars, startIndex, length); - } - /** - * @see ContentHandler#endDocument() - */ - public void endDocument() throws SAXException { - } - /** - * @see ContentHandler#endElement(java.lang.String, java.lang.String, java.lang.String) - */ - public void endElement(String namespaceURI, String localName, String qName) - throws SAXException { - if (localName.equals("project-description") && inProjectDescription) { //$NON-NLS-1$ - inProjectDescription = false; - desc.setBuildSpec((ICommand[]) builders.toArray(new ICommand[builders.size()])); - desc.setNatureIds((String[]) natures.toArray(new String[natures.size()])); - desc.setReferencedProjects( - (IProject[]) references.toArray(new IProject[references.size()])); - } else if (localName.equals("comment") && inProjectDescription && inComment) { //$NON-NLS-1$ - inComment = false; - desc.setComment(buffer.toString()); - } else if (localName.equals("builder") && inProjectDescription && inBuilder) { //$NON-NLS-1$ - inBuilder = false; - currentBuilder.setArguments(args); - if (currentBuilder.getBuilderName() != null) - builders.add(currentBuilder); - } - if (!localName.equals(tagStack.peek())) { - throw new RuntimeException(Policy.bind("ProjectDescriptionContentHandler.xml")); //$NON-NLS-1$ - } - tagStack.pop(); - } - /** - * @see ContentHandler#endPrefixMapping(java.lang.String) - */ - public void endPrefixMapping(String arg0) throws SAXException { - } - /** - * @see ContentHandler#ignorableWhitespace(char[], int, int) - */ - public void ignorableWhitespace(char[] arg0, int arg1, int arg2) - throws SAXException { - } - /** - * @see ContentHandler#processingInstruction(java.lang.String, java.lang.String) - */ - public void processingInstruction(String arg0, String arg1) - throws SAXException { - } - /** - * @see ContentHandler#setDocumentLocator(org.xml.sax.Locator) - */ - public void setDocumentLocator(Locator arg0) { - } - /** - * @see ContentHandler#skippedEntity(java.lang.String) - */ - public void skippedEntity(String e) throws SAXException { - } - /** - * @see ContentHandler#startDocument() - */ - public void startDocument() throws SAXException { - } - /** - * @see ContentHandler#startElement(java.lang.String, java.lang.String, java.lang.String, org.xml.sax.Attributes) - */ - public void startElement( - String namespaceURI, - String localName, - String qName, - Attributes atts) - throws SAXException { - if (localName.equals("project-description") && !inProjectDescription) { //$NON-NLS-1$ - inProjectDescription = true; - } else if (localName.equals("comment") && inProjectDescription && !inComment) { //$NON-NLS-1$ - inComment = true; - } else if (localName.equals("builder") && inProjectDescription && !inBuilder) { //$NON-NLS-1$ - String builderName = atts.getValue("name"); //$NON-NLS-1$ - if (builderName != null) { - inBuilder = true; - currentBuilder = desc.newCommand(); - currentBuilder.setBuilderName(builderName); - args = new HashMap(11); - } - } else if (localName.equals("arg") && inProjectDescription && inBuilder) { //$NON-NLS-1$ - String argName = atts.getValue("name"); //$NON-NLS-1$ - String argValue = atts.getValue("value"); //$NON-NLS-1$ - if (argName != null && argValue != null) - args.put(argName, argValue); - } else if (localName.equals("nature") && inProjectDescription && !inBuilder) { //$NON-NLS-1$ - String natureId = atts.getValue("id"); //$NON-NLS-1$ - if (natureId != null) - natures.add(natureId); - } else if ( - localName.equals("reference") && inProjectDescription && !inBuilder) { //$NON-NLS-1$ - String projectName = atts.getValue("project-name"); //$NON-NLS-1$ - if (projectName != null) - references.add( - ResourcesPlugin.getWorkspace().getRoot().getProject(projectName)); - } - // empty buffer - buffer = new StringBuffer(); - tagStack.push(localName); - } - /** - * @see ContentHandler#startPrefixMapping(java.lang.String, java.lang.String) - */ - public void startPrefixMapping(String arg0, String arg1) throws SAXException { - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionManager.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionManager.java deleted file mode 100644 index a2cc5550a..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionManager.java +++ /dev/null @@ -1,274 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.DataInputStream; -import java.io.IOException; -import java.io.InputStream; - -import org.apache.xerces.parsers.SAXParser; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IMarker; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IProjectDescription; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceChangeEvent; -import org.eclipse.core.resources.IResourceChangeListener; -import org.eclipse.core.resources.IResourceDelta; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IPath; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.core.RepositoryProvider; -import org.eclipse.team.core.TeamException; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSTeamProvider; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.xml.sax.InputSource; -import org.xml.sax.SAXException; - -/** - * This class handles the updating of the .vcm_meta file in projects managed by the CVSTeamProvider. - * - * It does so by listening to deltas on the project description and the .vcm_meta file itself. - * - */ -public class ProjectDescriptionManager implements IResourceChangeListener { - - public final static IPath PROJECT_DESCRIPTION_PATH = new Path(".vcm_meta"); //$NON-NLS-1$ - public final static IPath CORE_PROJECT_DESCRIPTION_PATH = new Path(".project"); //$NON-NLS-1$ - public final static boolean UPDATE_PROJECT_DESCRIPTION_ON_LOAD = true; - - public static final String VCMMETA_MARKER = "org.eclipse.team.cvs.core.vcmmeta"; //$NON-NLS-1$ - - /* - * Read the project meta file into the provider description - */ - public static void readProjectDescription(IProjectDescription desc, InputStream stream) throws IOException, CVSException { - SAXParser parser = new SAXParser(); - parser.setContentHandler(new ProjectDescriptionContentHandler(desc)); - try { - parser.parse(new InputSource(stream)); - } catch (SAXException ex) { - throw new CVSException(IStatus.ERROR, IStatus.ERROR, Policy.bind("ProjectDescriptionManager.unableToReadDescription"), ex); //$NON-NLS-1$ - } - } - - public static void writeProjectDescription(IProject project, IProgressMonitor progress) throws CVSException { - - // generate the new contents of the project meta file into a string - ByteArrayOutputStream byteOutputStream = new ByteArrayOutputStream(); - String newContents = null; - try { - IProjectDescription desc = project.getDescription(); - ProjectDescriptionWriter.writeProjectDescription(desc, byteOutputStream); - byteOutputStream.close(); - newContents = byteOutputStream.toString("UTF8"); //$NON-NLS-1$ - } catch (IOException ex) { - throw CVSException.wrapException(project, Policy.bind("ProjectDescriptionManager.ioDescription"), ex); //$NON-NLS-1$ - } catch (CoreException ex) { - throw CVSException.wrapException(project, Policy.bind("ProjectDescriptionManager.coreDescription"), ex); //$NON-NLS-1$ - } - - IFile descResource = project.getFile(PROJECT_DESCRIPTION_PATH); - if (descResource.exists()) { - // check if the existing contents are the same before rewriting - String oldContents = null; - try { - StringBuffer stringBuffer = new StringBuffer(); - InputStream is = ((IFile) descResource).getContents(); - byte[] buf = new byte[512]; - int result = is.read(buf); - while (result != -1) { - stringBuffer.append(new String(buf, 0, result, "UTF8")); //$NON-NLS-1$ - result = is.read(buf); - } - oldContents = stringBuffer.toString(); - is.close(); - } catch (IOException ex) { - throw CVSException.wrapException(project, Policy.bind("ProjectDescriptionManager.ioDescription"), ex); //$NON-NLS-1$ - } catch (CoreException ex) { - throw CVSException.wrapException(project, Policy.bind("ProjectDescriptionManager.coreDescription"), ex); //$NON-NLS-1$ - } - - if (oldContents.equals(newContents)) { - // the contents of the new file would be the same as the old - return; - } - try { - descResource.setContents( - new ByteArrayInputStream(byteOutputStream.toByteArray()), - false, - false, - progress); - } catch (CoreException ex) { - throw CVSException.wrapException(project, Policy.bind("ProjectDescriptionManager.coreDescription"), ex); //$NON-NLS-1$ - } - } else { - try { - descResource.create( - new ByteArrayInputStream(byteOutputStream.toByteArray()), - false, - progress); - } catch (CoreException ex) { - throw CVSException.wrapException(descResource, Policy.bind("ProjectDescriptionManager.coreDescription"), ex); //$NON-NLS-1$ - } - - } - } - - /* - * To be called whenever the project description file is believed to have changed by - * a load/loadIfIncoming operation. - */ - public static void updateProjectIfNecessary(IProject project, IProgressMonitor progress) throws CoreException, CVSException { - - IFile descResource = project.getFile(PROJECT_DESCRIPTION_PATH); - if (descResource.exists() && UPDATE_PROJECT_DESCRIPTION_ON_LOAD) { - - // If a managed .project files exists, don't read the .vcm_meta - ICVSFile coreDescResource = CVSWorkspaceRoot.getCVSFileFor(project.getFile(CORE_PROJECT_DESCRIPTION_PATH)); - if (coreDescResource.exists() && coreDescResource.isManaged()) { - createVCMMetaMarker(descResource); - Util.logError(Policy.bind("ProjectDescriptionManager.vcmmetaIgnored", project.getName()), null); //$NON-NLS-1$ - return; - } else { - ICVSFolder folder = CVSWorkspaceRoot.getCVSFolderFor(project); - if (! folder.isCVSFolder()) { - createVCMMetaMarker(descResource); - Util.logError(Policy.bind("ProjectDescriptionManager.vcmmetaIgnored", project.getName()), null); //$NON-NLS-1$ - return; - } - } - - // update project description file (assuming it has changed) - IProjectDescription desc = project.getDescription(); - DataInputStream is = null; - try { - is = new DataInputStream(((IFile) descResource).getContents()); - try { - readProjectDescription(desc, is); - } finally { - is.close(); - } - try { - project.setDescription(desc, IResource.FORCE | IResource.KEEP_HISTORY, progress); - } catch (CoreException ex) { - // Failing to set the description is probably due to a missing nature - // Other natures are still set - Util.logError(Policy.bind("ProjectDescriptionManager.unableToSetDescription"), ex); //$NON-NLS-1$ - } - - // Make sure we are still marked as a CVS project - if(RepositoryProvider.getProvider(project, CVSProviderPlugin.getTypeId()) == null) - RepositoryProvider.map(project, CVSProviderPlugin.getTypeId()); - - // Mark the .vcm_meta file with a problem marker - if (project.getFile(CORE_PROJECT_DESCRIPTION_PATH).exists()) { - createVCMMetaMarker(descResource); - } - } catch(TeamException ex) { - Util.logError(Policy.bind("ProjectDescriptionManager.unableToReadDescription"), ex); //$NON-NLS-1$ - // something went wrong, delete the project description file - descResource.delete(true, progress); - } catch (IOException ex) { - Util.logError(Policy.bind("ProjectDescriptionManager.unableToReadDescription"), ex); //$NON-NLS-1$ - // something went wrong, delete the project description file - descResource.delete(true, progress); - } - } - } - - /* - * Write out the project description file. - * - * For now just do it. It would be nice to detect the proper conditions - * - */ - public static void writeProjectDescriptionIfNecessary(CVSTeamProvider provider, IResource resource, IProgressMonitor monitor) throws CVSException { - if (resource.getType() == IResource.PROJECT || isProjectDescription(resource)) { - IProject project = resource.getProject(); - if (project.getFile(PROJECT_DESCRIPTION_PATH).exists() /* || ! project.getFile(CORE_PROJECT_DESCRIPTION_PATH).exists() */) { - writeProjectDescription(project, monitor); - } - } - } - - public static boolean isProjectDescription(IResource resource) { - return resource.getProjectRelativePath().equals(PROJECT_DESCRIPTION_PATH); - } - - public void resourceChanged(IResourceChangeEvent event) { - try { - IResourceDelta root = event.getDelta(); - IResourceDelta[] projectDeltas = root.getAffectedChildren(IResourceDelta.CHANGED | IResourceDelta.ADDED); - for (int i = 0; i < projectDeltas.length; i++) { - IResourceDelta delta = projectDeltas[i]; - IResource resource = delta.getResource(); - if (resource.getType() == IResource.PROJECT) { - IProject project = (IProject)resource; - RepositoryProvider provider = RepositoryProvider.getProvider(project, CVSProviderPlugin.getTypeId()); - if (provider == null) continue; - // First, check if the .vcm_meta file for the project is in the delta. - IResourceDelta[] children = delta.getAffectedChildren(IResourceDelta.ADDED); - boolean inSync = false; - for (int j = 0; j < children.length; j++) { - IResourceDelta childDelta = children[j]; - IResource childResource = childDelta.getResource(); - if (isProjectDescription(childResource)) - switch (childDelta.getKind()) { - case IResourceDelta.REMOVED: - writeProjectDescriptionIfNecessary((CVSTeamProvider)provider, project, Policy.monitorFor(null)); - inSync = true; - break; - case IResourceDelta.CHANGED: - case IResourceDelta.ADDED: - updateProjectIfNecessary(project, Policy.monitorFor(null)); - inSync = true; - break; - } - } - // Check if we didn't do anything above and the project description changed. - if (! inSync && (delta.getFlags() & IResourceDelta.DESCRIPTION) != 0) { - writeProjectDescriptionIfNecessary((CVSTeamProvider)provider, project, Policy.monitorFor(null)); - } - } - } - } catch (CVSException ex) { - Util.logError(Policy.bind("ProjectDescriptionManager.cannotUpdateDesc"), ex); //$NON-NLS-1$ - } catch (CoreException ex) { - Util.logError(Policy.bind("ProjectDescriptionManager.cannotUpdateDesc"), ex); //$NON-NLS-1$ - } - } - - protected static IMarker createVCMMetaMarker(IResource resource) { - try { - IMarker[] markers = resource.findMarkers(VCMMETA_MARKER, false, IResource.DEPTH_ZERO); - if (markers.length == 1) { - return markers[0]; - } - IMarker marker = resource.createMarker(VCMMETA_MARKER); - marker.setAttribute(IMarker.MESSAGE, Policy.bind("ProjectDescriptionManager.vcmmetaMarker" , resource.getName(), resource.getProject().getName())); //$NON-NLS-1$ - return marker; - } catch (CoreException e) { - Util.logError(Policy.bind("ProjectDescriptionManager.markerError"), e); //$NON-NLS-1$ - } - return null; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionWriter.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionWriter.java deleted file mode 100644 index d49624873..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ProjectDescriptionWriter.java +++ /dev/null @@ -1,110 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - -import java.util.*; -import org.eclipse.core.resources.*; -import org.eclipse.core.resources.IProjectDescription; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; - -import java.io.*; - -// NIK: Maybe we should make the Strings constants ? - -public class ProjectDescriptionWriter { - private static void appendEscapedChar(StringBuffer buffer, char c) { - String replacement = getReplacement(c); - if (replacement != null) { - buffer.append('&'); - buffer.append(replacement); - buffer.append(';'); - } else { - if ((c >= ' ' && c <= 0x7E) || c == '\n' || c == '\r' || c == '\t') { - buffer.append(c); - } else { - buffer.append("&#"); //$NON-NLS-1$ - buffer.append(Integer.toString(c)); - buffer.append(';'); - } - } - } - public static String getEscaped(String s) { - StringBuffer result = new StringBuffer(s.length() + 10); - for (int i = 0; i < s.length(); ++i) - appendEscapedChar(result, s.charAt(i)); - return result.toString(); - } - private static String getReplacement(char c) { - // Encode special XML characters into the equivalent character references. - // These five are defined by default for all XML documents. - switch (c) { - case '<' : - return "lt"; //$NON-NLS-1$ - case '>' : - return "gt"; //$NON-NLS-1$ - case '"' : - return "quot"; //$NON-NLS-1$ - case '\'' : - return "apos"; //$NON-NLS-1$ - case '&' : - return "amp"; //$NON-NLS-1$ - } - return null; - } - public static void writeProjectDescription( - IProjectDescription desc, - OutputStream os) - throws IOException { - PrintWriter writer = new PrintWriter(new OutputStreamWriter(os, "UTF8")); //$NON-NLS-1$ - writer.println("<?xml version=\"1.0\" encoding=\"UTF-8\"?>"); //$NON-NLS-1$ - writer.println("<project-description>"); //$NON-NLS-1$ - - String comment = desc.getComment(); - if (comment != null) { - writer.print("\t<comment>"); //$NON-NLS-1$ - writer.print(getEscaped(desc.getComment())); - writer.println("</comment>"); //$NON-NLS-1$ - } - - String[] natures = desc.getNatureIds(); - for (int i = 0; i < natures.length; i++) { - if ( ! natures[i].equals(CVSProviderPlugin.getTypeId())) - writer.println("\t<nature id=\"" + getEscaped(natures[i]) + "\"/>"); //$NON-NLS-1$ //$NON-NLS-2$ - } - - IProject[] references = desc.getReferencedProjects(); - for (int i = 0; i < references.length; i++) { - writer.println( - "\t<reference project-name=\"" + getEscaped(references[i].getName()) + "\"/>"); //$NON-NLS-1$ //$NON-NLS-2$ - } - - ICommand[] commands = desc.getBuildSpec(); - for (int i = 0; i < commands.length; i++) { - writer.println( - "\t<builder name=\"" + getEscaped(commands[i].getBuilderName()) + "\">"); //$NON-NLS-1$ //$NON-NLS-2$ - Map args = commands[i].getArguments(); - for (Iterator it = args.keySet().iterator(); it.hasNext();) { - String argName = (String) it.next(); - String argValue = (String) args.get(argName); - writer.println( - "\t\t<arg name=\"" //$NON-NLS-1$ - + getEscaped(argName) - + "\" value=\"" //$NON-NLS-1$ - + getEscaped(argValue) - + "\"/>"); //$NON-NLS-1$ - } - writer.println("\t</builder>"); //$NON-NLS-1$ - } - - writer.println("</project-description>"); //$NON-NLS-1$ - writer.flush(); - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ReplaceWithBaseVisitor.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ReplaceWithBaseVisitor.java deleted file mode 100644 index df6114f0f..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/ReplaceWithBaseVisitor.java +++ /dev/null @@ -1,130 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.ICVSResourceVisitor; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.client.Command; -import org.eclipse.team.internal.ccvs.core.client.Session; -import org.eclipse.team.internal.ccvs.core.client.Update; -import org.eclipse.team.internal.ccvs.core.client.Command.LocalOption; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -public class ReplaceWithBaseVisitor implements ICVSResourceVisitor { - - private IProgressMonitor monitor; - private int depth; - private Session session; - - /** - * @see ICVSResourceVisitor#visitFile(ICVSFile) - */ - public void visitFile(final ICVSFile file) throws CVSException { - byte[] syncBytes = file.getSyncBytes(); - if (syncBytes == null) { - // Delete unmanaged files if the user wants them deleted - if (CVSProviderPlugin.getPlugin().isReplaceUnmanaged()) { - file.delete(); - } - } else if (ResourceSyncInfo.isAddition(syncBytes)) { - file.delete(); - file.unmanage(null); - } else { - byte[] tagBytes = ResourceSyncInfo.getTagBytes(syncBytes); - boolean isModified = file.isModified(null); - if (ResourceSyncInfo.isDeletion(syncBytes)) { - // If deleted, null the sync info so the file will be refetched - syncBytes = ResourceSyncInfo.convertFromDeletion(syncBytes); - file.setSyncBytes(syncBytes, ICVSFile.UNKNOWN); - isModified = true; - } - // Fetch the file from the server - if (isModified) { - ICVSFolder parent = file.getParent(); - FolderSyncInfo folderInfo = parent.getFolderSyncInfo(); - // Use the session opened in tghe replaceWithBase method to make the connection. - Command.UPDATE.execute(this.session, Command.NO_GLOBAL_OPTIONS, - new LocalOption[] {Update.makeTagOption(CVSTag.BASE), Update.IGNORE_LOCAL_CHANGES}, - new ICVSResource[] { file }, null, Policy.subMonitorFor(monitor, 1)); - - // Set the tag to be the original tag - syncBytes = file.getSyncBytes(); - syncBytes = ResourceSyncInfo.setTag(syncBytes, tagBytes); - file.setSyncBytes(syncBytes, ICVSFile.UNKNOWN); - } - } - monitor.worked(1); - } - - /** - * @see ICVSResourceVisitor#visitFolder(ICVSFolder) - */ - public void visitFolder(ICVSFolder folder) throws CVSException { - // Visit the children of the folder as appropriate - if (depth == IResource.DEPTH_INFINITE) { - folder.acceptChildren(this); - } else if (depth == IResource.DEPTH_ONE) { - ICVSResource[] files = folder.members(ICVSFolder.FILE_MEMBERS); - for (int i = 0; i < files.length; i++) { - files[i].accept(this); - } - } - // Also delete ignored child files that start with .# - ICVSResource[] ignoredFiles = folder.members(ICVSFolder.FILE_MEMBERS | ICVSFolder.IGNORED_MEMBERS); - for (int i = 0; i < ignoredFiles.length; i++) { - ICVSResource cvsResource = ignoredFiles[i]; - if (cvsResource.getName().startsWith(".#")) { //$NON-NLS-1$ - cvsResource.delete(); - } - } - monitor.worked(1); - } - - /* - * This method will replace any changed resources in the local workspace with the - * base resource. Although CVS allows this operation using "cvs update -r BASE" the - * results in the workspace are "sticky". This operation does not leave the local workspace "sticky". - * - * NOTE: This operation issues multiple commands over a single connection. It may fail - * with some servers that are configured to run scripts during an update (see bug 40145). - */ - public void replaceWithBase(IProject project, final IResource[] resources, int depth, IProgressMonitor pm) throws CVSException { - this.depth = depth; - final ICVSFolder root = CVSWorkspaceRoot.getCVSFolderFor(project); - FolderSyncInfo folderInfo = root.getFolderSyncInfo(); - IProgressMonitor monitor = Policy.monitorFor(pm); - monitor.beginTask(null, 100); - this.session = new Session(CVSProviderPlugin.getPlugin().getRepository(folderInfo.getRoot()), root, true /* creat e backups */); - this.session.open(Policy.subMonitorFor(monitor, 10)); - try { - this.monitor = Policy.infiniteSubMonitorFor(monitor, 90); - this.monitor.beginTask(null, 512); - for (int i = 0; i < resources.length; i++) { - this.monitor.subTask(Policy.bind("ReplaceWithBaseVisitor.replacing", resources[i].getFullPath().toString())); //$NON-NLS-1$ - CVSWorkspaceRoot.getCVSResourceFor(resources[i]).accept(this); - } - } finally { - this.session.close(); - monitor.done(); - } - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/StringMatcher.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/StringMatcher.java deleted file mode 100644 index e9e151d36..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/StringMatcher.java +++ /dev/null @@ -1,398 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import java.util.*; - -/** - * A string pattern matcher, suppporting * and ? wildcards. - * Note: code copied from org.eclipse.jdt.internal.core.util.StringMatcher on April 3, 2001 - * (version 0.1 - 010901H18 [rename jbl]). - */ -public class StringMatcher { - protected String fPattern; - protected int fLength; // pattern length - protected boolean fIgnoreWildCards; - protected boolean fIgnoreCase; - protected boolean fHasLeadingStar; - protected boolean fHasTrailingStar; - protected String fSegments[]; //the given pattern is split into * separated segments - - /* boundary value beyond which we don't need to search in the text */ - protected int fBound = 0; - - - protected static final char fSingleWildCard = '\u0000'; - - public static class Position { - int start; //inclusive - int end; //exclusive - public Position(int start, int end) { - this.start = start; - this.end = end; - } - public int getStart() { - return start; - } - public int getEnd() { - return end; - } - } - /** - * Find the first occurrence of the pattern between <code>start</code)(inclusive) - * and <code>end</code>(exclusive). - * @param <code>text</code>, the String object to search in - * @param <code>start</code>, the starting index of the search range, inclusive - * @param <code>end</code>, the ending index of the search range, exclusive - * @return an <code>StringMatcher.Position</code> object that keeps the starting - * (inclusive) and ending positions (exclusive) of the first occurrence of the - * pattern in the specified range of the text; return null if not found or subtext - * is empty (start==end). A pair of zeros is returned if pattern is empty string - * Note that for pattern like "*abc*" with leading and trailing stars, position of "abc" - * is returned. For a pattern like"*??*" in text "abcdf", (1,3) is returned - */ - - public StringMatcher.Position find(String text, int start, int end) { - if (fPattern == null|| text == null) - throw new IllegalArgumentException(); - - int tlen = text.length(); - if (start < 0) - start = 0; - if (end > tlen) - end = tlen; - if (end < 0 ||start >= end ) - return null; - if (fLength == 0) - return new Position(start, start); - if (fIgnoreWildCards) { - int x = posIn(text, start, end); - if (x < 0) - return null; - return new Position(x, x+fLength); - } - - int segCount = fSegments.length; - if (segCount == 0)//pattern contains only '*'(s) - return new Position (start, end); - - int curPos = start; - int matchStart = -1; - int i; - for (i = 0; i < segCount && curPos < end; ++i) { - String current = fSegments[i]; - int nextMatch = regExpPosIn(text, curPos, end, current); - if (nextMatch < 0 ) - return null; - if(i == 0) - matchStart = nextMatch; - curPos = nextMatch + current.length(); - } - if (i < segCount) - return null; - return new Position(matchStart, curPos); - } - /** - * StringMatcher constructor takes in a String object that is a simple - * pattern which may contain * for 0 and many characters and - * ? for exactly one character. - * - * Literal '*' and '?' characters must be escaped in the pattern - * e.g., "\*" means literal "*", etc. - * - * Escaping any other character (including the escape character itself), - * just results in that character in the pattern. - * e.g., "\a" means "a" and "\\" means "\" - * - * If invoking the StringMatcher with string literals in Java, don't forget - * escape characters are represented by "\\". - * - * @param aPattern the pattern to match text with - * @param ignoreCase if true, case is ignored - * @param ignoreWildCards if true, wild cards and their escape sequences are ignored - * (everything is taken literally). - */ - public StringMatcher(String aPattern, boolean ignoreCase, boolean ignoreWildCards) { - fIgnoreCase = ignoreCase; - fIgnoreWildCards = ignoreWildCards; - fLength = aPattern.length(); - - /* convert case */ - if (fIgnoreCase) { - fPattern = aPattern.toUpperCase(); - } else { - fPattern = aPattern; - } - - if (fIgnoreWildCards) { - parseNoWildCards(); - } else { - parseWildCards(); - } - } - /** - * Given the starting (inclusive) and the ending (exclusive) poisitions in the - * <code>text</code>, determine if the given substring matches with aPattern - * @return true if the specified portion of the text matches the pattern - * @param String <code>text</code>, a String object that contains the substring to match - * @param int <code>start<code> marks the starting position (inclusive) of the substring - * @param int <code>end<code> marks the ending index (exclusive) of the substring - */ - public boolean match(String text, int start, int end) { - if (null == text) - throw new IllegalArgumentException(); - - if (start > end) - return false; - - if (fIgnoreWildCards) - return (end - start == fLength) && fPattern.regionMatches(fIgnoreCase, 0, text, start, fLength); - int segCount= fSegments.length; - if (segCount == 0 && (fHasLeadingStar || fHasTrailingStar)) // pattern contains only '*'(s) - return true; - if (start == end) - return fLength == 0; - if (fLength == 0) - return start == end; - - int tlen= text.length(); - if (start < 0) - start= 0; - if (end > tlen) - end= tlen; - - int tCurPos= start; - int bound= end - fBound; - if ( bound < 0) - return false; - int i=0; - String current= fSegments[i]; - int segLength= current.length(); - - /* process first segment */ - if (!fHasLeadingStar){ - if(!regExpRegionMatches(text, start, current, 0, segLength)) { - return false; - } else { - ++i; - tCurPos= tCurPos + segLength; - } - } - if ((fSegments.length == 1) && (!fHasLeadingStar) && (!fHasTrailingStar)) { - // only one segment to match, no wildcards specified - return tCurPos == end; - } - /* process middle segments */ - while (i < segCount) { - current= fSegments[i]; - int currentMatch; - int k= current.indexOf(fSingleWildCard); - if (k < 0) { - currentMatch= textPosIn(text, tCurPos, end, current); - if (currentMatch < 0) - return false; - } else { - currentMatch= regExpPosIn(text, tCurPos, end, current); - if (currentMatch < 0) - return false; - } - tCurPos= currentMatch + current.length(); - i++; - } - - /* process final segment */ - if (!fHasTrailingStar && tCurPos != end) { - int clen= current.length(); - return regExpRegionMatches(text, end - clen, current, 0, clen); - } - return i == segCount ; - } - /** - * match the given <code>text</code> with the pattern - * @return true if matched eitherwise false - * @param <code>text</code>, a String object - */ - public boolean match(String text) { - return match(text, 0, text.length()); - } - /** - * This method parses the given pattern into segments separated by wildcard '*' characters. - * Since wildcards are not being used in this case, the pattern consists of a single segment. - */ - private void parseNoWildCards() { - fSegments = new String[1]; - fSegments[0] = fPattern; - fBound = fLength; - } - /** - * This method parses the given pattern into segments separated by wildcard '*' characters. - * @param p, a String object that is a simple regular expression with * and/or ? - */ - private void parseWildCards() { - if(fPattern.startsWith("*"))//$NON-NLS-1$ - fHasLeadingStar = true; - if(fPattern.endsWith("*")) {//$NON-NLS-1$ - /* make sure it's not an escaped wildcard */ - if (fLength > 1 && fPattern.charAt(fLength - 2) != '\\') { - fHasTrailingStar = true; - } - } - - Vector temp = new Vector(); - - int pos = 0; - StringBuffer buf = new StringBuffer(); - while (pos < fLength) { - char c = fPattern.charAt(pos++); - switch (c) { - case '\\': - if (pos >= fLength) { - buf.append(c); - } else { - char next = fPattern.charAt(pos++); - /* if it's an escape sequence */ - if (next == '*' || next == '?' || next == '\\') { - buf.append(next); - } else { - /* not an escape sequence, just insert literally */ - buf.append(c); - buf.append(next); - } - } - break; - case '*': - if (buf.length() > 0) { - /* new segment */ - temp.addElement(buf.toString()); - fBound += buf.length(); - buf.setLength(0); - } - break; - case '?': - /* append special character representing single match wildcard */ - buf.append(fSingleWildCard); - break; - default: - buf.append(c); - } - } - - /* add last buffer to segment list */ - if (buf.length() > 0) { - temp.addElement(buf.toString()); - fBound += buf.length(); - } - - fSegments = new String[temp.size()]; - temp.copyInto(fSegments); - } - /** - * @param <code>text</code>, a string which contains no wildcard - * @param <code>start</code>, the starting index in the text for search, inclusive - * @param <code>end</code>, the stopping point of search, exclusive - * @return the starting index in the text of the pattern , or -1 if not found - */ - protected int posIn(String text, int start, int end) {//no wild card in pattern - int max = end - fLength; - - if (!fIgnoreCase) { - int i = text.indexOf(fPattern, start); - if (i == -1 || i > max) - return -1; - return i; - } - - for (int i = start; i <= max; ++i) { - if (text.regionMatches(true, i, fPattern, 0, fLength)) - return i; - } - - return -1; - } - /** - * @param <code>text</code>, a simple regular expression that may only contain '?'(s) - * @param <code>start</code>, the starting index in the text for search, inclusive - * @param <code>end</code>, the stopping point of search, exclusive - * @param <code>p</code>, a simple regular expression that may contains '?' - * @param <code>caseIgnored</code>, wether the pattern is not casesensitive - * @return the starting index in the text of the pattern , or -1 if not found - */ - protected int regExpPosIn(String text, int start, int end, String p) { - int plen = p.length(); - - int max = end - plen; - for (int i = start; i <= max; ++i) { - if (regExpRegionMatches(text, i, p, 0, plen)) - return i; - } - return -1; - } - /** - * - * @return boolean - * @param <code>text</code>, a String to match - * @param <code>start</code>, int that indicates the starting index of match, inclusive - * @param <code>end</code> int that indicates the ending index of match, exclusive - * @param <code>p</code>, String, String, a simple regular expression that may contain '?' - * @param <code>ignoreCase</code>, boolean indicating wether code>p</code> is case sensitive - */ - protected boolean regExpRegionMatches(String text, int tStart, String p, int pStart, int plen) { - while (plen-- > 0) { - char tchar = text.charAt(tStart++); - char pchar = p.charAt(pStart++); - - /* process wild cards */ - if (!fIgnoreWildCards) { - /* skip single wild cards */ - if (pchar == fSingleWildCard) { - continue; - } - } - if (pchar == tchar) - continue; - if (fIgnoreCase) { - char tc = Character.toUpperCase(tchar); - if (tc == pchar) - continue; - } - return false; - } - return true; - } - /** - * @param <code>text</code>, the string to match - * @param <code>start</code>, the starting index in the text for search, inclusive - * @param <code>end</code>, the stopping point of search, exclusive - * @param code>p</code>, a string that has no wildcard - * @param <code>ignoreCase</code>, boolean indicating wether code>p</code> is case sensitive - * @return the starting index in the text of the pattern , or -1 if not found - */ - protected int textPosIn(String text, int start, int end, String p) { - - int plen = p.length(); - int max = end - plen; - - if (!fIgnoreCase) { - int i = text.indexOf(p, start); - if (i == -1 || i > max) - return -1; - return i; - } - - for (int i = start; i <= max; ++i) { - if (text.regionMatches(true, i, p, 0, plen)) - return i; - } - - return -1; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/SyncFileChangeListener.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/SyncFileChangeListener.java deleted file mode 100644 index c7e5cf610..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/SyncFileChangeListener.java +++ /dev/null @@ -1,285 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - -import java.util.HashSet; -import java.util.Set; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceChangeEvent; -import org.eclipse.core.resources.IResourceChangeListener; -import org.eclipse.core.resources.IResourceDelta; -import org.eclipse.core.resources.IResourceDeltaVisitor; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.Path; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.ICVSFile; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot; -import org.eclipse.team.internal.ccvs.core.resources.EclipseSynchronizer; - -/* - * Listens to CVS meta-file changes and notifies the EclipseSynchronizer of changes made to sync files - * by 3rd parties. - * - * If CVS meta-directories are created outside of the CVS plugin their team-private state will be set - * by this listener however this change won't be known to other plugins because it does not generate - * a delta. As a result views, such as the navigator, may show CVS team-private directories. There - * are some common scenarios where a user may (depending on the order of delta traversal) see - * this behavior: - * - * 1. A user has an existing CVS project outside of Eclipse. By creating the project in Eclipse to point - * to the existing location the project's contents will be brought into Eclipse and the CVS folders - * will be marlked as team-private but other delta listeners that have handled the event already won't receive - * notification that the resource is now team-private. As a result, the user may have to close views or - * restart the workbench to have the CVS folders filtered. - * - * 2. A user performs CVS command line operations outside of Eclipse that result in new CVS folders. - * From Eclipse the refresh local will bring in the new folders and they will be marked as team-private. - * But as in 1, they may not appear in the UI. - * - * See: http://dev.eclipse.org/bugs/show_bug.cgi?id=12386 - */ -public class SyncFileChangeListener implements IResourceChangeListener { - - // consider the following changes types and ignore the others (e.g. marker and description changes are ignored) - protected int INTERESTING_CHANGES = IResourceDelta.CONTENT | - IResourceDelta.MOVED_FROM | - IResourceDelta.MOVED_TO | - IResourceDelta.OPEN | - IResourceDelta.REPLACED | - IResourceDelta.TYPE; - - protected boolean isProjectOpening = false; - - /* - * When a resource changes this method will detect if the changed resources is a meta file that has changed - * by a 3rd party. For example, if the command line tool was run and then the user refreshed from local. To - * distinguish changes made by this class and thoses made by others a modification stamp is persisted with each - * metafile. - * - * @see IResourceChangeListener#resourceChanged(IResourceChangeEvent) - */ - public void resourceChanged(IResourceChangeEvent event) { - try { - final Set changedContainers = new HashSet(); - setProjectOpening(false); - - event.getDelta().accept(new IResourceDeltaVisitor() { - public boolean visit(IResourceDelta delta) throws CoreException { - IResource resource = delta.getResource(); - - if(resource.getType()==IResource.ROOT) { - // continue with the delta - return true; - } - - if (resource.getType() == IResource.PROJECT) { - // If the project is not accessible, don't process it - if (!resource.isAccessible()) return false; - setProjectOpening((delta.getFlags() & IResourceDelta.OPEN) != 0); - } - - String name = resource.getName(); - int kind = delta.getKind(); - - // if the file has changed but not in a way that we care - // then ignore the change (e.g. marker changes to files). - if(kind == IResourceDelta.CHANGED && - (delta.getFlags() & INTERESTING_CHANGES) == 0) { - return true; - } - - IResource[] toBeNotified = new IResource[0]; - - if(name.equals(SyncFileWriter.CVS_DIRNAME)) { - handleCVSDir((IContainer)resource, kind); - // if the project is opening there is no need to notify about chagned CVs/ meta files - // they will all be read from disk. - if(isProjectOpening()) return false; - } else { - // Inform the synchronizer about folder creations - if(isProjectOpening()) return true; - if (kind == IResourceDelta.ADDED) { - try { - EclipseSynchronizer.getInstance().created(resource); - } catch (CVSException e) { - throw new CoreException(e.getStatus()); - } - } - } - - if(isMetaFile(resource)) { - toBeNotified = handleChangedMetaFile(resource, kind); - } else if(name.equals(SyncFileWriter.IGNORE_FILE)) { - toBeNotified = handleChangedIgnoreFile(resource, kind); - } else if (isExternalDeletion(resource, kind)) { - toBeNotified = handleExternalDeletion(resource); - } - - if(toBeNotified.length>0 && isModifiedBy3rdParty(resource)) { - for (int i = 0; i < toBeNotified.length; i++) { - changedContainers.add(toBeNotified[i]); - } - if(Policy.DEBUG_METAFILE_CHANGES) { - System.out.println("[cvs] metafile changed by 3rd party: " + resource.getFullPath()); //$NON-NLS-1$ - } - return false; /*don't visit any children we have all the information we need*/ - } else { - return true; - } - } - }, IContainer.INCLUDE_TEAM_PRIVATE_MEMBERS); - - if(!changedContainers.isEmpty()) { - EclipseSynchronizer.getInstance().syncFilesChanged((IContainer[])changedContainers.toArray(new IContainer[changedContainers.size()])); - } - } catch(CoreException e) { - CVSProviderPlugin.log(e); - } - } - - /** - * @param resource - * @return - */ - protected IContainer[] handleExternalDeletion(IResource resource) { - IContainer changedContainer = resource.getParent(); - if(changedContainer.exists()) { - return new IContainer[] {changedContainer}; - } else { - return new IContainer[0]; - } - } - - /** - * Treat a resource as an external deletion if - * - it is a file - * - the delta says the file was removed - * - the file is not managed but its parent is a CVS folder - * - * There will be some false positives but the reaction to this situation - * is to purge the cahced CVS meta-information so nothing bad will happen - * for the false positives. - * - * @param resource - * @param kind - * @return - */ - protected boolean isExternalDeletion(IResource resource, int kind) { - if (kind != IResourceDelta.REMOVED) return false; - if (resource.getType() != IResource.FILE) return false; - ICVSFile file = CVSWorkspaceRoot.getCVSFileFor((IFile)resource); - try { - return (!file.isManaged() && file.getParent().isCVSFolder()); - } catch (CVSException e) { - CVSProviderPlugin.log(e); - return false; - } - } - - /* - * Consider non-existing resources as being recently deleted and thus modified, and resources - * with modification stamps that differ from when the CVS plugin last modified the meta-file. - */ - protected boolean isModifiedBy3rdParty(IResource resource) { - if(!resource.exists()) return true; - long modStamp = resource.getModificationStamp(); - Long whenWeWrote; - try { - whenWeWrote = (Long)resource.getSessionProperty(SyncFileWriter.MODSTAMP_KEY); - } catch(CoreException e) { - CVSProviderPlugin.log(e); - whenWeWrote = null; - } - return (whenWeWrote==null || whenWeWrote.longValue() != modStamp); - } - - /* - * If it's a new CVS directory with the canonical child metafiles then mark it as team-private. Otherwise - * if changed or deleted - */ - protected void handleCVSDir(IContainer cvsDir, int kind) { - if((kind & IResourceDelta.ALL_WITH_PHANTOMS)!=0) { - if(kind==IResourceDelta.ADDED) { - // should this dir be made team-private? If it contains CVS/Root and CVS/Repository then yes! - IFile rootFile = cvsDir.getFile(new Path(SyncFileWriter.ROOT)); - IFile repositoryFile = cvsDir.getFile(new Path(SyncFileWriter.REPOSITORY)); - if(rootFile.exists() && repositoryFile.exists() && !cvsDir.isTeamPrivateMember()) { - try { - cvsDir.setTeamPrivateMember(true); - if(Policy.DEBUG_METAFILE_CHANGES) { - System.out.println("[cvs] found a new CVS meta folder, marking as team-private: " + cvsDir.getFullPath()); //$NON-NLS-1$ - } - } catch(CoreException e) { - CVSProviderPlugin.log(CVSException.wrapException(cvsDir, Policy.bind("SyncFileChangeListener.errorSettingTeamPrivateFlag"), e)); //$NON-NLS-1$ - } - } - } - } - } - - /* - * It's a meta file if it's parent is a team-private CVS folder. - */ - protected boolean isMetaFile(IResource resource) { - IContainer parent = resource.getParent(); - return resource.getType() == IResource.FILE && - parent!=null && - parent.getName().equals(SyncFileWriter.CVS_DIRNAME) && - (parent.isTeamPrivateMember() || !parent.exists()); - } - - /* - * This is a meta file (e.g. folder/CVS/Entries), notify that 'folder' and it's immediate children - * may have their CVS sync state changed. If the 'folder' is deleted than no notification is - * required. - */ - protected IContainer[] handleChangedMetaFile(IResource resource, int kind) { - IContainer changedContainer = resource.getParent().getParent(); - if(changedContainer.exists()) { - return new IContainer[] {changedContainer}; - } else { - return new IContainer[0]; - } - } - - /* - * This is an ignore file (e.g. folder/.cvsignore), notify that 'folder' and it's immediate children - * may have their CVS sync state changed. - */ - protected IContainer[] handleChangedIgnoreFile(IResource resource, int kind) { - IContainer changedContainer = resource.getParent(); - if(changedContainer.exists()) { - return new IContainer[] {changedContainer}; - } else { - return new IContainer[0]; - } - } - - /** - * @return boolean - */ - public boolean isProjectOpening() { - return isProjectOpening; - } - - /** - * Sets the isProjectOpening. - * @param isProjectOpening The isProjectOpening to set - */ - public void setProjectOpening(boolean isProjectOpening) { - this.isProjectOpening = isProjectOpening; - } -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/SyncFileWriter.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/SyncFileWriter.java deleted file mode 100644 index b305a97a0..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/SyncFileWriter.java +++ /dev/null @@ -1,612 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import java.io.BufferedReader; -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.io.OutputStream; -import java.util.ArrayList; -import java.util.Iterator; -import java.util.List; -import java.util.Map; -import java.util.TreeMap; - -import org.eclipse.core.resources.IContainer; -import org.eclipse.core.resources.IFile; -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.resources.IResourceStatus; -import org.eclipse.core.resources.IWorkspaceRunnable; -import org.eclipse.core.resources.ResourcesPlugin; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.Path; -import org.eclipse.core.runtime.QualifiedName; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.Policy; -import org.eclipse.team.internal.ccvs.core.resources.CVSEntryLineTag; -import org.eclipse.team.internal.ccvs.core.syncinfo.BaserevInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.NotifyInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/* - * This is a helper class that knows the format of the CVS metafiles. It - * provides a bridge between the CVS metafile formats and location to the - * Eclipse CVS client ResourceSyncInfo and FolderSyncInfo types. - */ -public class SyncFileWriter { - - // the famous CVS meta directory name - public static final String CVS_DIRNAME = "CVS"; //$NON-NLS-1$ - - // CVS meta files located in the CVS subdirectory - public static final String REPOSITORY = "Repository"; //$NON-NLS-1$ - public static final String ROOT = "Root"; //$NON-NLS-1$ - public static final String STATIC = "Entries.Static"; //$NON-NLS-1$ - public static final String TAG = "Tag"; //$NON-NLS-1$ - public static final String ENTRIES = "Entries"; //$NON-NLS-1$ - //private static final String PERMISSIONS = "Permissions"; //$NON-NLS-1$ - public static final String ENTRIES_LOG="Entries.Log"; //$NON-NLS-1$ - public static final String NOTIFY = "Notify"; //$NON-NLS-1$ - public static final String BASE_DIRNAME = "Base"; //$NON-NLS-1$ - public static final String BASEREV = "Baserev"; //$NON-NLS-1$ - - // the local workspace file that contains pattern for ignored resources - public static final String IGNORE_FILE = ".cvsignore"; //$NON-NLS-1$ - - // Some older CVS clients may of added a line to the entries file consisting - // of only a 'D'. It is safe to ingnore these entries. - private static final String FOLDER_TAG="D"; //$NON-NLS-1$ - - // Command characters found in the Entries.log file - private static final String ADD_TAG="A "; //$NON-NLS-1$ - private static final String REMOVE_TAG="R "; //$NON-NLS-1$ - - // key for saving the mod stamp for each writen meta file - public static final QualifiedName MODSTAMP_KEY = new QualifiedName("org.eclipse.team.cvs.core", "meta-file-modtime"); //$NON-NLS-1$ //$NON-NLS-2$ - - /** - * Reads the CVS/Entries, CVS/Entries.log and CVS/Permissions files from the - * specified folder and returns ResourceSyncInfo instances for the data stored therein. - * If the folder does not have a CVS subdirectory then <code>null</code> is returned. - */ - public static byte[][] readAllResourceSync(IContainer parent) throws CVSException { - IFolder cvsSubDir = getCVSSubdirectory(parent); - if (! cvsSubDir.exists()) return null; - - // process Entries file contents - String[] entries = readLines(cvsSubDir.getFile(ENTRIES)); - if (entries == null) return null; - Map infos = new TreeMap(); - for (int i = 0; i < entries.length; i++) { - String line = entries[i]; - if(!FOLDER_TAG.equals(line) && !"".equals(line)) { //$NON-NLS-1$ - ResourceSyncInfo info = new ResourceSyncInfo(line, null, null); - infos.put(info.getName(), info); - } - } - - // process Entries.log file contents - String[] entriesLog = readLines(cvsSubDir.getFile(ENTRIES_LOG)); - if (entriesLog != null) { - for (int i = 0; i < entriesLog.length; i++) { - String line = entriesLog[i]; - if (line.startsWith(ADD_TAG)) { - line = line.substring(ADD_TAG.length()); - ResourceSyncInfo info = new ResourceSyncInfo(line, null, null); - infos.put(info.getName(), info); - } else if (line.startsWith(REMOVE_TAG)) { - line = line.substring(REMOVE_TAG.length()); - ResourceSyncInfo info = new ResourceSyncInfo(line, null, null); - infos.remove(info.getName()); - } - } - } - - //return (ResourceSyncInfo[])infos.values().toArray(new ResourceSyncInfo[infos.size()]); - byte[][] result = new byte[infos.size()][]; - int i = 0; - for (Iterator iter = infos.values().iterator(); iter.hasNext();) { - ResourceSyncInfo info = (ResourceSyncInfo) iter.next(); - result[i++] = info.getBytes(); - } - return result; - } - - public static void writeAllResourceSync(IContainer parent, byte[][] infos) throws CVSException { - try { - IFolder cvsSubDir = createCVSSubdirectory(parent); - - // format file contents - String[] entries = new String[infos.length]; - for (int i = 0; i < infos.length; i++) { - byte[] info = infos[i]; - entries[i] = new String(info); - } - - // write Entries - writeLines(cvsSubDir.getFile(ENTRIES), entries); - - // delete Entries.log - cvsSubDir.getFile(ENTRIES_LOG).delete(IResource.NONE, null); - } catch(CoreException e) { - throw CVSException.wrapException(e); - } - } - /** - * Reads the CVS/Root, CVS/Repository, CVS/Tag, and CVS/Entries.static files from - * the specified folder and returns a FolderSyncInfo instance for the data stored therein. - * If the folder does not have a CVS subdirectory then <code>null</code> is returned. - */ - public static FolderSyncInfo readFolderSync(IContainer folder) throws CVSException { - IFolder cvsSubDir = getCVSSubdirectory(folder); - if (! cvsSubDir.exists()) return null; - - // check to make sure the the cvs folder is hidden - if (!cvsSubDir.isTeamPrivateMember()) { - try { - cvsSubDir.setTeamPrivateMember(true); - } catch (CoreException e) { - CVSProviderPlugin.log(e); - } - } - - // read CVS/Root - String root = readFirstLine(cvsSubDir.getFile(ROOT)); - if (root == null) return null; - - // read CVS/Repository - String repository = readFirstLine(cvsSubDir.getFile(REPOSITORY)); - if (repository == null) return null; - - // read CVS/Tag - String tag = readFirstLine(cvsSubDir.getFile(TAG)); - CVSTag cvsTag = (tag != null) ? new CVSEntryLineTag(tag) : null; - - // read Entries.Static - String staticDir = readFirstLine(cvsSubDir.getFile(STATIC)); - boolean isStatic = (staticDir != null); - - // return folder sync - return new FolderSyncInfo(repository, root, cvsTag, isStatic); - } - - /** - * Writes the CVS/Root, CVS/Repository, CVS/Tag, and CVS/Entries.static files to the - * specified folder using the data contained in the specified FolderSyncInfo instance. - */ - public static void writeFolderSync(IContainer folder, FolderSyncInfo info) throws CVSException { - try { - IFolder cvsSubDir = createCVSSubdirectory(folder); - - // write CVS/Root - writeLines(cvsSubDir.getFile(ROOT), new String[] {info.getRoot()}); - - // write CVS/Repository - writeLines(cvsSubDir.getFile(REPOSITORY), new String[] {info.getRepository()}); - - // write CVS/Tag - IFile tagFile = cvsSubDir.getFile(TAG); - if (info.getTag() != null) { - writeLines(tagFile, new String[] {info.getTag().toEntryLineFormat(false)}); - } else { - if(tagFile.exists()) { - tagFile.delete(IResource.NONE, null); - } - } - - // write CVS/Entries.Static - IFile staticFile = cvsSubDir.getFile(STATIC); - if(info.getIsStatic()) { - // the existance of the file is all that matters - writeLines(staticFile, new String[] {""}); //$NON-NLS-1$ - } else { - if(staticFile.exists()) { - staticFile.delete(IResource.NONE, null); - } - } - } catch(CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * Returns all .cvsignore entries for the specified folder. - */ - public static String[] readCVSIgnoreEntries(IContainer folder) throws CVSException { - IFile ignoreFile = folder.getFile(new Path(IGNORE_FILE)); - if (ignoreFile != null) { - return readLines(ignoreFile); - } - return null; - } - - /** - * Writes all entries to the specified folder's .cvsignore file, overwriting any - * previous edition of the file. - */ - public static void writeCVSIgnoreEntries(IContainer folder, String[] patterns) throws CVSException { - IFile ignoreFile = folder.getFile(new Path(IGNORE_FILE)); - writeLines(ignoreFile, patterns); - } - - /** - * Delete folder sync is equilavent to removing the CVS subdir. - */ - public static void deleteFolderSync(IContainer folder) throws CVSException { - try { - getCVSSubdirectory(folder).delete(IResource.NONE, null); - } catch(CoreException e) { - throw CVSException.wrapException(e); - } - } - - /** - * Reads the CVS/Notify file from the specified folder and returns NotifyInfo instances - * for the data stored therein. If the folder does not have a CVS subdirectory then <code>null</code> is returned. - */ - public static NotifyInfo[] readAllNotifyInfo(IContainer parent) throws CVSException { - IFolder cvsSubDir = getCVSSubdirectory(parent); - if (! cvsSubDir.exists()) return null; - - // process Notify file contents - String[] entries = readLines(cvsSubDir.getFile(NOTIFY)); - if (entries == null) return null; - Map infos = new TreeMap(); - for (int i = 0; i < entries.length; i++) { - String line = entries[i]; - if(!"".equals(line)) { //$NON-NLS-1$ - NotifyInfo info = new NotifyInfo(parent, line); - infos.put(info.getName(), info); - } - } - - return (NotifyInfo[])infos.values().toArray(new NotifyInfo[infos.size()]); - } - - /** - * Writes the CVS/Notify file to the specified folder using the data contained in the - * specified NotifyInfo instances. A CVS subdirectory must already exist (an exception - * is thrown if it doesn't). - */ - public static void writeAllNotifyInfo(IContainer parent, NotifyInfo[] infos) throws CVSException { - // get the CVS directory - IFolder cvsSubDir = getCVSSubdirectory(parent); - // write lines will throw an exception if the CVS directoru does not exist - - if (infos.length == 0) { - // if there are no notify entries, delete the notify file - try { - IFile notifyFile = cvsSubDir.getFile(NOTIFY); - if(notifyFile.exists()) { - notifyFile.delete(IResource.NONE, null); - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } else { - // format file contents - String[] entries = new String[infos.length]; - for (int i = 0; i < infos.length; i++) { - NotifyInfo info = infos[i]; - entries[i] = info.getNotifyLine(); - } - - // write Notify entries - writeLines(cvsSubDir.getFile(NOTIFY), entries); - } - } - - /** - * Reads the CVS/Baserev file from the specified folder and returns - * BaserevInfo instances for the data stored therein. If the folder does not - * have a CVS subdirectory then <code>null</code> is returned. - */ - public static BaserevInfo[] readAllBaserevInfo(IContainer parent) throws CVSException { - IFolder cvsSubDir = getCVSSubdirectory(parent); - if (! cvsSubDir.exists()) return null; - - // process Notify file contents - String[] entries = readLines(cvsSubDir.getFile(BASEREV)); - if (entries == null) return null; - Map infos = new TreeMap(); - for (int i = 0; i < entries.length; i++) { - String line = entries[i]; - if(!"".equals(line)) { //$NON-NLS-1$ - BaserevInfo info = new BaserevInfo(line); - infos.put(info.getName(), info); - } - } - - return (BaserevInfo[])infos.values().toArray(new BaserevInfo[infos.size()]); - } - - /** - * Writes the CVS/Baserev file to the specified folder using the data - * contained in the specified BaserevInfo instances. A CVS subdirectory must - * already exist (an exception is thrown if it doesn't). - */ - public static void writeAllBaserevInfo(IContainer parent, BaserevInfo[] infos) throws CVSException { - // get the CVS directory - IFolder cvsSubDir = getCVSSubdirectory(parent); - // write lines will throw an exception if the CVS directory does not exist - - // format file contents - String[] entries = new String[infos.length]; - for (int i = 0; i < infos.length; i++) { - BaserevInfo info = infos[i]; - entries[i] = info.getEntryLine(); - } - - // write Notify entries - writeLines(cvsSubDir.getFile(BASEREV), entries); - } - - /** - * Returns the CVS subdirectory for this folder. - */ - private static IFolder getCVSSubdirectory(IContainer folder) throws CVSException { - return folder.getFolder(new Path(CVS_DIRNAME)); - } - - /** - * Creates and makes team-private and returns a CVS subdirectory in this folder. - */ - private static IFolder createCVSSubdirectory(IContainer folder) throws CVSException { - try { - final IFolder cvsSubDir = getCVSSubdirectory(folder); - if (! cvsSubDir.exists()) { - // important to have both the folder creation and setting of team-private in the - // same runnable so that the team-private flag is set before other delta listeners - // sees the CVS folder creation. - ResourcesPlugin.getWorkspace().run(new IWorkspaceRunnable() { - public void run(IProgressMonitor monitor) throws CoreException { - cvsSubDir.create(false /*don't force*/, true /*make local*/, null); - cvsSubDir.setTeamPrivateMember(true); - } - }, null); - } - return cvsSubDir; - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /* - * Reads the first line of the specified file. - * Returns null if the file does not exist, or the empty string if it is blank. - */ - private static String readFirstLine(IFile file) throws CVSException { - if (! file.exists()) return null; - try { - BufferedReader reader = new BufferedReader(new InputStreamReader(file.getContents())); - try { - String line = reader.readLine(); - if (line == null) return ""; //$NON-NLS-1$ - return line; - } finally { - reader.close(); - } - } catch (IOException e) { - throw CVSException.wrapException(e); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - /* - * Reads all lines of the specified file. - * Returns null if the file does not exist. - */ - private static String[] readLines(IFile file) throws CVSException { - try { - if(! file.exists()) return null; - BufferedReader reader = new BufferedReader(new InputStreamReader(file.getContents())); - List fileContentStore = new ArrayList(); - try { - String line; - while ((line = reader.readLine()) != null) { - fileContentStore.add(line); - } - return (String[]) fileContentStore.toArray(new String[fileContentStore.size()]); - } finally { - reader.close(); - } - } catch (IOException e) { - throw CVSException.wrapException(e); - } catch (CoreException e) { - if (e.getStatus().getCode() == IResourceStatus.RESOURCE_NOT_FOUND) - return null; - throw CVSException.wrapException(e); - } - } - - /* - * Reads all lines of the specified file. - * Returns null if the file does not exist. - */ - public static byte[][] readLines(InputStream stream) throws CVSException { - try { - BufferedReader reader = new BufferedReader(new InputStreamReader(stream)); - List fileContentStore = new ArrayList(); - try { - String line; - while ((line = reader.readLine()) != null) { - fileContentStore.add(line.getBytes()); - } - return (byte[][]) fileContentStore.toArray(new byte[fileContentStore.size()][]); - } finally { - reader.close(); - } - } catch (IOException e) { - throw CVSException.wrapException(e); - } - } - - /* - * Writes all lines to the specified file, using linefeed terminators for - * compatibility with other CVS clients. - */ - private static void writeLines(final IFile file, final String[] contents) throws CVSException { - try { - // The creation of sync files has to be in a runnable in order for the resulting delta - // to include the MODSTAMP value. If not in a runnable then create/setContents - // will trigger a delta and the SyncFileWriter change listener won't know that the delta - // was a result of our own creation. - ResourcesPlugin.getWorkspace().run(new IWorkspaceRunnable() { - public void run(IProgressMonitor monitor) throws CoreException { - try { - ByteArrayOutputStream os = new ByteArrayOutputStream(); - writeLinesToStreamAndClose(os, contents); - if(!file.exists()) { - file.create(new ByteArrayInputStream(os.toByteArray()), IResource.NONE /*don't keep history and don't force*/, null); - } else { - file.setContents(new ByteArrayInputStream(os.toByteArray()), IResource.NONE /*don't keep history and don't force*/, null); - } - file.setSessionProperty(MODSTAMP_KEY, new Long(file.getModificationStamp())); - } catch(CVSException e) { - throw new CoreException(e.getStatus()); - } - } - }, null); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } - } - - private static void writeLinesToStreamAndClose(OutputStream os, String[] contents) throws CVSException { - try { - try { - for (int i = 0; i < contents.length; i++) { - os.write(contents[i].getBytes()); - os.write(0x0A); // newline byte - } - } finally { - os.close(); - } - } catch (IOException e) { - throw CVSException.wrapException(e); - } - } - - /** - * Method writeFileToBaseDirectory. - * - * @param file - * @param info - */ - public static void writeFileToBaseDirectory(IFile file, IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - try { - IFolder baseFolder = getBaseDirectory(file); - if (!baseFolder.exists()) { - baseFolder.create(false /* force */, true /* local */, Policy.subMonitorFor(monitor, 10)); - } - IFile target = baseFolder.getFile(new Path(file.getName())); - if (target.exists()) { - // XXX Should ensure that we haven't already copied it - // XXX write the revision to the CVS/Baserev file - target.delete(true, Policy.subMonitorFor(monitor, 10)); - } - // Copy the file so the timestamp is maintained - file.copy(target.getFullPath(), true /* force */, Policy.subMonitorFor(monitor, 80)); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - monitor.done(); - } - } - /** - * Method restoreFileFromBaseDirectory. - * @param file - * @param info - * @param monitor - */ - public static void restoreFileFromBaseDirectory(IFile file, IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - try { - IFolder baseFolder = getBaseDirectory(file); - IFile source = baseFolder.getFile(new Path(file.getName())); - if (!source.exists()) { - throw new CVSException(Policy.bind("SyncFileWriter.baseNotAvailable", file.getFullPath().toString())); //$NON-NLS-1$ - } - if (file.exists()) { - file.delete(false /* force */, true /* keep history */, Policy.subMonitorFor(monitor, 10)); - } - // Copy the file so the timestamp is maintained - source.move(file.getFullPath(), false /* force */, true /* keep history */,Policy.subMonitorFor(monitor, 100)); - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - monitor.done(); - } - } - - /** - * Method deleteFileFromBaseDirectory. - * @param file - * @param monitor - */ - public static void deleteFileFromBaseDirectory(IFile file, IProgressMonitor monitor) throws CVSException { - monitor = Policy.monitorFor(monitor); - monitor.beginTask(null, 100); - try { - IFolder baseFolder = getBaseDirectory(file); - IFile source = baseFolder.getFile(new Path(file.getName())); - if (source.exists()) { - source.delete(false, false, Policy.subMonitorFor(monitor, 100)); - } - } catch (CoreException e) { - throw CVSException.wrapException(e); - } finally { - monitor.done(); - } - } - - private static IFolder getBaseDirectory(IFile file) throws CVSException { - IContainer cvsFolder = getCVSSubdirectory(file.getParent()); - IFolder baseFolder = cvsFolder.getFolder(new Path(BASE_DIRNAME)); - return baseFolder; - } - - /** - * Return a handle to the CVS/Template file for the given folder - * @param folder - * @return IFile - * @throws CVSException - */ - public static IFile getTemplateFile(IContainer folder) throws CVSException { - IFolder cvsFolder = createCVSSubdirectory(folder); - return cvsFolder.getFile("Template"); //$NON-NLS-1$ - } - - /** - * Method isEdited. - * @param resource - * @return boolean - */ - public static boolean isEdited(IFile file) throws CVSException { - IFolder baseFolder = getBaseDirectory(file); - IFile baseFile = baseFolder.getFile(file.getName()); - return baseFile.exists(); - } - -} diff --git a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/Util.java b/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/Util.java deleted file mode 100644 index 4f410e3b2..000000000 --- a/bundles/org.eclipse.team.cvs.core/src/org/eclipse/team/internal/ccvs/core/util/Util.java +++ /dev/null @@ -1,442 +0,0 @@ -/******************************************************************************* - * Copyright (c) 2000, 2003 IBM Corporation and others. - * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v1.0 - * which accompanies this distribution, and is available at - * http://www.eclipse.org/legal/cpl-v10.html - * - * Contributors: - * IBM Corporation - initial API and implementation - *******************************************************************************/ -package org.eclipse.team.internal.ccvs.core.util; - - -import java.io.IOException; -import java.io.InterruptedIOException; -import java.net.Socket; -import java.net.UnknownHostException; -import java.util.ArrayList; -import java.util.List; - -import org.eclipse.core.resources.IFolder; -import org.eclipse.core.resources.IProject; -import org.eclipse.core.resources.IResource; -import org.eclipse.core.runtime.CoreException; -import org.eclipse.core.runtime.IProgressMonitor; -import org.eclipse.core.runtime.IStatus; -import org.eclipse.team.internal.ccvs.core.CVSException; -import org.eclipse.team.internal.ccvs.core.CVSProviderPlugin; -import org.eclipse.team.internal.ccvs.core.CVSTag; -import org.eclipse.team.internal.ccvs.core.ICVSFolder; -import org.eclipse.team.internal.ccvs.core.ICVSResource; -import org.eclipse.team.internal.ccvs.core.Policy; -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.FolderSyncInfo; -import org.eclipse.team.internal.ccvs.core.syncinfo.ResourceSyncInfo; - -/** - * Unsorted static helper-methods - */ -public class Util { - - /** - * Return the last segment of the given path - * @param path - * @return String - */ - public static String getLastSegment(String path) { - int index = path.lastIndexOf(Session.SERVER_SEPARATOR); - if (index == -1) - return path; - else - return path.substring(index + 1); - - } - - /** - * Return the the given path with the last segment removed - * @param path - * @return String - */ - public static String removeLastSegment(String path) { - int index = path.lastIndexOf(Session.SERVER_SEPARATOR); - if (index == -1) - return ""; //$NON-NLS-1$ - else - return path.substring(0, index); - - } - /** - * Return the path without a trailing / - * @param path - * @return String - */ - public static String asPath(String path) { - if (path.endsWith(Session.SERVER_SEPARATOR)) { - return path.substring(0, path.length() - Session.SERVER_SEPARATOR.length()); - } - return path; - } - /* - * * - * Get the extention of the path of resource - * relative to the path of root - * - * @throws CVSException if root is not a root-folder of resource - */ - public static String getRelativePath(String rootName, String resourceName) - throws CVSException { - - if (!resourceName.startsWith(rootName) || rootName.length() > resourceName.length()) { - throw new CVSException(Policy.bind("Util.Internal_error,_resource_does_not_start_with_root_3")); //$NON-NLS-1$ - } - - // Otherwise we would get an ArrayOutOfBoundException - // in case of two equal Resources - if (rootName.length() == resourceName.length()) { - return ""; //$NON-NLS-1$ - } - - // Remove leading slash if there is one - String result = resourceName.substring(rootName.length()).replace('\\', '/'); - if (result.startsWith("/")) { //$NON-NLS-1$ - result = result.substring(1); - } - return result; - } - - /** - * Append the prefix and suffix to form a valid CVS path. - */ - public static String appendPath(String prefix, String suffix) { - if (prefix.length() == 0 || prefix.equals(Session.CURRENT_LOCAL_FOLDER)) { - return suffix; - } else if (prefix.endsWith(Session.SERVER_SEPARATOR)) { - if (suffix.startsWith(Session.SERVER_SEPARATOR)) - return prefix + suffix.substring(1); - else - return prefix + suffix; - } else if (suffix.startsWith(Session.SERVER_SEPARATOR)) - return prefix + suffix; - else - return prefix + Session.SERVER_SEPARATOR + suffix; - } - - public static void logError(String message, Throwable throwable) { - CVSProviderPlugin.log(IStatus.ERROR, message, throwable); - } - - /** - * If the number of segments in the relative path of <code>resource</code> to <code>root</code> is - * greater than <code>split</code> then the returned path is truncated to <code>split</code> number - * of segments and '...' is shown as the first segment of the path. - */ - public static String toTruncatedPath(ICVSResource resource, ICVSFolder root, int split) { - try { - String stringPath = resource.getRelativePath(root); - if (stringPath.equals(Session.CURRENT_LOCAL_FOLDER)) { - return resource.getName(); - } - return toTruncatedPath(stringPath, split); - } catch(CVSException e) { - return resource.getName(); - } - } - - public static String toTruncatedPath(String stringPath, int split) { - // Search backwards until split separators are found - int count = 0; - int index = stringPath.length(); - while (count++ < split && index != -1) { - index = stringPath.lastIndexOf(Session.SERVER_SEPARATOR, index - 1); - } - if (index == -1) { - return stringPath; - } else { - return Policy.bind("Util.truncatedPath", stringPath.substring(index)); //$NON-NLS-1$ - } - } - - /** - * Helper method that will time out when making a socket connection. - * This i - * s required because there is no way to provide a timeout value - * when creating a socket and in some instances, they don't seem to - * timeout at all. - */ - public static Socket createSocket(final String host, final int port, IProgressMonitor monitor) throws UnknownHostException, IOException { - - // Start a thread to open a socket - final Socket[] socket = new Socket[] { null }; - final Exception[] exception = new Exception[] {null }; - final Thread thread = new Thread(new Runnable() { - public void run() { - try { - Socket newSocket = new Socket(host, port); - synchronized (socket) { - if (Thread.interrupted()) { - // we we're either cancelled or timed out so just close the socket - newSocket.close(); - } else { - socket[0] = newSocket; - } - } - } catch (UnknownHostException e) { - exception[0] = e; - } catch (IOException e) { - exception[0] = e; - } - } - }); - thread.start(); - - // Wait the appropriate number of seconds - int timeout = CVSProviderPlugin.getPlugin().getTimeout(); - if (timeout == 0) timeout = CVSProviderPlugin.DEFAULT_TIMEOUT; - for (int i = 0; i < timeout; i++) { - try { - // wait for the thread to complete or 1 second, which ever comes first - thread.join(1000); - } catch (InterruptedException e) { - // I think this means the thread was interupted but not necessarily timed out - // so we don't need to do anything - } - synchronized (socket) { - // if the user cancelled, clean up before preempting the operation - if (monitor.isCanceled()) { - if (thread.isAlive()) { - thread.interrupt(); - } - if (socket[0] != null) { - socket[0].close(); - } - // this method will throw the proper exception - Policy.checkCanceled(monitor); - } - } - } - // If the thread is still running (i.e. we timed out) signal that it is too late - synchronized (socket) { - if (thread.isAlive()) { - thread.interrupt(); - } - } - if (exception[0] != null) { - if (exception[0] instanceof UnknownHostException) - throw (UnknownHostException)exception[0]; - else - throw (IOException)exception[0]; - } - if (socket[0] == null) { - throw new InterruptedIOException(Policy.bind("Util.timeout", host)); //$NON-NLS-1$ - } - return socket[0]; - } - - public static String[] parseIntoSubstrings(String string, String delimiter) { - List result = new ArrayList(); - int start = 0; - int index = string.indexOf(delimiter); - String next; - while (index != -1) { - next = string.substring(start, index); - result.add(next); - start = index + 1; - index = string.indexOf(delimiter, start); - } - if (start >= string.length()) { - next = "";//$NON-NLS-1$ - } else { - next = string.substring(start); - } - result.add(next); - return (String[]) result.toArray(new String[result.size()]); - } - - /** - * Return the substring at the given index (starting at 0) where each - * element is delimited by the provided delimiter. - * - * @param bytes - * @param delimiter - * @param index - * @param includeRest - * @return String - */ - public static String getSubstring(byte[] bytes, byte delimiter, int index, boolean includeRest) { - byte[] bytesForSlot = getBytesForSlot(bytes, delimiter, index, includeRest); - if (bytesForSlot == null) { - return null; - } - return new String(bytesForSlot); - } - - /** - * Return the offset the the Nth delimeter from the given start index. - * @param bytes - * @param delimiter - * @param start - * @param n - * @return int - */ - public static int getOffsetOfDelimeter(byte[] bytes, byte delimiter, int start, int n) { - int count = 0; - for (int i = start; i < bytes.length; i++) { - if (bytes[i] == delimiter) count++; - if (count == n) return i; - } - // the Nth delimeter was not found - return -1; - } - - /** - * Method getBytesForSlot. - * @param syncBytes - * @param SEPARATOR_BYTE - * @param i - * @param b - * @return byte[] - */ - public static byte[] getBytesForSlot(byte[] bytes, byte delimiter, int index, boolean includeRest) { - // Find the starting index - int start; - if (index == 0) { - // make start -1 so that end determination will start at offset 0. - start = -1; - } else { - start = getOffsetOfDelimeter(bytes, delimiter, 0, index); - if (start == -1) return null; - } - // Find the ending index - int end = getOffsetOfDelimeter(bytes, delimiter, start + 1, 1); - // Calculate the length - int length; - if (end == -1 || includeRest) { - length = bytes.length - start - 1; - } else { - length = end - start - 1; - } - byte[] result = new byte[length]; - System.arraycopy(bytes, start + 1, result, 0, length); - return result; - } - - /** - * Method equals. - * @param syncBytes - * @param oldBytes - * @return boolean - */ - public static boolean equals(byte[] syncBytes, byte[] oldBytes) { - if (syncBytes.length != oldBytes.length) return false; - for (int i = 0; i < oldBytes.length; i++) { - if (oldBytes[i] != syncBytes[i]) return false; - } - return true; - } - - /** - * Workaround a CVS bug where a CVS Folder with no immediately contained files has an incorrect - * Tag type stored in the TAG file. In this case, the tag type is always BRANCH (Tv1) - * - * The fix is for folders with no files, use the tag type for the containing project. Since projects almost - * always have files the TAG file is usually correct. - * - * For the case where the folder tag name does not match the project tag name we can not do much so we just - * return the folder tag which will currently always be a branch. - * - * @param resource The IResource being tested. Can not be null. - * @param tag The CVSTag as reported by CVS for the IResource. May be null. - * @return CVSTag The corrected tag for the resource. May be null. - */ - - public static CVSTag getAccurateFolderTag(IResource resource, CVSTag tag) { - - // Determine if the folder contains files as immediate children. - if (resource.getType() != IResource.FOLDER) { - return tag; - } - - IResource[] members = null; - try { - members = ((IFolder) resource).members(); - } catch (CoreException e1) { - return tag; - } - - for (int i = 0; i < members.length; i++) { - if (members[i].getType() == IResource.FILE) { - return tag; - } - } - - // Folder contains no files so this may not really be a branch. - // Make the type the same as the project tag type if both are the same tag name. - IProject project = resource.getProject(); - if (project == null) { - return tag; - } - - ICVSFolder projectFolder = CVSWorkspaceRoot.getCVSFolderFor(project); - FolderSyncInfo projectSyncInfo; - try { - projectSyncInfo = projectFolder.getFolderSyncInfo(); - } catch (CVSException e) { - return tag; - } - - if (projectSyncInfo == null) { - return tag; - } - - CVSTag projectTag = projectSyncInfo.getTag(); - - if (projectTag != null && projectTag.getName().equals(tag.getName())) { - return projectTag; - } else { - return tag; - } - } - - /** - * Workaround for CVS "bug" where CVS ENTRIES file does not contain correct - * Branch vs. Version info. Entries files always record a Tv1 so all entries would - * appear as branches. - * - * By comparing the revision number to the tag name - * you can determine if the tag is a branch or version. - * - * @param cvsResource the resource to test. Must nut be null. - * @return the correct cVSTag. May be null. - */ - - public static CVSTag getAccurateFileTag(ICVSResource cvsResource) throws CVSException { - - CVSTag tag = null; - ResourceSyncInfo info = cvsResource.getSyncInfo(); - if(info != null) { - tag = info.getTag(); - } - - FolderSyncInfo parentInfo = cvsResource.getParent().getFolderSyncInfo(); - CVSTag parentTag = null; - if(parentInfo != null) { - parentTag = parentInfo.getTag(); - } - - if(tag != null) { - if(tag.getName().equals(info.getRevision())) { - tag = new CVSTag(tag.getName(), CVSTag.VERSION); - } else if(parentTag != null){ - tag = new CVSTag(tag.getName(), parentTag.getType()); - } - } else { - // if a file doesn't have tag info, very possible for example - // when the file is in HEAD, use the parents. - tag = parentTag; - } - - return tag; - } -} |