| /******************************************************************************* |
| * Copyright (c) 2000, 2012 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| *******************************************************************************/ |
| package org.eclipse.core.tests.resources.regression; |
| |
| import java.io.IOException; |
| import java.io.InputStream; |
| import junit.framework.Test; |
| import junit.framework.TestSuite; |
| import org.eclipse.core.filesystem.IFileStore; |
| import org.eclipse.core.internal.resources.Resource; |
| import org.eclipse.core.resources.*; |
| import org.eclipse.core.runtime.CoreException; |
| import org.eclipse.core.runtime.Platform; |
| import org.eclipse.core.tests.resources.ResourceTest; |
| |
| /** |
| * When moving a resource "x" from parent "a" to parent "b", if "x" or any of |
| * its children can't be deleted, both "a" and "b" become out-of-sync and resource info is lost. |
| */ |
| public class Bug_032076 extends ResourceTest { |
| |
| public Bug_032076() { |
| super(""); |
| } |
| |
| public Bug_032076(String name) { |
| super(name); |
| } |
| |
| public static Test suite() { |
| return new TestSuite(Bug_032076.class); |
| } |
| |
| public void testFileBugOnWindows() { |
| if (!isWindows()) { |
| return; |
| } |
| |
| InputStream input = null; |
| IProject project = null; |
| try { |
| IWorkspace workspace = getWorkspace(); |
| project = workspace.getRoot().getProject(getUniqueString()); |
| IFolder sourceParent = project.getFolder("source_parent"); |
| IFolder destinationParent = project.getFolder("destination_parent"); |
| // this file will be made irremovable |
| IFile sourceFile = sourceParent.getFile("file1.txt"); |
| IFile destinationFile = destinationParent.getFile(sourceFile.getName()); |
| |
| ensureExistsInWorkspace(new IResource[] {sourceFile, destinationParent}, true); |
| |
| // add a marker to a file to ensure the move operation is not losing anything |
| String attributeKey = getRandomString(); |
| String attributeValue = getRandomString(); |
| long markerId = -1; |
| try { |
| IMarker bookmark = null; |
| bookmark = sourceFile.createMarker(IMarker.BOOKMARK); |
| bookmark.setAttribute(attributeKey, attributeValue); |
| markerId = bookmark.getId(); |
| } catch (CoreException e) { |
| fail("0.1", e); |
| } |
| |
| // opens the file so it cannot be removed on Windows |
| try { |
| input = sourceFile.getContents(); |
| } catch (CoreException ce) { |
| fail("1.0"); |
| } |
| |
| try { |
| sourceFile.move(destinationFile.getFullPath(), IResource.FORCE, getMonitor()); |
| fail("2.0"); |
| } catch (CoreException ce) { |
| // success |
| } |
| |
| // the source parent is in sync |
| assertTrue("3.0", sourceParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| // the target parent is in sync |
| assertTrue("3.1", destinationParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| // file has been copied to destination |
| assertTrue("3.4", destinationFile.exists()); |
| |
| // ensure marker info has not been lost |
| try { |
| IMarker marker = destinationFile.findMarker(markerId); |
| assertNotNull("3.6", marker); |
| assertEquals("3.7", attributeValue, marker.getAttribute(attributeKey)); |
| } catch (CoreException e) { |
| fail("3.8", e); |
| } |
| |
| // non-removable file has been moved (but not in file system - they are out-of-sync) |
| assertTrue("4.1", sourceFile.exists()); |
| assertTrue("4.2", sourceFile.isSynchronized(IResource.DEPTH_ZERO)); |
| |
| // refresh the source parent |
| try { |
| sourceParent.refreshLocal(IResource.DEPTH_INFINITE, getMonitor()); |
| } catch (CoreException e) { |
| fail("4.4"); |
| } |
| |
| // file is still found in source tree |
| assertTrue("4.7", sourceFile.exists()); |
| |
| } finally { |
| try { |
| if (input != null) { |
| input.close(); |
| } |
| } catch (IOException e) { |
| fail("5.0", e); |
| } finally { |
| if (project != null) { |
| ensureDoesNotExistInFileSystem(project); |
| } |
| } |
| } |
| } |
| |
| public void testFolderBugOnWindows() { |
| if (!isWindows()) { |
| return; |
| } |
| |
| InputStream input = null; |
| IProject project = null; |
| try { |
| IWorkspace workspace = getWorkspace(); |
| project = workspace.getRoot().getProject(getUniqueString()); |
| IFolder sourceParent = project.getFolder("source_parent"); |
| IFolder destinationParent = project.getFolder("destination_parent"); |
| IFolder folder = sourceParent.getFolder("folder"); |
| IFolder destinationFolder = destinationParent.getFolder(folder.getName()); |
| // this file will be made un-removable |
| IFile file1 = folder.getFile("file1.txt"); |
| // but not this one |
| IFile file2 = folder.getFile("file2.txt"); |
| |
| ensureExistsInWorkspace(new IResource[] {file1, file2, destinationParent}, true); |
| |
| // add a marker to a file to ensure the move operation is not losing anything |
| String attributeKey = getRandomString(); |
| String attributeValue = getRandomString(); |
| long markerId = -1; |
| try { |
| IMarker bookmark = null; |
| bookmark = file1.createMarker(IMarker.BOOKMARK); |
| bookmark.setAttribute(attributeKey, attributeValue); |
| markerId = bookmark.getId(); |
| } catch (CoreException e) { |
| fail("0.1", e); |
| } |
| |
| // opens a file so it (and its parent) cannot be removed on Windows |
| try { |
| input = file1.getContents(); |
| } catch (CoreException ce) { |
| fail("1.0", ce); |
| } |
| |
| try { |
| folder.move(destinationFolder.getFullPath(), IResource.FORCE, getMonitor()); |
| fail("2.0"); |
| } catch (CoreException ce) { |
| // success |
| } |
| |
| // the source parent is in sync |
| assertTrue("3.0", sourceParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| // the target parent is in-sync |
| assertTrue("3.1", destinationParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| // resources have been copied to destination |
| assertTrue("3.3", destinationFolder.exists()); |
| assertTrue("3.4", destinationFolder.getFile(file1.getName()).exists()); |
| assertTrue("3.5", destinationFolder.getFile(file2.getName()).exists()); |
| |
| // ensure marker info has not been lost |
| try { |
| IMarker marker = destinationFolder.getFile(file1.getName()).findMarker(markerId); |
| assertNotNull("3.6", marker); |
| assertEquals("3.7", attributeValue, marker.getAttribute(attributeKey)); |
| } catch (CoreException e) { |
| fail("3.8", e); |
| } |
| |
| // non-removable resources still exist in source |
| assertTrue("4.1", folder.exists()); |
| assertTrue("4.2", file1.exists()); |
| //this file should be successfully moved |
| assertTrue("4.3", !file2.exists()); |
| |
| // refresh the source parent |
| try { |
| sourceParent.refreshLocal(IResource.DEPTH_INFINITE, getMonitor()); |
| } catch (CoreException e) { |
| fail("4.4"); |
| } |
| |
| // non-removable resources still in source tree |
| assertTrue("4.6", folder.exists()); |
| assertTrue("4.7", file1.exists()); |
| assertTrue("4.8", !file2.exists()); |
| |
| } finally { |
| try { |
| if (input != null) { |
| input.close(); |
| } |
| } catch (IOException e) { |
| fail("5.0", e); |
| } finally { |
| if (project != null) { |
| ensureDoesNotExistInFileSystem(project); |
| } |
| } |
| } |
| } |
| |
| public void testProjectBugOnWindows() { |
| if (!isWindows()) { |
| return; |
| } |
| |
| IProject sourceProject = null; |
| IProject destinationProject = null; |
| InputStream input = null; |
| try { |
| IWorkspace workspace = getWorkspace(); |
| sourceProject = workspace.getRoot().getProject(getUniqueString() + ".source"); |
| destinationProject = workspace.getRoot().getProject(getUniqueString() + ".dest"); |
| // this file will be made un-removable |
| IFile file1 = sourceProject.getFile("file1.txt"); |
| // but not this one |
| IFile file2 = sourceProject.getFile("file2.txt"); |
| |
| ensureExistsInWorkspace(new IResource[] {file1, file2}, true); |
| |
| // add a marker to a file to ensure the move operation is not losing anything |
| String attributeKey = getRandomString(); |
| String attributeValue = getRandomString(); |
| long markerId = -1; |
| try { |
| IMarker bookmark = null; |
| bookmark = file1.createMarker(IMarker.BOOKMARK); |
| bookmark.setAttribute(attributeKey, attributeValue); |
| markerId = bookmark.getId(); |
| } catch (CoreException e) { |
| fail("0.1", e); |
| } |
| |
| // opens a file so it (and its parent) cannot be removed on Windows |
| try { |
| input = file1.getContents(); |
| } catch (CoreException ce) { |
| fail("1.0", ce); |
| } |
| |
| try { |
| sourceProject.move(destinationProject.getFullPath(), IResource.FORCE, getMonitor()); |
| fail("2.0"); |
| } catch (CoreException ce) { |
| // success |
| } |
| |
| // the source does not exist |
| assertTrue("3.0", !sourceProject.exists()); |
| assertTrue("3.1", sourceProject.isSynchronized(IResource.DEPTH_INFINITE)); |
| // the target exists and is in sync |
| assertTrue("3.2", destinationProject.exists()); |
| assertTrue("3.3", destinationProject.isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| // resources have been copied to destination |
| assertTrue("3.4", destinationProject.getFile(file1.getProjectRelativePath()).exists()); |
| assertTrue("3.5", destinationProject.getFile(file2.getProjectRelativePath()).exists()); |
| |
| // ensure marker info has not been lost |
| try { |
| IMarker marker = destinationProject.getFile(file1.getProjectRelativePath()).findMarker(markerId); |
| assertNotNull("3.6", marker); |
| assertEquals("3.7", attributeValue, marker.getAttribute(attributeKey)); |
| } catch (CoreException e) { |
| fail("3.8", e); |
| } |
| |
| assertTrue("5.0", workspace.getRoot().isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| } finally { |
| try { |
| if (input != null) { |
| input.close(); |
| } |
| } catch (IOException e) { |
| fail("6.0", e); |
| } finally { |
| if (sourceProject != null) { |
| ensureDoesNotExistInFileSystem(sourceProject); |
| } |
| if (destinationProject != null) { |
| ensureDoesNotExistInFileSystem(destinationProject); |
| } |
| } |
| } |
| } |
| |
| /** |
| * TODO: This test is currently failing and needs further investigation (bug 203078) |
| */ |
| public void _testFileBugOnLinux() { |
| if (!(Platform.getOS().equals(Platform.OS_LINUX) && isReadOnlySupported())) { |
| return; |
| } |
| |
| IFileStore roFolderStore = null; |
| IProject project = null; |
| try { |
| IWorkspace workspace = getWorkspace(); |
| project = workspace.getRoot().getProject(getUniqueString()); |
| IFolder sourceParent = project.getFolder("source_parent"); |
| IFolder roFolder = sourceParent.getFolder("sub-folder"); |
| IFolder destinationParent = project.getFolder("destination_parent"); |
| // this file will be made un-removable |
| IFile sourceFile = roFolder.getFile("file.txt"); |
| IFile destinationFile = destinationParent.getFile("file.txt"); |
| |
| ensureExistsInWorkspace(new IResource[] {sourceFile, destinationParent}, true); |
| |
| roFolderStore = ((Resource) roFolder).getStore(); |
| |
| // add a marker to a file to ensure the move operation is not losing anything |
| String attributeKey = getRandomString(); |
| String attributeValue = getRandomString(); |
| long markerId = -1; |
| try { |
| IMarker bookmark = null; |
| bookmark = sourceFile.createMarker(IMarker.BOOKMARK); |
| bookmark.setAttribute(attributeKey, attributeValue); |
| markerId = bookmark.getId(); |
| } catch (CoreException e) { |
| fail("0.1", e); |
| } |
| |
| // mark sub-folder as read-only so its immediate children cannot be removed on Linux |
| setReadOnly(roFolder, true); |
| try { |
| sourceFile.move(destinationFile.getFullPath(), IResource.FORCE, getMonitor()); |
| fail("2.0"); |
| } catch (CoreException ce) { |
| // success |
| } |
| |
| // the source parent is out-of-sync |
| assertTrue("3.0", !sourceParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| // the target parent is in-sync |
| assertTrue("3.1", destinationParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| // file has been copied to destination |
| assertTrue("3.4", destinationFile.exists()); |
| |
| // ensure marker info has not been lost |
| try { |
| IMarker marker = destinationFile.findMarker(markerId); |
| assertNotNull("3.6", marker); |
| assertEquals("3.7", attributeValue, marker.getAttribute(attributeKey)); |
| } catch (CoreException e) { |
| fail("3.8", e); |
| } |
| |
| // non-removable file has been moved (but not in file system - they are out-of-sync) |
| assertTrue("4.1", !sourceFile.exists()); |
| |
| // refresh the source parent |
| try { |
| sourceParent.refreshLocal(IResource.DEPTH_INFINITE, getMonitor()); |
| } catch (CoreException e) { |
| fail("4.4"); |
| } |
| |
| // non-removable file now reappear in the resource tree |
| assertTrue("4.7", sourceFile.exists()); |
| |
| } finally { |
| if (roFolderStore != null) { |
| setReadOnly(roFolderStore, false); |
| } |
| if (project != null) { |
| ensureDoesNotExistInFileSystem(project); |
| } |
| } |
| } |
| |
| /** |
| * TODO: This test is currently failing and needs further investigation (bug 203078) |
| */ |
| public void _testFolderBugOnLinux() { |
| if (!(Platform.getOS().equals(Platform.OS_LINUX) && isReadOnlySupported())) { |
| return; |
| } |
| |
| IFileStore roFolderLocation = null, destinationROFolderLocation = null; |
| IProject project = null; |
| try { |
| IWorkspace workspace = getWorkspace(); |
| project = workspace.getRoot().getProject(getUniqueString()); |
| IFolder sourceParent = project.getFolder("source_parent"); |
| IFolder roFolder = sourceParent.getFolder("sub-folder"); |
| IFolder folder = roFolder.getFolder("folder"); |
| IFile file1 = roFolder.getFile("file1.txt"); |
| IFile file2 = folder.getFile("file2.txt"); |
| IFolder destinationParent = project.getFolder("destination_parent"); |
| IFolder destinationROFolder = destinationParent.getFolder(roFolder.getName()); |
| |
| ensureExistsInWorkspace(new IResource[] {file1, file2, destinationParent}, true); |
| |
| roFolderLocation = ((Resource) roFolder).getStore(); |
| destinationROFolderLocation = ((Resource) destinationROFolder).getStore(); |
| |
| // add a marker to a file to ensure the move operation is not losing anything |
| String attributeKey = getRandomString(); |
| String attributeValue = getRandomString(); |
| long markerId = -1; |
| try { |
| IMarker bookmark = null; |
| bookmark = file1.createMarker(IMarker.BOOKMARK); |
| bookmark.setAttribute(attributeKey, attributeValue); |
| markerId = bookmark.getId(); |
| } catch (CoreException e) { |
| fail("0.1", e); |
| } |
| |
| // mark sub-folder as read-only so its immediate children cannot be removed on Linux |
| setReadOnly(roFolder, true); |
| |
| try { |
| roFolder.move(destinationParent.getFullPath().append(roFolder.getName()), IResource.FORCE, getMonitor()); |
| fail("2.0"); |
| } catch (CoreException ce) { |
| // success |
| } |
| |
| // the source parent is out-of-sync |
| assertTrue("3.0", !sourceParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| // the target parent is in-sync |
| assertTrue("3.1", destinationParent.isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| // resources have been copied to destination |
| IFolder destinationFolder = destinationROFolder.getFolder(folder.getName()); |
| IFile destinationFile1 = destinationROFolder.getFile(file1.getName()); |
| IFile destinationFile2 = destinationFolder.getFile(file2.getName()); |
| assertTrue("3.2", destinationROFolder.exists()); |
| assertTrue("3.4", destinationFolder.exists()); |
| assertTrue("3.5", destinationFile1.exists()); |
| assertTrue("3.6", destinationFile2.exists()); |
| |
| // ensure marker info has not been lost |
| try { |
| IMarker marker = destinationROFolder.getFile(file1.getName()).findMarker(markerId); |
| assertNotNull("3.7", marker); |
| assertEquals("3.8", attributeValue, marker.getAttribute(attributeKey)); |
| } catch (CoreException e) { |
| fail("3.9", e); |
| } |
| |
| // non-removable resources have been moved (but not in file system - they are out-of-sync) |
| assertTrue("4.0", !roFolder.exists()); |
| assertTrue("4.1", !folder.exists()); |
| assertTrue("4.2", !file1.exists()); |
| assertTrue("4.3", !file2.exists()); |
| |
| // refresh the source parent |
| try { |
| sourceParent.refreshLocal(IResource.DEPTH_INFINITE, getMonitor()); |
| } catch (CoreException e) { |
| fail("4.4"); |
| } |
| |
| // non-removed resources now reappear in the resource tree |
| assertTrue("4.5", roFolder.exists()); |
| assertTrue("4.6", folder.exists()); |
| assertTrue("4.7", file1.exists()); |
| assertTrue("4.8", !file2.exists()); |
| |
| } finally { |
| if (roFolderLocation != null) { |
| setReadOnly(roFolderLocation, false); |
| } |
| if (destinationROFolderLocation != null) { |
| setReadOnly(destinationROFolderLocation, false); |
| } |
| if (project != null) { |
| ensureDoesNotExistInFileSystem(project); |
| } |
| } |
| } |
| |
| /** |
| * TODO: This test is currently failing and needs further investigation (bug 203078) |
| */ |
| public void _testProjectBugOnLinux() { |
| if (!(Platform.getOS().equals(Platform.OS_LINUX) && isReadOnlySupported())) { |
| return; |
| } |
| |
| IWorkspace workspace = getWorkspace(); |
| IProject sourceProject = workspace.getRoot().getProject(getUniqueString() + ".source"); |
| IProject destinationProject = null; |
| IFileStore projectParentStore = getTempStore(); |
| IFileStore projectStore = projectParentStore.getChild(sourceProject.getName()); |
| try { |
| IProjectDescription sourceDescription = workspace.newProjectDescription(sourceProject.getName()); |
| sourceDescription.setLocationURI(projectStore.toURI()); |
| |
| destinationProject = workspace.getRoot().getProject(getUniqueString() + ".dest"); |
| IProjectDescription destinationDescription = workspace.newProjectDescription(destinationProject.getName()); |
| |
| // create and open the source project at a non-default location |
| try { |
| sourceProject.create(sourceDescription, getMonitor()); |
| } catch (CoreException e) { |
| fail("0.1", e); |
| } |
| try { |
| sourceProject.open(getMonitor()); |
| } catch (CoreException e) { |
| fail("0.2", e); |
| } |
| |
| IFile file1 = sourceProject.getFile("file1.txt"); |
| |
| ensureExistsInWorkspace(new IResource[] {file1}, true); |
| |
| // add a marker to a file to ensure the move operation is not losing anything |
| String attributeKey = getRandomString(); |
| String attributeValue = getRandomString(); |
| long markerId = -1; |
| try { |
| IMarker bookmark = null; |
| bookmark = file1.createMarker(IMarker.BOOKMARK); |
| bookmark.setAttribute(attributeKey, attributeValue); |
| markerId = bookmark.getId(); |
| } catch (CoreException e) { |
| fail("0.5", e); |
| } |
| |
| // mark sub-folder as read-only so its immediate children cannot be removed on Linux |
| setReadOnly(projectParentStore, true); |
| |
| try { |
| sourceProject.move(destinationDescription, IResource.FORCE, getMonitor()); |
| fail("2.0"); |
| } catch (CoreException ce) { |
| // success |
| } |
| |
| // the source does not exist |
| assertTrue("3.0", !sourceProject.exists()); |
| // the target exists and is in sync |
| assertTrue("3.1", destinationProject.exists()); |
| assertTrue("3.2", destinationProject.isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| // resources have been copied to destination |
| assertTrue("3.4", destinationProject.getFile(file1.getProjectRelativePath()).exists()); |
| |
| // ensure marker info has not been lost |
| try { |
| IMarker marker = destinationProject.getFile(file1.getProjectRelativePath()).findMarker(markerId); |
| assertNotNull("3.6", marker); |
| assertEquals("3.7", attributeValue, marker.getAttribute(attributeKey)); |
| } catch (CoreException e) { |
| fail("3.8", e); |
| } |
| // project's content area still exists in file system |
| assertTrue("4.0", projectStore.fetchInfo().exists()); |
| |
| assertTrue("5.0", workspace.getRoot().isSynchronized(IResource.DEPTH_INFINITE)); |
| |
| } finally { |
| setReadOnly(projectParentStore, false); |
| ensureDoesNotExistInFileSystem(sourceProject); |
| if (destinationProject != null) { |
| ensureDoesNotExistInFileSystem(destinationProject); |
| } |
| } |
| } |
| } |