Fix for 17944.
diff --git a/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/ResourceTree.java b/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/ResourceTree.java index c147ee1..8fe4c53 100644 --- a/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/ResourceTree.java +++ b/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/ResourceTree.java
@@ -1,16 +1,15 @@ /********************************************************************** * Copyright (c) 2002 IBM Corporation and others. * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v0.5 + * 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-v05.html + * http://www.eclipse.org/legal/cpl-v10.html * * Contributors: * IBM - Initial API and implementation **********************************************************************/ package org.eclipse.core.internal.resources; -import java.io.*; import org.eclipse.core.internal.localstore.*; import org.eclipse.core.internal.properties.PropertyManager; import org.eclipse.core.internal.utils.Assert; @@ -205,7 +204,7 @@ // Move the workspace tree. try { - workspace.move(source, destination.getFullPath(), depth, false); + workspace.move(source, destination.getFullPath(), depth, false, true); } catch (CoreException e) { String message = Policy.bind("resources.errorMoving", source.getFullPath().toString(), destination.getFullPath().toString()); //$NON-NLS-1$ IStatus status = new ResourceStatus(IStatus.ERROR, source.getFullPath(), message, e);
diff --git a/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/Workspace.java b/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/Workspace.java index 6dd5e3f..815ab3d 100644 --- a/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/Workspace.java +++ b/bundles/org.eclipse.core.resources/src/org/eclipse/core/internal/resources/Workspace.java
@@ -1,9 +1,9 @@ /******************************************************************************* * Copyright (c) 2000, 2002 IBM Corporation and others. * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v0.5 + * 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-v05.html + * http://www.eclipse.org/legal/cpl-v10.html * * Contributors: * IBM - Initial API and implementation @@ -428,6 +428,9 @@ } protected void copyTree(IResource source, IPath destination, int depth, boolean phantom, boolean overwrite) throws CoreException { + copyTree(source, destination, depth, phantom, overwrite, false); +} +protected void copyTree(IResource source, IPath destination, int depth, boolean phantom, boolean overwrite, boolean keepSyncInfo) throws CoreException { // FIXME: change this method signature to use the int updateFlags rather than the booleans. // retrieve the resource at the destination if there is one (phantoms included). @@ -452,7 +455,7 @@ sourceInfo = (ResourceInfo) sourceInfo.clone(); sourceInfo.setType(destinationResource.getType()); } - ResourceInfo newInfo = createResource(destinationResource, sourceInfo, phantom, overwrite); + ResourceInfo newInfo = createResource(destinationResource, sourceInfo, phantom, overwrite, keepSyncInfo); // get/set the node id from the source's resource info so we can later put it in the // info for the destination resource. This will help us generate the proper deltas, // indicating a move rather than a add/delete @@ -475,7 +478,7 @@ for (int i = 0; i < children.length; i++) { IResource child = children[i]; IPath childPath = destination.append(child.getName()); - copyTree(child, childPath, depth, phantom, overwrite); + copyTree(child, childPath, depth, phantom, overwrite, keepSyncInfo); } } /** @@ -505,6 +508,9 @@ } return 0; } +public ResourceInfo createResource(IResource resource, ResourceInfo info, boolean phantom, boolean overwrite) throws CoreException { + return createResource(resource, info, phantom, overwrite, false); +} /* * Creates the given resource in the tree and returns the new resource info object. * If phantom is true, the created element is marked as a phantom. @@ -514,8 +520,12 @@ * the element is overwritten with the new element. (but the synchronization * information is preserved) If the specified resource info is null, then create * a new one. + * + * If keepSyncInfo is set to be true, the sync info in the given ResourceInfo is NOT + * cleared before being created and thus any sync info already existing at that namespace + * (as indicated by an already existing phantom resource) will be lost. */ -public ResourceInfo createResource(IResource resource, ResourceInfo info, boolean phantom, boolean overwrite) throws CoreException { +public ResourceInfo createResource(IResource resource, ResourceInfo info, boolean phantom, boolean overwrite, boolean keepSyncInfo) throws CoreException { info = info == null ? newElement(resource.getType()) : (ResourceInfo) info.clone(); ResourceInfo original = getResourceInfo(resource.getFullPath(), true, false); if (phantom) { @@ -526,7 +536,8 @@ if (original == null) { // we got here from a copy/move. we don't want to copy over any sync info // from the source so clear it. - info.setSyncInfo(null); + if (!keepSyncInfo) + info.setSyncInfo(null); tree.createElement(resource.getFullPath(), info); } else { // if overwrite==true then slam the new info into the tree even if one existed before @@ -537,7 +548,8 @@ // preserve the old sync info so its not dirty // XXX: must copy over the generic sync info from the old info to the new // XXX: do we really need to clone the sync info here? - info.setSyncInfo(original.getSyncInfo(true)); + if (!keepSyncInfo) + info.setSyncInfo(original.getSyncInfo(true)); // mark the markers bit as dirty so we snapshot an empty marker set for // the new resource info.set(ICoreConstants.M_MARKERS_SNAP_DIRTY); @@ -1146,15 +1158,20 @@ return move(resources, destination, updateFlags, monitor); } +/* package */ void move(Resource source, IPath destination, int depth, boolean overwrite) throws CoreException { + move(source, destination, depth, overwrite, false); +} /** * Moves this resource's subtree to the destination. This operation should only be * used by move methods. Destination must be a valid destination for this resource. + * The keepSyncInfo boolean is used to indicated whether or not the sync info should + * be moved from the source to the destination. */ -/* package */ void move(Resource source, IPath destination, int depth, boolean overwrite) throws CoreException { +/* package */ void move(Resource source, IPath destination, int depth, boolean overwrite, boolean keepSyncInfo) throws CoreException { // overlay the tree at the destination path, preserving any important info // in any already existing resource infos - copyTree(source, destination, depth, false, overwrite); + copyTree(source, destination, depth, false, overwrite, keepSyncInfo); source.fixupAfterMoveSource(); } /**
diff --git a/tests/org.eclipse.core.tests.resources/src/org/eclipse/core/tests/resources/ISynchronizerTest.java b/tests/org.eclipse.core.tests.resources/src/org/eclipse/core/tests/resources/ISynchronizerTest.java index 7e0edf5..eb95f6c 100644 --- a/tests/org.eclipse.core.tests.resources/src/org/eclipse/core/tests/resources/ISynchronizerTest.java +++ b/tests/org.eclipse.core.tests.resources/src/org/eclipse/core/tests/resources/ISynchronizerTest.java
@@ -1,9 +1,9 @@ /********************************************************************** * Copyright (c) 2000,2002 IBM Corporation and others. * All rights reserved. This program and the accompanying materials - * are made available under the terms of the Common Public License v0.5 + * 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-v05.html + * http://www.eclipse.org/legal/cpl-v10.html * * Contributors: * IBM - Initial API and implementation @@ -370,6 +370,90 @@ fail("4.3", e); } } +public void testMoveResource2() { + final QualifiedName qname = new QualifiedName("org.eclipse.core.tests.resources", "myTarget"); + final ISynchronizer synchronizer = ResourcesPlugin.getWorkspace().getSynchronizer(); + + // cleanup auto-created resources + try { + getWorkspace().getRoot().delete(true, getMonitor()); + } catch (CoreException e) { + fail("0.0", e); + } + + // setup + IResource[] resources = buildResources(getWorkspace().getRoot(), new String[] { "/Foo", "/Foo/file.txt" }); + IProject sourceProject = (IProject) resources[0]; + IFile sourceFile = (IFile) resources[1]; + // create in workspace + ensureExistsInWorkspace(resources, true); + + // register partner and add sync info + synchronizer.add(qname); + byte[] b = new byte[] { 1, 2, 3, 4 }; + try { + synchronizer.setSyncInfo(qname, sourceProject, b); + synchronizer.setSyncInfo(qname, sourceFile, b); + } catch (CoreException e) { + fail("2.0", e); + } + + // move the file + IFile destFile = sourceProject.getFile("newFile.txt"); + try { + sourceFile.move(destFile.getFullPath(), true, getMonitor()); + } catch (CoreException e) { + fail("3.0", e); + } + + // check sync info + try { + byte[] old = synchronizer.getSyncInfo(qname, sourceFile); + assertNotNull("4.0", old); + assertEquals("4.1", b, old); + assertNull("4.2", synchronizer.getSyncInfo(qname, destFile)); + } catch (CoreException e) { + fail("4.3", e); + } + + // move the file back + try { + destFile.move(sourceFile.getFullPath(), true, getMonitor()); + } catch (CoreException e) { + fail("5.0", e); + } + + // check the sync info + try { + byte[] old = synchronizer.getSyncInfo(qname, sourceFile); + assertNotNull("6.0", old); + assertEquals("6.1", b, old); + assertNull("6.2", synchronizer.getSyncInfo(qname, destFile)); + } catch (CoreException e) { + fail("6.3", e); + } + + // rename the file and ensure that the sync info is moved with it + IProject destProject = getWorkspace().getRoot().getProject("newProject"); + try { + sourceProject.move(destProject.getFullPath(), true, getMonitor()); + } catch (CoreException e) { + fail("7.0", e); + } + try { + assertNull("7.1", synchronizer.getSyncInfo(qname, sourceProject)); + assertNull("7.2", synchronizer.getSyncInfo(qname, sourceFile)); + byte[] old = synchronizer.getSyncInfo(qname, destProject.getFile(sourceFile.getName())); + assertNotNull("7.3", old); + assertEquals("7.4", b, old); + old = synchronizer.getSyncInfo(qname, destProject); + assertNotNull("7.5", old); + assertEquals("7.6", b, old); + } catch (CoreException e) { + fail("7.3", e); + } + +} public void testRegistration() { // setup QualifiedName[] partners = new QualifiedName[NUMBER_OF_PARTNERS];