KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > eclipse > team > internal > ccvs > core > CVSCompareSubscriber


1 /*******************************************************************************
2  * Copyright (c) 2000, 2006 IBM Corporation and others.
3  * All rights reserved. This program and the accompanying materials
4  * are made available under the terms of the Eclipse Public License v1.0
5  * which accompanies this distribution, and is available at
6  * http://www.eclipse.org/legal/epl-v10.html
7  *
8  * Contributors:
9  * IBM Corporation - initial API and implementation
10  *******************************************************************************/

11 package org.eclipse.team.internal.ccvs.core;
12
13 import java.util.*;
14
15 import org.eclipse.core.resources.*;
16 import org.eclipse.core.runtime.QualifiedName;
17 import org.eclipse.osgi.util.NLS;
18 import org.eclipse.team.core.TeamException;
19 import org.eclipse.team.core.subscribers.*;
20 import org.eclipse.team.core.variants.IResourceVariantTree;
21 import org.eclipse.team.core.variants.SessionResourceVariantByteStore;
22 import org.eclipse.team.internal.ccvs.core.resources.CVSWorkspaceRoot;
23 import org.eclipse.team.internal.ccvs.core.syncinfo.CVSResourceVariantTree;
24 import org.eclipse.team.internal.ccvs.core.syncinfo.MultiTagResourceVariantTree;
25
26 /**
27  * This subscriber is used when comparing the local workspace with its
28  * corresponding remote.
29  */

