blob: c3e74a283da507b95d43348e5f5e442a8949d419 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2000, 2015 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
* Alexander Kurtakov <akurtako@redhat.com> - Bug 459343
*******************************************************************************/
package org.eclipse.core.tests.internal.localstore;
import java.io.*;
import java.util.*;
import junit.framework.Test;
import junit.framework.TestSuite;
import org.eclipse.core.filesystem.IFileStore;
import org.eclipse.core.filesystem.provider.FileInfo;
import org.eclipse.core.internal.localstore.IHistoryStore;
import org.eclipse.core.internal.resources.*;
import org.eclipse.core.internal.utils.UniversalUniqueIdentifier;
import org.eclipse.core.resources.*;
import org.eclipse.core.runtime.*;
import org.eclipse.core.tests.resources.ResourceTest;
/**
* This class defines all tests for the HistoryStore Class.
*/
public class HistoryStoreTest extends ResourceTest {
class LogListenerVerifier implements ILogListener {
List<Integer> actual = new ArrayList<>();
List<Integer> expected = new ArrayList<>();
void addExpected(int statusCode) {
expected.add(Integer.valueOf(statusCode));
}
String dump() {
StringBuffer buffer = new StringBuffer();
buffer.append("Expected:\n");
for (Integer integer : expected) {
buffer.append("\t" + integer + "\n");
}
buffer.append("Actual:\n");
for (Integer integer : actual) {
buffer.append("\t" + integer + "\n");
}
return buffer.toString();
}
@Override
public void logging(IStatus status, String plugin) {
actual.add(Integer.valueOf(status.getCode()));
}
void reset() {
expected = new ArrayList<>();
actual = new ArrayList<>();
}
void verify() throws VerificationFailedException {
String message;
if (expected.size() != actual.size()) {
message = "Expected size: " + expected.size() + " does not equal actual size: " + actual.size() + "\n";
message += dump();
throw new VerificationFailedException(message);
}
for (Integer status : expected) {
if (!actual.contains(status)) {
message = "Expected and actual results differ.\n";
message += dump();
throw new VerificationFailedException(message);
}
}
}
}
class VerificationFailedException extends Exception {
/**
* All serializable objects should have a stable serialVersionUID
*/
private static final long serialVersionUID = 1L;
VerificationFailedException(String message) {
super(message);
}
}
private IWorkspaceDescription original;
public static void assertEquals(String tag, IFileState expected, IFileState actual) {
assertEquals(tag + " path differs", expected.getFullPath(), actual.getFullPath());
assertEquals(tag + " timestamp differs", expected.getModificationTime(), actual.getModificationTime());
assertEquals(tag + " uuid differs", ((FileState) expected).getUUID(), ((FileState) actual).getUUID());
}
public static Test suite() {
// TestSuite suite = new TestSuite(HistoryStoreTest.class.getName());
// suite.addTest(new HistoryStoreTest("testMoveProject"));
// suite.addTest(new HistoryStoreTest("testFindDeleted"));
// return suite;
return new TestSuite(HistoryStoreTest.class);
}
/*
* This little helper method makes sure that the history store is
* completely clean after it is invoked. If a history store entry or
* a file is left, it may become part of the history for another file in
* another test (if this file has the same name).
*/
public static void wipeHistoryStore(IProgressMonitor monitor) {
IHistoryStore store = ((Workspace) getWorkspace()).getFileSystemManager().getHistoryStore();
// Remove all the entries from the history store index. Note that
// this does not cause the history store states to be removed.
store.remove(Path.ROOT, monitor);
// Now make sure all the states are really removed.
store.removeGarbage();
}
public HistoryStoreTest() {
super();
}
public HistoryStoreTest(String name) {
super(name);
}
private int numBytes(InputStream input) {
int i = 0;
int c = -1;
try {
c = input.read();
while (c != -1) {
i++;
c = input.read();
}
} catch (IOException e) {
i = 0;
}
if (c != -1) {
i = 0;
}
return i;
}
public IWorkspaceDescription setMaxFileStates(int maxFileStates) throws CoreException {
IWorkspaceDescription currentDescription = getWorkspace().getDescription();
IWorkspaceDescription newDescription = getWorkspace().getDescription();
newDescription.setMaxFileStates(maxFileStates);
getWorkspace().setDescription(newDescription);
return currentDescription;
}
@Override
protected void setUp() throws Exception {
super.setUp();
original = getWorkspace().getDescription();
}
@Override
protected void tearDown() throws Exception {
getWorkspace().setDescription(original);
super.tearDown();
wipeHistoryStore(getMonitor());
}
/**
* Test the various policies in place to ensure that the history store
* does not grow to unmanageable size. The policies currently in place
* include:
* - store only a maximum number of states for each file
* - do not store files greater than some stated size
* - consider history store information stale after some specified period
* of time and discard stale data
*
* History store states are always stored in order from the newest state to
* the oldest state. This will be tested as well
*
* Scenario:
* 1. Create project AddStateAndPoliciesProject
* 2. Create file (file.txt) random contents
* 3. Set policy information in the workspace description as follows:
* - don't store states older than 1 day
* - keep a maximum of 5 states per file
* - file states must be less than 1 Mb
* 4. Make 8 modifications to file.txt (causing 8 states to be created)
* 5. Ensure only 5 states were kept.
* 6. Ensure states are in order from newest to oldest.
* 7. Set policy such that file states must be no greater than 7 bytes.
* 8. Create a new file file1.txt
* 9. Add 10 bytes of data to this file.
* 10. Check each of the states for this file and ensure they are not
* greater than 7 bytes.
* 11. Revert to policy in #3
* 12. Make sure we still have 5 states for file.txt (the first file we
* worked with)
* 13. Change the policy so that data older than 10 seconds is stale.
* 14. Wait 12 seconds (make it longer than 10 seconds to ensure we don't
* encounter granularity issues).
* 15. Check file states. There should be none left.
*/
public void testAddStateAndPolicies() {
/* Create common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
IFile file = project.getFile("file.txt");
try {
project.create(getMonitor());
project.open(getMonitor());
file.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
/* set local history policies */
IWorkspaceDescription description = getWorkspace().getDescription();
// longevity set to 1 day
description.setFileStateLongevity(1000 * 3600 * 24);
// keep a max of 5 file states
description.setMaxFileStates(5);
// max size of file = 1 Mb
description.setMaxFileStateSize(1024 * 1024);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("0.1", e);
}
/* test max file states */
for (int i = 0; i < 8; i++) {
try {
ensureOutOfSync(file);
file.refreshLocal(IResource.DEPTH_ZERO, getMonitor());
file.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("1.0", e);
}
}
IFileState[] states = null;
try {
states = file.getHistory(getMonitor());
} catch (CoreException e) {
fail("1.01", e);
}
// Make sure we have 8 states as we haven't trimmed yet.
assertEquals("1.02", 8, states.length);
IFileState[] oldStates = states;
try {
getWorkspace().save(true, null);
states = file.getHistory(getMonitor());
} catch (CoreException e) {
fail("1.1", e);
}
// We added 8 states. Make sure we only have 5 (the max).
assertEquals("1.2", description.getMaxFileStates(), states.length);
// assert that states are in the correct order (newer ones first)
long lastModified = states[0].getModificationTime();
for (int i = 1; i < states.length; i++) {
assertTrue("1.3." + i, lastModified >= states[i].getModificationTime());
lastModified = states[i].getModificationTime();
}
// assert that the most recent states were preserved
for (int i = 0; i < states.length; i++) {
assertEquals("1.4." + i, oldStates[i], states[i]);
}
/* test max file state size */
description.setMaxFileStates(15);
// max size of file = 7 bytes
description.setMaxFileStateSize(7);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("2.0.0", e);
}
file = project.getFile("file1.txt");
try {
file.create(new ByteArrayInputStream(new byte[0]), true, getMonitor());
} catch (CoreException e) {
fail("2.0", e);
}
// Add 10 bytes to exceed the max file state size.
for (int i = 0; i < 10; i++) {
try {
file.appendContents(getContents("a"), true, true, getMonitor());
} catch (CoreException e) {
fail("2.1", e);
}
}
try {
getWorkspace().save(true, null);
states = file.getHistory(getMonitor());
// #states = size + 1 for the 0 byte length file to begin with.
for (int i = 0; i < states.length; i++) {
int bytesRead = numBytes(states[i].getContents());
assertTrue("2.2." + i, bytesRead <= description.getMaxFileStateSize());
}
} catch (CoreException e) {
fail("2.3", e);
}
/* test max file longevity */
// use the file of the first test
file = project.getFile("file.txt");
// 1 day
description.setFileStateLongevity(1000 * 3600 * 24);
description.setMaxFileStates(5);
// 1 Mb
description.setMaxFileStateSize(1024 * 1024);
// the description should be the same as the first test
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("3.0", e);
}
try {
states = file.getHistory(getMonitor());
// Make sure we have 5 states for file file.txt
assertEquals("3.1", description.getMaxFileStates(), states.length);
} catch (CoreException e) {
fail("3.2", e);
}
// change policies
// 10 seconds
description.setFileStateLongevity(1000 * 10);
// 1 Mb
description.setMaxFileStateSize(1024 * 1024);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("3.3", e);
}
try {
// sleep for more than 10 seconds (the granularity varies on
// some machines so we will sleep for 12 seconds)
Thread.sleep(1000 * 12);
} catch (InterruptedException e) {
fail("3.4", e);
}
try {
getWorkspace().save(true, null);
states = file.getHistory(getMonitor());
// The 5 states for file.txt should have exceeded their longevity
// and been removed. Make sure we have 0 states left.
assertEquals("3.5", 0, states.length);
} catch (CoreException e) {
fail("3.6", e);
}
}
public void testBug28238() {
// paths to mimic files in the workspace
IProject project = getWorkspace().getRoot().getProject("myproject");
IFolder folder = project.getFolder("myfolder");
IFolder destinationFolder = project.getFolder("myfolder2");
IFile file = folder.getFile("myfile.txt");
IFile destinationFile = destinationFolder.getFile(file.getName());
IHistoryStore store = ((Resource) getWorkspace().getRoot()).getLocalManager().getHistoryStore();
// location of the data on disk
IFileStore fileStore = getTempStore();
createFileInFileSystem(fileStore);
// add the data to the history store
FileInfo fileInfo = new FileInfo(file.getName());
fileInfo.setLastModified(System.currentTimeMillis());
store.addState(file.getFullPath(), fileStore, fileInfo, true);
IFileState[] states = store.getStates(file.getFullPath(), getMonitor());
assertEquals("2.0", 1, states.length);
// copy the data
store.copyHistory(folder, destinationFolder, true);
states = store.getStates(destinationFile.getFullPath(), getMonitor());
assertEquals("3.0", 1, states.length);
}
public void testBug28603() {
// paths to mimic files in the workspace
IProject project = getWorkspace().getRoot().getProject("myproject");
IFolder folder1 = project.getFolder("myfolder1");
IFolder folder2 = project.getFolder("myfolder2");
IFile file1 = folder1.getFile("myfile.txt");
IFile file2 = folder2.getFile(file1.getName());
ensureExistsInWorkspace(new IResource[] {project, folder1, folder2}, true);
try {
file1.create(getRandomContents(), IResource.FORCE, getMonitor());
file1.setContents(getRandomContents(), IResource.FORCE | IResource.KEEP_HISTORY, getMonitor());
file1.setContents(getRandomContents(), IResource.FORCE | IResource.KEEP_HISTORY, getMonitor());
file1.setContents(getRandomContents(), IResource.FORCE | IResource.KEEP_HISTORY, getMonitor());
setMaxFileStates(50);
} catch (CoreException e) {
fail("0.0", e);
}
int maxStates = ResourcesPlugin.getWorkspace().getDescription().getMaxFileStates();
IFileState[] states = null;
try {
states = file1.getHistory(getMonitor());
} catch (CoreException e) {
fail("1.0", e);
}
assertEquals("1.1", 3, states.length);
int currentStates = 3;
for (int i = 0; i < maxStates + 10; i++) {
try {
states = file1.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.0." + i, e);
}
assertEquals("2.1." + i + " file1 states", currentStates, states.length);
try {
file1.move(file2.getFullPath(), true, true, getMonitor());
} catch (CoreException e) {
fail("2.2." + i, e);
}
try {
states = file2.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.3." + i, e);
}
currentStates = currentStates < maxStates ? currentStates + 1 : maxStates;
assertEquals("2.4." + i + " file2 states", currentStates, states.length);
try {
file2.move(file1.getFullPath(), true, true, getMonitor());
} catch (CoreException e) {
fail("2.5." + i, e);
}
try {
states = file1.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.6." + i, e);
}
currentStates = currentStates < maxStates ? currentStates + 1 : maxStates;
assertEquals("2.7." + i + " file1 states", currentStates, states.length);
}
}
/*
* Test the functionality in store.clean() which is called to ensure
* the history store to ensure that the history store does not grow to
* unmanageable size. The policies currently in place include:
* - store only a maximum number of states for each file
* - do not store files greater than some stated size
* - consider history store information stale after some specified period
* of time and discard stale data
*
*/
public void testClean() {
/* Create common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
IFile file = project.getFile("file.txt");
try {
project.create(getMonitor());
project.open(getMonitor());
file.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
IHistoryStore store = ((Workspace) getWorkspace()).getFileSystemManager().getHistoryStore();
// get another copy for changes
IWorkspaceDescription description = getWorkspace().getDescription();
/* test max file states */
// 1 day
description.setFileStateLongevity(1000 * 3600 * 24);
// 500 states per file max.
description.setMaxFileStates(500);
// 1Mb max size
description.setMaxFileStateSize(1024 * 1024);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("0.1", e);
}
// Set up 8 file states for this file when 500 are allowed
for (int i = 0; i < 8; i++) {
try {
ensureOutOfSync(file);
file.refreshLocal(IResource.DEPTH_ZERO, getMonitor());
// try {
// Thread.sleep(5000); // necessary because of lastmodified granularity in some file systems
// } catch (InterruptedException e) {
// }
file.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("1.0", e);
}
}
// All 8 states should exist.
long oldLastModTimes[] = new long[8];
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.1", 8, states.length);
for (int i = 0; i < 8; i++) {
oldLastModTimes[i] = states[i].getModificationTime();
}
} catch (CoreException e) {
fail("1.2", e);
}
// Set max. number of file states to be 3
description.setMaxFileStates(3);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("2.0", e);
}
// Run 'clean' - should cause 5 of 8 states to be removed
store.clean(getMonitor());
// Restore max. number of states/file to 500
description.setMaxFileStates(500);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("2.2", e);
}
// Check to ensure only 3 states remain. Make sure these are the 3
// newer states.
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("2.3", 3, states.length);
// assert that states are in the correct order (newer ones first)
long lastModified = states[0].getModificationTime();
for (int i = 1; i < states.length; i++) {
assertTrue("2.4." + i, lastModified >= states[i].getModificationTime());
lastModified = states[i].getModificationTime();
}
// Make sure we kept the 3 newer states.
for (int i = 0; i < states.length; i++) {
assertTrue("2.5." + i, oldLastModTimes[i] == states[i].getModificationTime());
}
} catch (CoreException e) {
fail("2.6", e);
}
/* test max file longevity */
file = project.getFile("file.txt"); // use the file of the first test
description.setFileStateLongevity(1000 * 3600 * 24); // 1 day
description.setMaxFileStates(500);
description.setMaxFileStateSize(1024 * 1024); // 1 Mb
// the description should be the same as the first test
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("3.0", e);
}
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("3.1", 3, states.length);
} catch (CoreException e) {
fail("3.2", e);
}
// change policies
// 10 seconds
description.setFileStateLongevity(1000 * 10);
// 1 Mb
description.setMaxFileStateSize(1024 * 1024);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("4.0", e);
}
try {
// sleep for 12 seconds (must exceed 10 seconds). This should
// cause all 3 states for file.txt to be considered stale.
Thread.sleep(1000 * 12);
} catch (InterruptedException e) {
fail("4.1", e);
}
store.clean(getMonitor());
// change policies - restore to original values
// 1 day
description.setFileStateLongevity(1000 * 3600 * 24);
// 1 Mb
description.setMaxFileStateSize(1024 * 1024);
try {
getWorkspace().setDescription(description);
} catch (CoreException e) {
fail("5.0", e);
}
// Ensure we have no state information left. It should have been
// considered stale.
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("5.1", 0, states.length);
} catch (CoreException e) {
fail("5.2", e);
}
}
/**
* Copy case for History Store of folder when the local history is being
* copied.
*
* Scenario:
* 1. Create folder (folder1)
* 2. Create file "content 1"
* 3. Set new content "content 2"
* 4. Set new content "content 3"
* 5. Copy folder
* 6. Set new content to moved file "content 4"
* 7. Set new content to moved file "content 5"
*
* The original file should have two states available.
* But the copied file should have 4 states as it retains the states from
* before the copy took place as well.
*/
public void testCopyFolder() {
String[] contents = {"content1", "content2", "content3", "content4", "content5"};
// create common objects
IProject project = getWorkspace().getRoot().getProject("CopyFolderProject");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
IFile file = project.getFile("file1.txt");
IFolder folder = project.getFolder("folder1");
IFolder folder2 = project.getFolder("folder2");
file = folder.getFile("file1.txt");
try {
// Setup folder1 and file1.txt with some local history
folder.create(true, true, getMonitor());
file.create(getContents(contents[0]), true, getMonitor());
file.setContents(getContents(contents[1]), true, true, getMonitor());
file.setContents(getContents(contents[2]), true, true, getMonitor());
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
assertTrue("1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("1.2", compareContent(getContents(contents[0]), states[1].getContents()));
// Now do the move
folder.copy(folder2.getFullPath(), true, getMonitor());
// Check to make sure the file has been copied
IFile file2 = folder2.getFile("file1.txt");
assertTrue("1.3", file2.getFullPath().toString().endsWith("folder2/file1.txt"));
// Give the new (copied file) some new contents
file2.setContents(getContents(contents[3]), true, true, getMonitor());
file2.setContents(getContents(contents[4]), true, true, getMonitor());
// Check the local history of both files
states = file.getHistory(getMonitor());
assertEquals("2.0", 2, states.length);
assertTrue("2.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("2.2", compareContent(getContents(contents[0]), states[1].getContents()));
states = file2.getHistory(getMonitor());
assertEquals("2.3", 4, states.length);
assertTrue("2.4", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("2.5", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("2.6", compareContent(getContents(contents[1]), states[2].getContents()));
assertTrue("2.7", compareContent(getContents(contents[0]), states[3].getContents()));
} catch (CoreException e) {
fail("2.8", e);
}
try {
project.delete(true, getMonitor());
} catch (CoreException e) {
fail("3.0", e);
}
}
/*
* This test is designed to exercise the public API method
* HistoryStore.copyHistory(). The following tests will be performed:
* - give a null source path
* - give a null destination path
* - give the same path for source and destination
* - give an invalid source path but a valid destination path
* - give an invalid destination path but a valid source path
*/
public void testCopyHistoryFile() {
// Create a project, folder and file so we have some history store
// Should have a project that appears as follows:
// - project name TestCopyHistoryProject
// - has one folder called folder1
// - folder1 has one file called file1.txt
// - file1.txt was created with initial data "content1"
// - change data in file1.txt to be "content2"
// - change data in file1.txt to be "content3"
// As a result of the above, there should be 2 history store states for
// file1.txt (one with "contents1" and the other with "contents2".
String[] contents = {"content0", "content1", "content2", "content3", "content4"};
// create common objects
IProject project = getWorkspace().getRoot().getProject("TestCopyHistoryProject");
ensureExistsInWorkspace(project, true);
IFolder folder = project.getFolder("folder1");
IFile file = folder.getFile("file1.txt");
IFile file2 = folder.getFile("file2.txt");
try {
// Setup folder1 and file1.txt with some local history
folder.create(true, true, getMonitor());
file.create(getContents(contents[0]), true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.0", e);
}
file.setContents(getContents(contents[1]), true, true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.1", e);
}
file.setContents(getContents(contents[2]), true, true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.2", e);
}
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
assertTrue("1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("1.2", compareContent(getContents(contents[0]), states[1].getContents()));
file2.create(getContents(contents[3]), true, getMonitor());
file2.setContents(getContents(contents[4]), true, true, getMonitor());
} catch (CoreException e) {
fail("1.3", e);
}
// Run some tests with illegal arguments
LogListenerVerifier verifier = new LogListenerVerifier();
ILog log = ResourcesPlugin.getPlugin().getLog();
log.addLogListener(verifier);
// Test with null source and/or destination
IHistoryStore store = ((Resource) file).getLocalManager().getHistoryStore();
verifier.addExpected(IResourceStatus.INTERNAL_ERROR);
store.copyHistory(null, null, false);
try {
verifier.verify();
} catch (VerificationFailedException e) {
fail("1.4 ", e);
}
verifier.reset();
verifier.addExpected(IResourceStatus.INTERNAL_ERROR);
store.copyHistory(null, file2, false);
try {
verifier.verify();
} catch (VerificationFailedException e) {
fail("1.5 ", e);
}
verifier.reset();
verifier.addExpected(IResourceStatus.INTERNAL_ERROR);
store.copyHistory(file, null, false);
try {
verifier.verify();
} catch (VerificationFailedException e) {
fail("1.6 ", e);
}
verifier.reset();
// Try to copy the history store stuff to the same location
verifier.addExpected(IResourceStatus.INTERNAL_ERROR);
store.copyHistory(file, file, false);
try {
verifier.verify();
} catch (VerificationFailedException e) {
fail("1.7 ", e);
}
verifier.reset();
// Remember to remove the log listener now that we are done
// testing illegal arguments.
log.removeLogListener(verifier);
// Test a valid copy of a file
store.copyHistory(file, file2, false);
IFileState[] states = null;
try {
states = file2.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.3");
}
assertEquals("2.4", 3, states.length);
try {
assertTrue("2.5", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("2.6", compareContent(getContents(contents[1]), states[1].getContents()));
assertTrue("2.7", compareContent(getContents(contents[0]), states[2].getContents()));
} catch (CoreException e) {
fail("2.8");
}
}
public void testCopyHistoryFolder() {
String[] contents = {"content0", "content1", "content2", "content3", "content4"};
// create common objects
IProject project = getWorkspace().getRoot().getProject("TestCopyHistoryProject");
ensureExistsInWorkspace(project, true);
IFolder folder = project.getFolder("folder1");
IFolder folder2 = project.getFolder("folder2");
IFile file = folder.getFile("file1.txt");
IFile file2 = folder2.getFile("file1.txt");
try {
// Setup folder1 and file1.txt with some local history
folder.create(true, true, getMonitor());
file.create(getContents(contents[0]), true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.0", e);
}
file.setContents(getContents(contents[1]), true, true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.1", e);
}
file.setContents(getContents(contents[2]), true, true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.2", e);
}
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
assertTrue("1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("1.2", compareContent(getContents(contents[0]), states[1].getContents()));
folder2.create(true, true, getMonitor());
file2.create(getContents(contents[3]), true, getMonitor());
file2.setContents(getContents(contents[4]), true, true, getMonitor());
} catch (CoreException e) {
fail("1.9", e);
}
// Test a valid copy of a folder
IHistoryStore store = ((Resource) file).getLocalManager().getHistoryStore();
store.copyHistory(folder, folder2, false);
IFileState[] states = null;
try {
states = file2.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.3");
}
assertEquals("2.4", 3, states.length);
try {
assertTrue("2.5", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("2.6", compareContent(getContents(contents[1]), states[1].getContents()));
assertTrue("2.7", compareContent(getContents(contents[0]), states[2].getContents()));
} catch (CoreException e) {
fail("2.8");
}
}
public void testCopyHistoryProject() {
String[] contents = {"content0", "content1", "content2", "content3", "content4"};
// create common objects
IProject project = getWorkspace().getRoot().getProject("TestCopyHistoryProject");
IProject project2 = getWorkspace().getRoot().getProject("TestCopyHistoryProject2");
ensureExistsInWorkspace(new IResource[] {project, project2}, true);
IFolder folder = project.getFolder("folder1");
IFolder folder2 = project2.getFolder("folder1");
IFile file = folder.getFile("file1.txt");
IFile file2 = folder2.getFile("file1.txt");
try {
// Setup folder1 and file1.txt with some local history
folder.create(true, true, getMonitor());
file.create(getContents(contents[0]), true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.0", e);
}
file.setContents(getContents(contents[1]), true, true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.1", e);
}
file.setContents(getContents(contents[2]), true, true, getMonitor());
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
fail("0.2", e);
}
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
assertTrue("1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("1.2", compareContent(getContents(contents[0]), states[1].getContents()));
folder2.create(true, true, getMonitor());
file2.create(getContents(contents[3]), true, getMonitor());
file2.setContents(getContents(contents[4]), true, true, getMonitor());
} catch (CoreException e) {
fail("1.9", e);
}
// Test a valid copy of a folder
IHistoryStore store = ((Resource) file).getLocalManager().getHistoryStore();
store.copyHistory(project, project2, false);
IFileState[] states = null;
try {
states = file2.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.3");
}
assertEquals("2.4", 3, states.length);
try {
assertTrue("2.5", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("2.6", compareContent(getContents(contents[1]), states[1].getContents()));
assertTrue("2.7", compareContent(getContents(contents[0]), states[2].getContents()));
} catch (CoreException e) {
fail("2.8");
}
}
public void testDelete() {
// create common objects
IProject project = getWorkspace().getRoot().getProject("MyProject");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
// test file
IFile file = project.getFile("file.txt");
try {
file.create(getRandomContents(), true, getMonitor());
file.setContents(getRandomContents(), true, true, getMonitor());
file.setContents(getRandomContents(), true, true, getMonitor());
// Check to see that there are only 2 states before the deletion
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
// Delete the file. This should add a state to the history store.
file.delete(true, true, getMonitor());
states = file.getHistory(getMonitor());
assertEquals("1.1", 3, states.length);
// Re-create the file. This should not affect the history store.
file.create(getRandomContents(), true, getMonitor());
states = file.getHistory(getMonitor());
assertEquals("1.2", 3, states.length);
} catch (CoreException e) {
fail("1.20", e);
}
// test folder
IFolder folder = project.getFolder("folder");
// Make sure this has a different name as the history store information
// for the first 'file.txt' is likely still around.
file = folder.getFile("file2.txt");
try {
folder.create(true, true, getMonitor());
file.create(getRandomContents(), true, getMonitor());
file.setContents(getRandomContents(), true, true, getMonitor());
file.setContents(getRandomContents(), true, true, getMonitor());
// There should only be 2 history store entries.
IFileState[] states = file.getHistory(getMonitor());
assertEquals("2.0", 2, states.length);
// Delete the folder. This should cause one more history store entry.
folder.delete(true, true, getMonitor());
states = file.getHistory(getMonitor());
assertEquals("2.1", 3, states.length);
// Re-create the folder. There should be no new history store entries.
folder.create(true, true, getMonitor());
file.create(getRandomContents(), true, getMonitor());
states = file.getHistory(getMonitor());
assertEquals("2.2", 3, states.length);
} catch (CoreException e) {
fail("2.99", e);
}
try {
project.delete(true, getMonitor());
} catch (CoreException e) {
fail("20.0", e);
}
}
/**
* Test for existence of file states in the HistoryStore.
*/
public void testExists() throws Throwable {
/* Create common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
IFile file = project.getFile("removeAllStatesFile.txt");
try {
project.create(getMonitor());
project.open(getMonitor());
file.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
// Constant for the number of states we will create
final int ITERATIONS = 20;
/* Add multiple states for one file location. */
for (int i = 0; i < ITERATIONS; i++) {
try {
file.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("3.0." + i, e);
}
}
/* Valid Case: Test retrieved values. */
IFileState[] states = null;
try {
states = file.getHistory(getMonitor());
} catch (CoreException e) {
fail("5.0", e);
}
// Make sure we have ITERATIONS number of states
assertEquals("5.1", ITERATIONS, states.length);
// Make sure that each of these states really exists in the filesystem.
for (int i = 0; i < states.length; i++) {
assertTrue("5.2." + i, states[i].exists());
}
}
public void testFindDeleted() {
// create common objects
IWorkspaceRoot root = getWorkspace().getRoot();
IProject project = root.getProject("MyProject");
try {
project.create(getMonitor());
project.open(getMonitor());
IFile[] df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("0.1", 0, df.length);
} catch (CoreException e) {
fail("0.0", e);
}
// test that a deleted file can be found
IFile pfile = project.getFile("findDeletedFile.txt");
try {
// create and delete a file
pfile.create(getRandomContents(), true, getMonitor());
pfile.delete(true, true, getMonitor());
// the deleted file should show up as a deleted member of project
IFile[] df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("0.1", 1, df.length);
assertEquals("0.2", pfile, df[0]);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("0.3", 1, df.length);
assertEquals("0.4", pfile, df[0]);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("0.5", 0, df.length);
// the deleted file should show up as a deleted member of workspace root
df = root.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("0.5.1", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("0.5.2", 1, df.length);
assertEquals("0.5.3", pfile, df[0]);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("0.5.4", 0, df.length);
// recreate the file
pfile.create(getRandomContents(), true, getMonitor());
// the deleted file should no longer show up as a deleted member of project
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("0.6", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("0.7", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("0.8", 0, df.length);
// the deleted file should no longer show up as a deleted member of ws root
df = root.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("0.8.1", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("0.8.2", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("0.8.3", 0, df.length);
} catch (CoreException e) {
fail("0.00", e);
}
// scrub the project
try {
project.delete(true, getMonitor());
project.create(getMonitor());
project.open(getMonitor());
IFile[] df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("0.9", 0, df.length);
} catch (CoreException e) {
fail("0.10", e);
}
// test folder
IFolder folder = project.getFolder("folder");
IFile file = folder.getFile("filex.txt");
IFile folderAsFile = project.getFile(folder.getProjectRelativePath());
try {
// create and delete a file in a folder
folder.create(true, true, getMonitor());
file.create(getRandomContents(), true, getMonitor());
file.delete(true, true, getMonitor());
// the deleted file should show up as a deleted member
IFile[] df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("1.1", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("1.2", 1, df.length);
assertEquals("1.3", file, df[0]);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("1.4", 0, df.length);
// recreate the file
file.create(getRandomContents(), true, getMonitor());
// the deleted file should no longer show up as a deleted member
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("1.5", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("1.6", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("1.7", 0, df.length);
// deleting the folder should bring it back
folder.delete(true, true, getMonitor());
// the deleted file should show up as a deleted member of project
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("1.8", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("1.9", 1, df.length);
assertEquals("1.10", file, df[0]);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("1.11", 0, df.length);
// create and delete a file where the folder was
folderAsFile.create(getRandomContents(), true, getMonitor());
folderAsFile.delete(true, true, getMonitor());
folder.create(true, true, getMonitor());
// the deleted file should show up as a deleted member of folder
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("1.12", 1, df.length);
assertEquals("1.13", folderAsFile, df[0]);
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("1.14", 2, df.length);
List<IFile> dfList = Arrays.asList(df);
assertTrue("1.15", dfList.contains(file));
assertTrue("1.16", dfList.contains(folderAsFile));
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("1.17", 2, df.length);
dfList = Arrays.asList(df);
assertTrue("1.18", dfList.contains(file));
assertTrue("1.19", dfList.contains(folderAsFile));
} catch (CoreException e) {
fail("1.00", e);
}
// scrub the project
try {
project.delete(true, getMonitor());
project.create(getMonitor());
project.open(getMonitor());
IFile[] df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("1.50", 0, df.length);
} catch (CoreException e) {
fail("1.51", e);
}
// test a bunch of deletes
folder = project.getFolder("folder");
IFile file1 = folder.getFile("file1.txt");
IFile file2 = folder.getFile("file2.txt");
IFolder folder2 = folder.getFolder("folder2");
IFile file3 = folder2.getFile("file3.txt");
try {
// create and delete a file in a folder
folder.create(true, true, getMonitor());
folder2.create(true, true, getMonitor());
file1.create(getRandomContents(), true, getMonitor());
file2.create(getRandomContents(), true, getMonitor());
file3.create(getRandomContents(), true, getMonitor());
folder.delete(true, true, getMonitor());
// under root
IFile[] df = root.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("3.1", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("3.2", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("3.3", 3, df.length);
List<IFile> dfList = Arrays.asList(df);
assertTrue("3.3.1", dfList.contains(file1));
assertTrue("3.3.2", dfList.contains(file2));
assertTrue("3.3.3", dfList.contains(file3));
// under project
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("3.4", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("3.5", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("3.6", 3, df.length);
dfList = Arrays.asList(df);
assertTrue("3.6.1", dfList.contains(file1));
assertTrue("3.6.2", dfList.contains(file2));
assertTrue("3.6.3", dfList.contains(file3));
// under folder
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("3.7", 0, df.length);
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("3.8", 2, df.length);
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("3.9", 3, df.length);
// under folder2
df = folder2.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("3.10", 0, df.length);
df = folder2.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("3.11", 1, df.length);
df = folder2.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("3.12", 1, df.length);
} catch (CoreException e) {
fail("3.00", e);
}
try {
project.delete(true, getMonitor());
} catch (CoreException e) {
fail("3.5", e);
}
// once the project is gone, so is all the history for that project
try {
// under root
IFile[] df = root.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("4.1", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("4.2", 0, df.length);
df = root.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("4.3", 0, df.length);
// under project
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("4.4", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("4.5", 0, df.length);
df = project.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("4.6", 0, df.length);
// under folder
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("4.7", 0, df.length);
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("4.8", 0, df.length);
df = folder.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("4.9", 0, df.length);
// under folder2
df = folder2.findDeletedMembersWithHistory(IResource.DEPTH_ZERO, getMonitor());
assertEquals("4.10", 0, df.length);
df = folder2.findDeletedMembersWithHistory(IResource.DEPTH_ONE, getMonitor());
assertEquals("4.11", 0, df.length);
df = folder2.findDeletedMembersWithHistory(IResource.DEPTH_INFINITE, getMonitor());
assertEquals("4.12", 0, df.length);
} catch (CoreException e) {
fail("4.00", e);
}
}
/**
* Test for retrieving contents of files with states logged in the HistoryStore.
*/
public void testGetContents() throws Throwable {
final int ITERATIONS = 20;
/* Create common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
/* Create files. */
IFile file = project.getFile("getContentsFile.txt");
String contents = "This file has some contents in testGetContents.";
ensureExistsInWorkspace(file, contents);
IFile secondValidFile = project.getFile("secondGetContentsFile.txt");
contents = "A file with some other contents in testGetContents.";
ensureExistsInWorkspace(secondValidFile, contents);
IHistoryStore historyStore = ((Workspace) getWorkspace()).getFileSystemManager().getHistoryStore();
/* Simulated date -- Increment once for each edition added. */
long myLong = 0L;
/* Add multiple editions for one file location. */
for (int i = 0; i < ITERATIONS; i++, myLong++) {
FileInfo fileInfo = new FileInfo(file.getName());
fileInfo.setLastModified(myLong);
historyStore.addState(file.getFullPath(), ((Resource) file).getStore(), fileInfo, true);
try {
contents = "This file has some contents in testGetContents.";
InputStream is = new ByteArrayInputStream(contents.getBytes());
createFileInFileSystem(file.getLocation(), is);
file.refreshLocal(IResource.DEPTH_INFINITE, null);
} catch (CoreException e) {
fail("1.1." + i, e);
}
}
/* Add multiple editions for second file location. */
for (int i = 0; i < ITERATIONS; i++, myLong++) {
FileInfo fileInfo = new FileInfo(file.getName());
fileInfo.setLastModified(myLong);
historyStore.addState(secondValidFile.getFullPath(), ((Resource) secondValidFile).getStore(), fileInfo, true);
try {
contents = "A file with some other contents in testGetContents.";
InputStream is = new ByteArrayInputStream(contents.getBytes());
createFileInFileSystem(secondValidFile.getLocation(), is);
secondValidFile.refreshLocal(IResource.DEPTH_INFINITE, null);
} catch (CoreException e) {
fail("2.1." + i, e);
}
}
/* Ensure contents of file and retrieved resource are identical.
Does not check timestamps. Timestamp checks are performed in a separate test. */
DataInputStream inFile = null;
DataInputStream inContents = null;
IFileState[] stateArray = null;
stateArray = historyStore.getStates(file.getFullPath(), getMonitor());
for (int i = 0; i < stateArray.length; i++, myLong++) {
inFile = new DataInputStream(file.getContents(false));
try {
inContents = new DataInputStream(historyStore.getContents(stateArray[i]));
} catch (CoreException e) {
fail("3.1." + i, e);
}
if (!compareContent(inFile, inContents)) {
fail("3.2." + i + " No match, files are not identical.");
}
}
stateArray = historyStore.getStates(secondValidFile.getFullPath(), getMonitor());
for (int i = 0; i < stateArray.length; i++, myLong++) {
inFile = new DataInputStream(secondValidFile.getContents(false));
try {
inContents = new DataInputStream(historyStore.getContents(stateArray[i]));
} catch (CoreException e) {
fail("4.1." + i, e);
}
if (!compareContent(inFile, inContents)) {
fail("4.2." + i + " No match, files are not identical.");
}
}
/* Test getting an invalid file state. */
for (int i = 0; i < ITERATIONS; i++) {
// Create bogus FileState using invalid uuid.
try {
InputStream in = historyStore.getContents(new FileState(historyStore, Path.ROOT, myLong, new UniversalUniqueIdentifier()));
in.close();
fail("6." + i + " Edition should be invalid.");
} catch (CoreException e) {
// expected
}
}
/* Test verification using null file state. */
for (int i = 0; i < ITERATIONS; i++) {
try {
historyStore.getContents(null);
fail("7." + i + " Null edition should be invalid.");
} catch (RuntimeException e) {
// expected
}
}
}
public void testModifiedStamp() {
/* Initialize common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
IFile file = project.getFile("file");
try {
file.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("1.0", e);
}
IFileState[] history = null;
try {
history = file.getHistory(getMonitor());
} catch (CoreException e) {
fail("1.1", e);
}
// no history yet
assertEquals("1.2", 0, history.length);
// save the file's current time stamp - it will be remembered in the file state
long fileTimeStamp = file.getLocalTimeStamp();
try {
file.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("2.0", e);
}
try {
history = file.getHistory(getMonitor());
} catch (CoreException e) {
fail("2.1", e);
}
// one state in the history
assertEquals("2.2", 1, history.length);
// the timestamp in the state should match the previous file's timestamp
assertEquals("3.0", fileTimeStamp, history[0].getModificationTime());
}
/**
* Move case for History Store of folder when the local history is being
* copied.
*
* Scenario:
* 1. Create folder (folder1)
* 2. Create file "content 1"
* 3. Set new content "content 2"
* 4. Set new content "content 3"
* 5. Move folder
* 6. Set new content to moved file "content 4"
* 7. Set new content to moved file "content 5"
*
* The original file should have two states available.
* But the moved file should have 4 states as it retains the states from
* before the move took place as well.
*/
public void testMoveFolder() {
String[] contents = {"content1", "content2", "content3", "content4", "content5"};
// create common objects
IProject project = getWorkspace().getRoot().getProject("MyProject");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
IFile file = project.getFile("file1.txt");
IFolder folder = project.getFolder("folder1");
IFolder folder2 = project.getFolder("folder2");
file = folder.getFile("file1.txt");
try {
// Setup folder1 and file1.txt with some local history
folder.create(true, true, getMonitor());
file.create(getContents(contents[0]), true, getMonitor());
file.setContents(getContents(contents[1]), true, true, getMonitor());
file.setContents(getContents(contents[2]), true, true, getMonitor());
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
assertTrue("1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("1.2", compareContent(getContents(contents[0]), states[1].getContents()));
// Now do the move
folder.move(folder2.getFullPath(), true, getMonitor());
// Check to make sure the file has been moved
IFile file2 = folder2.getFile("file1.txt");
assertTrue("1.3", file2.getFullPath().toString().endsWith("folder2/file1.txt"));
// Give the new (moved file) some new contents
file2.setContents(getContents(contents[3]), true, true, getMonitor());
file2.setContents(getContents(contents[4]), true, true, getMonitor());
// Check the local history of both files
states = file.getHistory(getMonitor());
assertEquals("2.0", 2, states.length);
assertTrue("2.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("2.2", compareContent(getContents(contents[0]), states[1].getContents()));
states = file2.getHistory(getMonitor());
assertEquals("2.3", 4, states.length);
assertTrue("2.4", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("2.5", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("2.6", compareContent(getContents(contents[1]), states[2].getContents()));
assertTrue("2.7", compareContent(getContents(contents[0]), states[3].getContents()));
} catch (CoreException e) {
fail("2.8", e);
}
try {
project.delete(true, getMonitor());
} catch (CoreException e) {
fail("3.0", e);
}
}
/**
* Move case for History Store of project. Note that local history is
* NOT copied for a project move.
*
* Scenario:
* 1. Create folder (folder1)
* 2. Create file "content 1"
* 2. Set new content "content 2"
* 3. Set new content "content 3"
* 4. Copy folder
* 5. Set new content to moved file "content 4"
* 6. Set new content to moved file "content 5"
*
* The original file should have two states available.
* But the copied file should have 4 states as it retains the states from
* before the copy took place as well.
*/
public void testMoveProject() {
String[] contents = {"content1", "content2", "content3", "content4", "content5"};
// create common objects
IProject project = getWorkspace().getRoot().getProject("MoveProjectProject");
IProject project2 = getWorkspace().getRoot().getProject("SecondMoveProjectProject");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
IFile file = project.getFile("file1.txt");
IFolder folder = project.getFolder("folder1");
file = folder.getFile("file1.txt");
try {
// Setup folder1 and file1.txt with some local history
folder.create(true, true, getMonitor());
file.create(getContents(contents[0]), true, getMonitor());
file.setContents(getContents(contents[1]), true, true, getMonitor());
file.setContents(getContents(contents[2]), true, true, getMonitor());
IFileState[] states = file.getHistory(getMonitor());
assertEquals("1.0", 2, states.length);
assertTrue("1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("1.2", compareContent(getContents(contents[0]), states[1].getContents()));
// Now do the move
project.move(new Path("SecondMoveProjectProject"), true, getMonitor());
// Check to make sure the file has been moved
IFile file2 = project2.getFile("folder1/file1.txt");
assertTrue("1.3", file2.getFullPath().toString().endsWith("SecondMoveProjectProject/folder1/file1.txt"));
// Give the new (copied file) some new contents
file2.setContents(getContents(contents[3]), true, true, getMonitor());
file2.setContents(getContents(contents[4]), true, true, getMonitor());
// Check the local history of both files
states = file.getHistory(getMonitor());
// original file should not remember history when project is moved
assertEquals("2.0", 0, states.length);
states = file2.getHistory(getMonitor());
assertEquals("2.3", 4, states.length);
assertTrue("2.4", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("2.5", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("2.6", compareContent(getContents(contents[1]), states[2].getContents()));
assertTrue("2.7", compareContent(getContents(contents[0]), states[3].getContents()));
} catch (CoreException e) {
fail("2.9", e);
}
try {
project.delete(true, getMonitor());
} catch (CoreException e) {
fail("3.0", e);
}
}
public void testRemoveAll() {
/* Create common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
IFile file = project.getFile("removeAllStatesFile.txt");
try {
project.create(getMonitor());
project.open(getMonitor());
file.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
final int ITERATIONS = 20;
/* test remove in a file */
for (int i = 0; i < ITERATIONS; i++) {
try {
file.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("3.0." + i, e);
}
}
/* Valid Case: Ensure correct number of states available. */
IFileState[] states = null;
try {
states = file.getHistory(getMonitor());
} catch (CoreException e) {
fail("4.0", e);
}
assertEquals("4.1", ITERATIONS, states.length);
/* Remove all states, and verify that no states remain. */
try {
file.clearHistory(getMonitor());
states = file.getHistory(getMonitor());
assertEquals("5.0", 0, states.length);
} catch (CoreException e) {
fail("5.1", e);
}
/* test remove in a folder -- make sure it does not affect other resources' states*/
IFolder folder = project.getFolder("folder");
IFile anotherOne = folder.getFile("anotherOne");
try {
folder.create(true, true, getMonitor());
anotherOne.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("6.0", e);
}
for (int i = 0; i < ITERATIONS; i++) {
try {
file.setContents(getRandomContents(), true, true, getMonitor());
anotherOne.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("6.1." + i, e);
}
}
try {
states = file.getHistory(getMonitor());
assertEquals("6.2", ITERATIONS, states.length);
states = anotherOne.getHistory(getMonitor());
assertEquals("6.3", ITERATIONS, states.length);
} catch (CoreException e) {
fail("6.4", e);
}
/* Remove all states, and verify that no states remain. */
try {
project.clearHistory(getMonitor());
states = file.getHistory(getMonitor());
assertEquals("7.0", 0, states.length);
states = anotherOne.getHistory(getMonitor());
assertEquals("7.1", 0, states.length);
} catch (CoreException e) {
fail("7.2", e);
}
/* test remove in a folder -- make sure it does not affect other resources' states*/
IFile aaa = project.getFile("aaa");
IFolder bbb = project.getFolder("bbb");
anotherOne = bbb.getFile("anotherOne");
IFile ccc = project.getFile("ccc");
try {
bbb.create(true, true, getMonitor());
anotherOne.create(getRandomContents(), true, getMonitor());
aaa.create(getRandomContents(), true, getMonitor());
ccc.create(getRandomContents(), true, getMonitor());
} catch (CoreException e) {
fail("8.0", e);
}
for (int i = 0; i < ITERATIONS; i++) {
try {
anotherOne.setContents(getRandomContents(), true, true, getMonitor());
aaa.setContents(getRandomContents(), true, true, getMonitor());
ccc.setContents(getRandomContents(), true, true, getMonitor());
} catch (CoreException e) {
fail("8.1." + i, e);
}
}
try {
states = anotherOne.getHistory(getMonitor());
assertEquals("8.3", ITERATIONS, states.length);
states = aaa.getHistory(getMonitor());
assertEquals("8.4", ITERATIONS, states.length);
states = ccc.getHistory(getMonitor());
assertEquals("8.5", ITERATIONS, states.length);
} catch (CoreException e) {
fail("8.6", e);
}
/* Remove all states, and verify that no states remain. aaa and ccc should not be affected. */
try {
bbb.clearHistory(getMonitor());
states = anotherOne.getHistory(getMonitor());
assertEquals("9.1", 0, states.length);
states = aaa.getHistory(getMonitor());
assertEquals("9.2", ITERATIONS, states.length);
states = ccc.getHistory(getMonitor());
assertEquals("9.3", ITERATIONS, states.length);
} catch (CoreException e) {
fail("9.4", e);
}
}
/**
* Simple copy case for History Store when the local history is being
* copied.
*
* Scenario:
* 1. Create file "content 1"
* 2. Set new content "content 2"
* 3. Set new content "content 3"
* 4. Move file
* 5. Set new content to copied file "content 4"
* 6. Set new content to copied file "content 5"
*
* The original file should have two states available.
* But the copied file should have 4 states as it retains the states from
* before the copy took place as well.
*/
public void testSimpleCopy() {
/* Initialize common objects. */
IProject project = getWorkspace().getRoot().getProject("SimpleCopyProject");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
String[] contents = {"content1", "content2", "content3", "content4", "content5"};
IFile file = project.getFile("simpleCopyFileWithHistoryCopy");
IFile copyFile = project.getFile("copyOfSimpleCopyFileWithHistoryCopy");
/* Create first file. */
try {
file.create(getContents(contents[0]), true, null);
} catch (CoreException e) {
fail("1.2", e);
}
/* Set new contents on first file. Should add two entries to the history store. */
try {
file.setContents(getContents(contents[1]), true, true, null);
file.setContents(getContents(contents[2]), true, true, null);
} catch (CoreException e) {
fail("2.0", e);
}
/* Copy first file to the second. Second file should have no history. */
try {
file.copy(copyFile.getFullPath(), true, null);
} catch (CoreException e) {
fail("3.0", e);
}
/* Check history for both files. */
try {
IFileState[] states = file.getHistory(null);
assertEquals("4.0", 2, states.length);
states = copyFile.getHistory(null);
assertEquals("4.1", 2, states.length);
} catch (CoreException e) {
fail("4.2", e);
}
/* Set new contents on second file. Should add two entries to the history store. */
try {
copyFile.setContents(getContents(contents[3]), true, true, null);
copyFile.setContents(getContents(contents[4]), true, true, null);
} catch (CoreException e) {
fail("5.0", e);
}
/* Check history for both files. */
try {
// Check log for original file.
IFileState[] states = file.getHistory(null);
assertEquals("6.0", 2, states.length);
assertTrue("6.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("6.2", compareContent(getContents(contents[0]), states[1].getContents()));
// Check log for copy.
states = copyFile.getHistory(null);
assertEquals("6.3", 4, states.length);
assertTrue("6.4", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("6.5", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("6.6", compareContent(getContents(contents[1]), states[2].getContents()));
assertTrue("6.7", compareContent(getContents(contents[0]), states[3].getContents()));
} catch (CoreException e) {
fail("6.8", e);
}
}
/**
* Simple move case for History Store when the local history is being
* copied.
*
* Scenario:
* 1. Create file "content 1"
* 2. Set new content "content 2"
* 3. Set new content "content 3"
* 4. Move file
* 5. Set new content to moved file "content 4"
* 6. Set new content to moved file "content 5"
*
* The original file should have two states available.
* But the moved file should have 4 states as it retains the states from
* before the move took place as well.
*/
public void testSimpleMove() {
/* Initialize common objects. */
IProject project = getWorkspace().getRoot().getProject("SimpleMoveProject");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
String[] contents = {"content1", "content2", "content3", "content4", "content5"};
IFile file = project.getFile("simpleMoveFileWithCopy");
IFile moveFile = project.getFile("copyOfSimpleMoveFileWithCopy");
/* Create first file. */
try {
file.create(getContents(contents[0]), true, null);
} catch (CoreException e) {
fail("1.2", e);
}
/* Set new contents on source file. Should add two entries to the history store. */
try {
file.setContents(getContents(contents[1]), true, true, null);
file.setContents(getContents(contents[2]), true, true, null);
} catch (CoreException e) {
fail("2.0", e);
}
/* Move source file to second location.
* Moved files should have the history of the original file.
*/
try {
file.move(moveFile.getFullPath(), true, null);
} catch (CoreException e) {
fail("3.0", e);
}
/* Check history for both files. */
try {
IFileState[] states = file.getHistory(null);
assertEquals("4.0", 2, states.length);
states = moveFile.getHistory(null);
assertEquals("4.1", 2, states.length);
} catch (CoreException e) {
fail("4.2", e);
}
/* Set new contents on moved file. Should add two entries to the history store. */
try {
moveFile.setContents(getContents(contents[3]), true, true, null);
moveFile.setContents(getContents(contents[4]), true, true, null);
} catch (CoreException e) {
fail("5.0", e);
}
/* Check history for both files. */
try {
// Check log for original file.
IFileState[] states = file.getHistory(null);
assertEquals("6.0", 2, states.length);
assertTrue("6.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("6.2", compareContent(getContents(contents[0]), states[1].getContents()));
// Check log for moved file.
states = moveFile.getHistory(null);
assertEquals("6.3", 4, states.length);
assertTrue("6.4", compareContent(getContents(contents[3]), states[0].getContents()));
assertTrue("6.5", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("6.6", compareContent(getContents(contents[1]), states[2].getContents()));
assertTrue("6.7", compareContent(getContents(contents[0]), states[3].getContents()));
} catch (CoreException e) {
fail("6.8", e);
}
}
/**
* Simple use case for History Store.
*
* Scenario: # Editions
* 1. Create file "content 1" 0
* 2. Set new content "content 2" 1
* 3. Set new content "content 3" 2
* 4. Delete file 3
* 5. Roll back to first version "content 1" 3
* 6. Set new content "content 2" 4
* 7. Roll back to third version "content 3" 5
*/
public void testSimpleUse() {
/* Initialize common objects. */
IProject project = getWorkspace().getRoot().getProject("Project");
try {
project.create(getMonitor());
project.open(getMonitor());
} catch (CoreException e) {
fail("0.0", e);
}
String[] contents = {"content1", "content2", "content3"};
IFile file = project.getFile("file");
/* Create the file. */
try {
file.create(getContents(contents[0]), true, getMonitor());
} catch (CoreException e) {
fail("1.0", e);
}
/* Set new contents on the file. Should add two entries to the store. */
try {
for (int i = 0; i < 2; i++) {
file.setContents(getContents(contents[i + 1]), true, true, getMonitor());
}
} catch (CoreException e) {
fail("2.0", e);
}
/* Ensure two entries are available for the file, and that content matches. */
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("3.0", 2, states.length);
assertTrue("3.1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("3.1.2", compareContent(getContents(contents[0]), states[1].getContents()));
} catch (CoreException e) {
fail("3.2", e);
}
/* Delete the file. Should add an entry to the store. */
try {
file.delete(true, true, getMonitor());
} catch (CoreException e) {
fail("4.0", e);
}
/* Ensure three entries are available for the file, and that content matches. */
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("5.0", 3, states.length);
assertTrue("5.1.1", compareContent(getContents(contents[2]), states[0].getContents()));
assertTrue("5.1.2", compareContent(getContents(contents[1]), states[1].getContents()));
assertTrue("5.1.3", compareContent(getContents(contents[0]), states[2].getContents()));
} catch (CoreException e) {
fail("5.2", e);
}
/* Roll file back to first version, and ensure that content matches. */
try {
IFileState[] states = file.getHistory(getMonitor());
// Create the file with the contents from one of the states.
// Won't add another entry to the store.
file.create(states[0].getContents(), false, getMonitor());
// Check history store.
states = file.getHistory(getMonitor());
assertEquals("6.0", 3, states.length);
assertTrue("6.1.1", compareContent(getContents(contents[2]), states[0].getContents()));
assertTrue("6.1.2", compareContent(getContents(contents[1]), states[1].getContents()));
assertTrue("6.1.3", compareContent(getContents(contents[0]), states[2].getContents()));
// Check file contents.
assertTrue("6.2", compareContent(getContents(contents[2]), file.getContents(false)));
} catch (CoreException e) {
fail("6.3", e);
}
/* Set new contents on the file. Should add an entry to the history store. */
try {
file.setContents(getContents(contents[1]), true, true, null);
} catch (CoreException e) {
fail("7.0", e);
}
/* Ensure four entries are available for the file, and that entries match. */
try {
IFileState[] states = file.getHistory(getMonitor());
assertEquals("8.0", 4, states.length);
assertTrue("8.1.1", compareContent(getContents(contents[2]), states[0].getContents()));
assertTrue("8.1.2", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("8.1.3", compareContent(getContents(contents[1]), states[2].getContents()));
assertTrue("8.1.4", compareContent(getContents(contents[0]), states[3].getContents()));
} catch (CoreException e) {
fail("8.2", e);
}
/* Roll file back to third version, and ensure that content matches. */
try {
IFileState[] states = file.getHistory(getMonitor());
// Will add another entry to log.
file.setContents(states[2], true, true, getMonitor());
// Check history log.
states = file.getHistory(getMonitor());
assertEquals("9.0", 5, states.length);
assertTrue("9.1.1", compareContent(getContents(contents[1]), states[0].getContents()));
assertTrue("9.1.2", compareContent(getContents(contents[2]), states[1].getContents()));
assertTrue("9.1.3", compareContent(getContents(contents[2]), states[2].getContents()));
assertTrue("9.1.4", compareContent(getContents(contents[1]), states[3].getContents()));
assertTrue("9.1.5", compareContent(getContents(contents[0]), states[4].getContents()));
// Check file contents.
assertTrue("9.2", compareContent(getContents(contents[1]), file.getContents(false)));
} catch (CoreException e) {
fail("9.3", e);
}
}
}