30 public class CVSCompareSubscriber extends CVSSyncTreeSubscriber implements ISubscriberChangeListener {
31
32     public static final String JavaDoc ID = "org.eclipse.team.cvs.ui.compare-participant"; //$NON-NLS-1$
33
public static final String JavaDoc ID_MODAL = "org.eclipse.team.cvs.ui.compare-participant-modal"; //$NON-NLS-1$
34

35     public static final String JavaDoc QUALIFIED_NAME = CVSProviderPlugin.ID + ".compare"; //$NON-NLS-1$
36
private static final String JavaDoc UNIQUE_ID_PREFIX = "compare-"; //$NON-NLS-1$
37

38     private IResource[] resources;
39     private CVSResourceVariantTree tree;
40     
41     public CVSCompareSubscriber(IResource[] resources, CVSTag tag) {
42         super(getUniqueId(), NLS.bind(CVSMessages.CVSCompareSubscriber_2, new String JavaDoc[] { tag.getName() })); //
43
this.resources = resources;
44         tree = new CVSResourceVariantTree(new SessionResourceVariantByteStore(), tag, getCacheFileContentsHint());
45         initialize();
46     }
47
48     public CVSCompareSubscriber(IResource[] resources, CVSTag[] tags, String JavaDoc name) {
49         super(getUniqueId(), NLS.bind(CVSMessages.CVSCompareSubscriber_2, new String JavaDoc[] { name })); //
50
resetRoots(resources, tags);
51         initialize();
52     }
53
54     /**
55      * @param resources
56      * @param tags
57      */

58     public void resetRoots(IResource[] resources, CVSTag[] tags) {
59         if (this.resources != null) {
60             List removed = new ArrayList();
61             for (int i = 0; i < this.resources.length; i++) {
62                 IResource resource = this.resources[i];
63                 removed.add(new SubscriberChangeEvent(this, ISubscriberChangeEvent.ROOT_REMOVED, resource));
64             }
65             this.resources = new IResource[0];
66             fireTeamResourceChange((ISubscriberChangeEvent[]) removed.toArray(new ISubscriberChangeEvent[removed.size()]));
67             if (tree != null) {
68                 tree.dispose();
69                 tree = null;
70             }
71         }
72         this.resources = resources;
73         MultiTagResourceVariantTree multiTree = new MultiTagResourceVariantTree(new SessionResourceVariantByteStore(), getCacheFileContentsHint());
74         for (int i = 0; i < tags.length; i++) {
75             multiTree.addResource(resources[i], tags[i]);
76         }
77         tree = multiTree;
78     }
79
80     private void initialize() {
81         CVSProviderPlugin.getPlugin().getCVSWorkspaceSubscriber().addListener(this);
82     }
83
84     public void dispose() {
85         CVSProviderPlugin.getPlugin().getCVSWorkspaceSubscriber().removeListener(this);
86         tree.dispose();
87     }
88     
89     private static QualifiedName getUniqueId() {
90         String JavaDoc uniqueId = Long.toString(System.currentTimeMillis());
91         return new QualifiedName(QUALIFIED_NAME, UNIQUE_ID_PREFIX + uniqueId);
92     }
93
94     /* (non-Javadoc)
95      * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getBaseSynchronizationCache()
96      */

97     protected IResourceVariantTree getBaseTree() {
98         // No base cache needed since it's a two way compare
99
return null;
100     }
101
102     /* (non-Javadoc)
103      * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getRemoteSynchronizationCache()
104      */

105     protected IResourceVariantTree getRemoteTree() {
106         return tree;
107     }
108     
109     /* (non-Javadoc)
110      * @see org.eclipse.team.core.subscribers.TeamSubscriber#isThreeWay()
111      */

112     public boolean isThreeWay() {
113         return false;
114     }
115
116     /* (non-Javadoc)
117      * @see org.eclipse.team.core.subscribers.TeamSubscriber#roots()
118      */

119     public IResource[] roots() {
120         return resources;
121     }
122
123     /* (non-Javadoc)
124      * @see org.eclipse.team.core.subscribers.ITeamResourceChangeListener#teamResourceChanged(org.eclipse.team.core.subscribers.TeamDelta[])
125      */

126     public void subscriberResourceChanged(ISubscriberChangeEvent[] deltas) {
127         List outgoingDeltas = new ArrayList(deltas.length);
128         for (int i = 0; i < deltas.length; i++) {
129             ISubscriberChangeEvent delta = deltas[i];
130             if ((delta.getFlags() & ISubscriberChangeEvent.ROOT_REMOVED) != 0) {
131                 IResource resource = delta.getResource();
132                 outgoingDeltas.addAll(Arrays.asList(handleRemovedRoot(resource)));
133             } else if ((delta.getFlags() & ISubscriberChangeEvent.SYNC_CHANGED) != 0) {
134                 IResource resource = delta.getResource();
135                 try {
136                     if (isSupervised(resource)) {
137                         outgoingDeltas.add(new SubscriberChangeEvent(this, delta.getFlags(), resource));
138                     }
139                 } catch (TeamException e) {
140                     // Log and ignore
141
CVSProviderPlugin.log(e);
142                 }
143             }
144         }
145         
146         fireTeamResourceChange((SubscriberChangeEvent[]) outgoingDeltas.toArray(new SubscriberChangeEvent[outgoingDeltas.size()]));
147     }
148
149     private SubscriberChangeEvent[] handleRemovedRoot(IResource removedRoot) {
150         // Determine if any of the roots of the compare are affected
151
List removals = new ArrayList(resources.length);
152         for (int j = 0; j < resources.length; j++) {
153             IResource root = resources[j];
154             if (removedRoot.getFullPath().isPrefixOf(root.getFullPath())) {
155                 // The root is no longer managed by CVS
156
removals.add(root);
157                 try {
158                     tree.flushVariants(root, IResource.DEPTH_INFINITE);
159                 } catch (TeamException e) {
160                     CVSProviderPlugin.log(e);
161                 }
162             }
163         }
164         if (removals.isEmpty()) {
165             return new SubscriberChangeEvent[0];
166         }
167         
168         // Adjust the roots of the subscriber
169
List newRoots = new ArrayList(resources.length);
170         newRoots.addAll(Arrays.asList(resources));
171         newRoots.removeAll(removals);
172         resources = (IResource[]) newRoots.toArray(new IResource[newRoots.size()]);
173          
174         // Create the deltas for the removals
175
SubscriberChangeEvent[] deltas = new SubscriberChangeEvent[removals.size()];
176         for (int i = 0; i < deltas.length; i++) {
177             deltas[i] = new SubscriberChangeEvent(this, ISubscriberChangeEvent.ROOT_REMOVED, (IResource)removals.get(i));
178         }
179         return deltas;
180     }
181     
182     /* (non-Javadoc)
183      * @see org.eclipse.team.core.subscribers.TeamSubscriber#isSupervised(org.eclipse.core.resources.IResource)
184      */

185     public boolean isSupervised(IResource resource) throws TeamException {
186         if (super.isSupervised(resource)) {
187             if (!resource.exists() && !getRemoteTree().hasResourceVariant(resource)) {
188                 // Exclude conflicting deletions
189
return false;
190             }
191             for (int i = 0; i < resources.length; i++) {
192                 IResource root = resources[i];
193                 if (root.getFullPath().isPrefixOf(resource.getFullPath())) {
194                     return true;
195                 }
196             }
197         }
198         return false;
199     }
200     
201     /* (non-Javadoc)
202      * @see org.eclipse.team.internal.ccvs.core.CVSSyncTreeSubscriber#getCacheFileContentsHint()
203      */

204     protected boolean getCacheFileContentsHint() {
205         return true;
206     }
207     
208     public CVSTag getTag() {
209         return tree.getTag(ResourcesPlugin.getWorkspace().getRoot());
210     }
211         
212     /* (non-Javadoc)
213      * @see java.lang.Object#equals(java.lang.Object)
214      */

215     public boolean equals(Object JavaDoc other) {
216         if(this == other) return true;
217         if(! (other instanceof CVSCompareSubscriber)) return false;
218         CVSCompareSubscriber s = (CVSCompareSubscriber)other;
219         CVSResourceVariantTree tree1 = (CVSResourceVariantTree)getRemoteTree();
220         CVSResourceVariantTree tree2 = (CVSResourceVariantTree)s.getRemoteTree();
221         IWorkspaceRoot root = ResourcesPlugin.getWorkspace().getRoot();
222         CVSTag tag1 = tree1.getTag(root);
223         CVSTag tag2 = tree2.getTag(root);
224         if (tag1 == null || tag2 == null) return false;
225         return tag1.equals(tag2) && rootsEqual(s);
226     }
227     
228     /**
229      * Prime the remote tree with the sync info from the local workspace.
230      * This is done to ensure that we don't get a huge nimber of outgoing
231      * changes before the first refresh.
232      *
233      */

234     public void primeRemoteTree() throws CVSException {
235         for (int i = 0; i < resources.length; i++) {
236             IResource resource = resources[i];
237             ICVSResource cvsResource = CVSWorkspaceRoot.getCVSResourceFor(resource);
238             cvsResource.accept(new ICVSResourceVisitor() {
239                 public void visitFile(ICVSFile file) throws CVSException {
240                     byte[] bytes = file.getSyncBytes();
241                     if (bytes != null) {
242                         try {
243                             tree.getByteStore().setBytes(file.getIResource(), bytes);
244                         } catch (TeamException e) {
245                             throw CVSException.wrapException(e);
246                         }
247                     }
248                 }
249                 public void visitFolder(ICVSFolder folder) throws CVSException {
250                     // No need to copy sync info for folders since
251
// CVS resource variant tree will get missing
252
// folder info from the local resources
253
folder.acceptChildren(this);
254                 }
255             });
256         }
257     }
258
259     /**
260      * Return the tag associated with the given root resource
261      * or <code>null</code> if there is only a single tag
262      * for the subscriber.
263      * @param root the root resource
264      * @return the tag associated with the given root resource
265      */

266     public CVSTag getTag(IResource root) {
267         return tree.getTag(root);
268     }
269     
270     /**
271      * Return <code>true</code> if the tag against which each
272      * root is compared may differ.
273      * @return whether the tag on each root may differ.
274      */

275     public boolean isMultipleTagComparison() {
276         return getTag() == null;
277     }
278
279 }
280
Popular Tags