Bug 468047 - ESLocalProjectImpl.delete does not delete all files

Change-Id: Ib6123160cffda6383b75f15dd1a18c30be113f0a
diff --git a/bundles/org.eclipse.emf.emfstore.client/src/org/eclipse/emf/emfstore/internal/client/model/impl/ProjectSpaceBase.java b/bundles/org.eclipse.emf.emfstore.client/src/org/eclipse/emf/emfstore/internal/client/model/impl/ProjectSpaceBase.java
index 5bea09e..4dc85d1 100644
--- a/bundles/org.eclipse.emf.emfstore.client/src/org/eclipse/emf/emfstore/internal/client/model/impl/ProjectSpaceBase.java
+++ b/bundles/org.eclipse.emf.emfstore.client/src/org/eclipse/emf/emfstore/internal/client/model/impl/ProjectSpaceBase.java
@@ -5,7 +5,7 @@
  * 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:
  * Otto von Wesendonk, Edgar Mueller, Maximilian Koegel - initial API and implementation
  * Johannes Faltermeier - adaptions for independent storage
@@ -107,6 +107,7 @@
 import org.eclipse.emf.emfstore.internal.server.model.versioning.VersionSpec;
 import org.eclipse.emf.emfstore.internal.server.model.versioning.VersioningFactory;
 import org.eclipse.emf.emfstore.internal.server.model.versioning.Versions;
+import org.eclipse.emf.emfstore.internal.server.model.versioning.impl.FileBasedChangePackageImpl;
 import org.eclipse.emf.emfstore.internal.server.model.versioning.impl.persistent.ChangePackageContainer;
 import org.eclipse.emf.emfstore.internal.server.model.versioning.operations.AbstractOperation;
 import org.eclipse.emf.emfstore.internal.server.model.versioning.operations.CreateDeleteOperation;
@@ -118,12 +119,12 @@
 
 /**
  * Project space base class that contains custom user methods.
- * 
+ *
  * @author koegel
  * @author wesendon
  * @author emueller
  * @author jfaltermeier
- * 
+ *
  */
 public abstract class ProjectSpaceBase extends IdentifiableElementImpl
 	implements ProjectSpace, ESLoginObserver, ESDisposable, ChangePackageContainer {
@@ -162,7 +163,7 @@
 	 * This may be used to provide a context while applying operations on a
 	 * {@link org.eclipse.emf.emfstore.client.ESLocalProject}.
 	 * </p>
-	 * 
+	 *
 	 * @param runnableContext
 	 *            the runnable context to be set
 	 */
@@ -179,7 +180,7 @@
 
 	/**
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#addFile(java.io.File)
 	 */
 	public FileIdentifier addFile(File file) throws FileTransferException {
@@ -187,9 +188,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#addFile(java.io.File, java.lang.String)
 	 */
 	public FileIdentifier addFile(File file, String fileIdentifier) throws FileTransferException {
@@ -197,9 +198,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#addOperations(java.util.List)
 	 */
 	public void addOperations(List<? extends AbstractOperation> operations) {
@@ -219,9 +220,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#addTag(org.eclipse.emf.emfstore.internal.server.model.versioning.PrimaryVersionSpec,
 	 *      org.eclipse.emf.emfstore.internal.server.model.versioning.TagVersionSpec)
 	 */
@@ -233,7 +234,7 @@
 	/**
 	 * Helper method which applies merged changes on the ProjectSpace. This
 	 * method is used by merge mechanisms in update as well as branch merging.
-	 * 
+	 *
 	 * @param baseSpec
 	 *            new base version
 	 * @param incomingChangePackages
@@ -244,7 +245,7 @@
 	 *            an {@link IProgressMonitor} to inform about the progress of the UpdateCallback in case it is called
 	 * @param runChecksumCheckOnBaseSpec
 	 *            whether the checksum check is performed while applying the changes
-	 * 
+	 *
 	 * @throws ESException in case the checksum comparison failed and the activated IChecksumErrorHandler
 	 *             also failed
 	 */
@@ -354,13 +355,13 @@
 	/**
 	 * Applies a list of operations to the project. The change tracking will be
 	 * stopped meanwhile.
-	 * 
-	 * 
+	 *
+	 *
 	 * @param operations
 	 *            the list of operations to be applied upon the project space
 	 * @param addOperations
 	 *            whether the operations should be saved in project space
-	 * 
+	 *
 	 */
 	public void applyOperations(Iterable<AbstractOperation> operations, boolean addOperations) {
 		executeRunnable(new ApplyOperationsRunnable(this, operations, addOperations));
@@ -369,11 +370,11 @@
 	/**
 	 * Applies a list of operations to the project. The change tracking will be
 	 * stopped meanwhile.
-	 * 
-	 * 
+	 *
+	 *
 	 * @param operations
 	 *            the list of operations to be applied upon the project space
-	 * 
+	 *
 	 */
 	public void applyOperationsWithRerecording(Iterable<AbstractOperation> operations) {
 		executeRunnable(new ApplyOperationsAndRecordRunnable(this, operations));
@@ -382,7 +383,7 @@
 	/**
 	 * Executes a given {@link Runnable} in the context of this {@link ProjectSpace}.<br>
 	 * The {@link Runnable} usually modifies the Project contained in the {@link ProjectSpace}.
-	 * 
+	 *
 	 * @param runnable
 	 *            the {@link Runnable} to be executed in the context of this {@link ProjectSpace}
 	 */
@@ -392,7 +393,7 @@
 
 	/**
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#beginCompositeOperation()
 	 */
 	public CompositeOperationHandle beginCompositeOperation() {
@@ -410,9 +411,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#commit(org.eclipse.core.runtime.IProgressMonitor)
 	 */
 	public PrimaryVersionSpec commit(IProgressMonitor monitor) throws ESException {
@@ -420,9 +421,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#commit(java.lang.String,
 	 *      org.eclipse.emf.emfstore.client.callbacks.ESCommitCallback, org.eclipse.core.runtime.IProgressMonitor)
 	 */
@@ -441,9 +442,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#exportLocalChanges(java.io.File,
 	 *      org.eclipse.core.runtime.IProgressMonitor)
 	 */
@@ -452,9 +453,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#exportLocalChanges(java.io.File)
 	 */
 	public void exportLocalChanges(File file) throws IOException {
@@ -462,9 +463,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#exportProject(java.io.File,
 	 *      org.eclipse.core.runtime.IProgressMonitor)
 	 */
@@ -473,9 +474,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#exportProject(java.io.File)
 	 */
 	public void exportProject(File file) throws IOException {
@@ -483,9 +484,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getChanges(org.eclipse.emf.emfstore.internal.server.model.versioning.VersionSpec,
 	 *      org.eclipse.emf.emfstore.internal.server.model.versioning.VersionSpec)
 	 */
@@ -500,9 +501,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getFile(org.eclipse.emf.emfstore.internal.server.model.FileIdentifier)
 	 */
 	public FileDownloadStatus getFile(FileIdentifier fileIdentifier) throws FileTransferException {
@@ -510,9 +511,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getFileInfo(org.eclipse.emf.emfstore.internal.server.model.FileIdentifier)
 	 */
 	public FileInformation getFileInfo(FileIdentifier fileIdentifier) {
@@ -520,9 +521,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getLocalChangePackage(boolean)
 	 */
 	public AbstractChangePackage getLocalChangePackage(boolean canonize) {
@@ -554,7 +555,7 @@
 
 	/**
 	 * Get the current notification recorder.
-	 * 
+	 *
 	 * @return the recorder
 	 */
 	public NotificationRecorder getNotificationRecorder() {
@@ -562,9 +563,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getOperationManager()
 	 */
 	public OperationManager getOperationManager() {
@@ -572,9 +573,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getProjectInfo()
 	 */
 	public ProjectInfo getProjectInfo() {
@@ -589,7 +590,7 @@
 
 	/**
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getPropertyManager()
 	 */
 	public PropertyManager getPropertyManager() {
@@ -617,7 +618,7 @@
 
 	/**
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#importLocalChanges(java.lang.String)
 	 */
 	public void importLocalChanges(String fileName) throws IOException {
@@ -754,7 +755,7 @@
 
 	/**
 	 * Returns the file transfer manager.
-	 * 
+	 *
 	 * @return the file transfer manager
 	 */
 	public FileTransferManager getFileTransferManager() {
@@ -762,9 +763,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#initResources(org.eclipse.emf.ecore.resource.ResourceSet)
 	 */
 	public void initResources(ResourceSet resourceSet) {
@@ -810,9 +811,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#delete(org.eclipse.core.runtime.IProgressMonitor)
 	 */
 	public void delete(IProgressMonitor monitor) throws IOException {
@@ -825,20 +826,25 @@
 		// remove resources from resource set and delete them
 		deleteResource(getProject().eResource());
 		deleteResource(eResource());
-		// TODO: LCP - no change package in memory anymore, hence no resource available
-		// deleteResource(getLocalChangePackageOLD().eResource());
-		final URI localChangePackageUri = ESClientURIUtil.createOperationsURI(this);
-		final URI normalizedUri = getResourceSet().getURIConverter().normalize(localChangePackageUri);
-		final String fileString = normalizedUri.toFileString();
-		final File operationsFile = new File(fileString);
 
-		operationsFile.delete();
-		boolean isDeleted = !operationsFile.exists();
-		int retries = 0;
-		while (!isDeleted && retries < 3) {
+		if (FileBasedChangePackage.class.isInstance(getLocalChangePackage())) {
+			FileBasedChangePackageImpl.class.cast(getLocalChangePackage()).delete();
+		} else {
+			// LCP - no change package in memory anymore, hence no resource available
+			final URI localChangePackageUri = ESClientURIUtil.createOperationsURI(this);
+			final URI normalizedUri = getResourceSet().getURIConverter().normalize(localChangePackageUri);
+			final String fileString = normalizedUri.toFileString();
+			final File operationsFile = new File(fileString);
+
 			operationsFile.delete();
-			isDeleted = !operationsFile.exists();
-			retries++;
+
+			boolean isDeleted = !operationsFile.exists();
+			int retries = 0;
+			while (!isDeleted && retries < 3) {
+				operationsFile.delete();
+				isDeleted = !operationsFile.exists();
+				retries++;
+			}
 		}
 
 		// TODO: remove project space from workspace, this is not the case if delete
@@ -856,10 +862,10 @@
 
 	/**
 	 * Returns the {@link ECrossReferenceAdapter}, if available.
-	 * 
+	 *
 	 * @param modelElement
 	 *            the model element for which to find inverse cross references
-	 * 
+	 *
 	 * @return the {@link ECrossReferenceAdapter}
 	 */
 	public Collection<Setting> findInverseCrossReferences(EObject modelElement) {
@@ -871,9 +877,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getResourceSet()
 	 */
 	public ResourceSet getResourceSet() {
@@ -881,9 +887,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#setResourceSet(org.eclipse.emf.ecore.resource.ResourceSet)
 	 */
 	public void setResourceSet(ResourceSet resourceSet) {
@@ -891,9 +897,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#isTransient()
 	 */
 	public boolean isTransient() {
@@ -901,9 +907,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#isUpdated()
 	 */
 	public boolean isUpdated() throws ESException {
@@ -932,7 +938,7 @@
 
 	/**
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#makeTransient()
 	 */
 	public void makeTransient() {
@@ -985,9 +991,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#mergeResolvedConflicts(org.eclipse.emf.emfstore.internal.server.conflictDetection.ChangeConflictSet,
 	 *      java.util.List, java.util.List)
 	 */
@@ -1095,9 +1101,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#getBranches()
 	 */
 	public List<BranchInfo> getBranches() throws ESException {
@@ -1111,9 +1117,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#removeTag(org.eclipse.emf.emfstore.internal.server.model.versioning.PrimaryVersionSpec,
 	 *      org.eclipse.emf.emfstore.internal.server.model.versioning.TagVersionSpec)
 	 */
@@ -1123,9 +1129,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#resolve(org.eclipse.emf.emfstore.internal.server.model.url.ModelElementUrlFragment)
 	 */
 	public EObject resolve(ModelElementUrlFragment modelElementUrlFragment) throws MEUrlResolutionException {
@@ -1138,9 +1144,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#resolveVersionSpec(org.eclipse.emf.emfstore.internal.server.model.versioning.VersionSpec,
 	 *      org.eclipse.core.runtime.IProgressMonitor)
 	 */
@@ -1158,9 +1164,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#revert()
 	 */
 	public void revert() {
@@ -1188,7 +1194,7 @@
 
 	/**
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#hasUnsavedChanges()
 	 */
 	public boolean hasUnsavedChanges() {
@@ -1212,7 +1218,7 @@
 
 	/**
 	 * Save the given resource that is part of the project space resource set.
-	 * 
+	 *
 	 * @param resource
 	 *            the resource
 	 */
@@ -1233,9 +1239,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#setProperty(org.eclipse.emf.emfstore.internal.server.model.accesscontrol.OrgUnitProperty)
 	 */
 	public void setProperty(OrgUnitProperty property) {
@@ -1269,9 +1275,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#shareProject(org.eclipse.core.runtime.IProgressMonitor)
 	 */
 	public ProjectInfo shareProject(IProgressMonitor monitor) throws ESException {
@@ -1279,9 +1285,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#shareProject(org.eclipse.emf.emfstore.internal.client.model.Usersession,
 	 *      org.eclipse.core.runtime.IProgressMonitor)
 	 */
@@ -1309,9 +1315,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#transmitProperties()
 	 */
 	public void transmitProperties() {
@@ -1337,9 +1343,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#undoLastOperation()
 	 */
 	public void undoLastOperation() {
@@ -1347,9 +1353,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#undoLastOperation()
 	 */
 	public void undoLastOperations(int numberOfOperations) {
@@ -1374,9 +1380,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#update(org.eclipse.core.runtime.IProgressMonitor)
 	 */
 	public PrimaryVersionSpec update(IProgressMonitor monitor) throws ESException {
@@ -1384,9 +1390,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#update(org.eclipse.emf.emfstore.internal.server.model.versioning.VersionSpec)
 	 */
 	public PrimaryVersionSpec update(final VersionSpec version) throws ESException {
@@ -1394,9 +1400,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#update(org.eclipse.emf.emfstore.internal.server.model.versioning.VersionSpec,
 	 *      org.eclipse.emf.emfstore.client.callbacks.ESUpdateCallback, org.eclipse.core.runtime.IProgressMonitor)
 	 */
@@ -1422,9 +1428,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.common.ESDisposable#dispose()
 	 */
 	@SuppressWarnings("unchecked")
@@ -1458,9 +1464,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.client.model.ProjectSpace#isShared()
 	 */
 	public boolean isShared() {
@@ -1495,9 +1501,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.common.api.APIDelegate#toAPI()
 	 */
 	public ESLocalProjectImpl toAPI() {
@@ -1508,9 +1514,9 @@
 	}
 
 	/**
-	 * 
+	 *
 	 * {@inheritDoc}
-	 * 
+	 *
 	 * @see org.eclipse.emf.emfstore.internal.common.api.APIDelegate#createAPI()
 	 */
 	public ESLocalProjectImpl createAPI() {
@@ -1519,7 +1525,7 @@
 
 	/**
 	 * Returns the {@link ESRunnableContext} operations are applied in.
-	 * 
+	 *
 	 * @return the runnable context operations are executed in
 	 */
 	public ESRunnableContext getRunnableContext() {
diff --git a/bundles/org.eclipse.emf.emfstore.server.model/src/org/eclipse/emf/emfstore/internal/server/model/versioning/impl/FileBasedChangePackageImpl.java b/bundles/org.eclipse.emf.emfstore.server.model/src/org/eclipse/emf/emfstore/internal/server/model/versioning/impl/FileBasedChangePackageImpl.java
index e443bfa..94866f4 100644
--- a/bundles/org.eclipse.emf.emfstore.server.model/src/org/eclipse/emf/emfstore/internal/server/model/versioning/impl/FileBasedChangePackageImpl.java
+++ b/bundles/org.eclipse.emf.emfstore.server.model/src/org/eclipse/emf/emfstore/internal/server/model/versioning/impl/FileBasedChangePackageImpl.java
@@ -1,5 +1,5 @@
 /*******************************************************************************
- * Copyright (c) 2008-2011 Chair for Applied Software Engineering,
+ * Copyright (c) 2008-2015 Chair for Applied Software Engineering,
  * Technische Universitaet Muenchen.
  * All rights reserved. This program and the accompanying materials
  * are made available under the terms of the Eclipse Public License v1.0
@@ -7,6 +7,7 @@
  * http://www.eclipse.org/legal/epl-v10.html
  *
  * Contributors:
+ * Edgar Mueller - initial API and implementation
  ******************************************************************************/
 package org.eclipse.emf.emfstore.internal.server.model.versioning.impl;
 
@@ -25,7 +26,6 @@
 import java.util.List;
 import java.util.Map;
 
-import org.apache.commons.io.IOUtils;
 import org.apache.commons.io.input.ReversedLinesFileReader;
 import org.eclipse.emf.common.notify.Notification;
 import org.eclipse.emf.common.notify.NotificationChain;
@@ -88,6 +88,16 @@
  */
 public class FileBasedChangePackageImpl extends EObjectImpl implements FileBasedChangePackage {
 
+	private static final String EMPTY_CHANGE_PACKAGE = XmlTags.XML_HEADER + XmlTags.CHANGE_PACKAGE_START
+		+ XmlTags.CHANGE_PACKAGE_END;
+
+	private static final String TEMP_FILE_PREFIX = "temp-"; //$NON-NLS-1$
+
+	private static final String TEMP_SUFFIX = ".temp"; //$NON-NLS-1$
+
+	// FIXME we also have a constant for this on the client side
+	private static final String OPERATION_FILE_SUFFIX = ".eoc"; //$NON-NLS-1$
+
 	/**
 	 * The cached value of the '{@link #getLogMessage() <em>Log Message</em>}' containment reference.
 	 * <!-- begin-user-doc -->
@@ -116,7 +126,7 @@
 	/**
 	 * Whether this change package has been initialized.
 	 *
-	 * TODO: move to Ecore? Maybe we don't even need this
+	 * FIXME: move to Ecore? Maybe we don't even need this
 	 *
 	 * @generated NOT
 	 */
@@ -281,7 +291,7 @@
 	 * @generated NOT
 	 */
 	public String getTempFilePath() {
-		return filePath + ".temp"; //$NON-NLS-1$
+		return filePath + TEMP_SUFFIX;
 	}
 
 	/**
@@ -464,7 +474,7 @@
 	 * @see org.eclipse.emf.emfstore.internal.server.model.versioning.AbstractChangePackage#addAll(java.util.List)
 	 */
 	public void addAll(List<AbstractOperation> ops) {
-		// TODO: LCP - file is reopened for each op
+		// FIXME: LCP - file is reopened for each operation
 		for (final AbstractOperation op : ops) {
 			add(op);
 		}
@@ -478,37 +488,38 @@
 	 */
 	public void add(final AbstractOperation op) {
 
+		final ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
 		final Resource resource = createVirtualResource();
-
 		resource.getContents().add(op);
 
-		final ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
-		RandomAccessFile raf = null;
+		Optional<RandomAccessFile> maybeRandomAccessFile = Optional.absent();
+
 		try {
 			outputStream.write(asBytes(XmlTags.OPERATIONS_START_TAG + XmlTags.NEWLINE));
 			resource.save(outputStream, loadingOptions());
-			outputStream.write((XmlTags.OPERATIONS_END_TAG + XmlTags.NEWLINE).getBytes());
-			final String filePath = getTempFilePath();
-
-			final File file = new File(filePath);
+			outputStream.write(asBytes(XmlTags.OPERATIONS_END_TAG + XmlTags.NEWLINE));
 
 			if (needsInit) {
-				needsInit = false;
-				final FileWriter writer = new FileWriter(file);
-				writer.write(XmlTags.XML_HEADER + XmlTags.CHANGE_PACKAGE_START);
-				writer.write(XmlTags.CHANGE_PACKAGE_END);
-				writer.close();
+				initializeEmptyChangePackage();
 			}
 
-			raf = new RandomAccessFile(filePath, "rw"); //$NON-NLS-1$
-			raf.skipBytes((int) (raf.length() - XmlTags.CHANGE_PACKAGE_END.getBytes().length));
-			raf.write(outputStream.toByteArray());
-			raf.write(XmlTags.CHANGE_PACKAGE_END.getBytes());
+			final RandomAccessFile randomAccessFile = new RandomAccessFile(getTempFilePath(), "rw"); //$NON-NLS-1$
+			maybeRandomAccessFile = Optional.of(randomAccessFile);
+			randomAccessFile.skipBytes((int) (randomAccessFile.length() - asBytes(XmlTags.CHANGE_PACKAGE_END).length));
+			randomAccessFile.write(outputStream.toByteArray());
+			randomAccessFile.write(asBytes(XmlTags.CHANGE_PACKAGE_END));
 		} catch (final IOException e) {
-			// avoid checked exception since this would lead to cluttered code
-			throw new RuntimeException(e);
+			// ESException not available
+			throw new IllegalStateException(e);
 		} finally {
-			IOUtils.closeQuietly(raf);
+			try {
+				outputStream.close();
+				if (maybeRandomAccessFile.isPresent()) {
+					maybeRandomAccessFile.get().close();
+				}
+			} catch (final IOException ex) {
+				ModelUtil.logException(ex);
+			}
 		}
 	}
 
@@ -519,15 +530,15 @@
 	 * @see org.eclipse.emf.emfstore.internal.server.model.versioning.AbstractChangePackage#reverse()
 	 */
 	public FileBasedChangePackage reverse() {
+		// create a new temporary change package that will contain all reversed operations
 		final FileBasedChangePackage reversedChangePackage = VersioningFactory.eINSTANCE.createFileBasedChangePackage();
-		// TODO LCP: where should we put the file
 		try {
-			final File tempFile = File.createTempFile("temp-", ".eoc"); //$NON-NLS-1$ //$NON-NLS-2$
+			final File tempFile = File.createTempFile(TEMP_FILE_PREFIX, OPERATION_FILE_SUFFIX);
 			tempFile.deleteOnExit();
 			reversedChangePackage.initialize(tempFile.getAbsolutePath());
 		} catch (final IOException ex) {
-			// TODO
-			ex.printStackTrace();
+			// we cannot throw ESException, since it cannot be brought into scope
+			throw new IllegalStateException(ex);
 		}
 		final ESCloseableIterable<AbstractOperation> operationsHandle = reversedOperations();
 		try {
@@ -544,14 +555,12 @@
 
 	public FileBasedChangePackage copy() {
 		final FileBasedChangePackage changePackage = VersioningFactory.eINSTANCE.createFileBasedChangePackage();
-		// TODO LCP: where should we put the file
 		try {
-			final File tempFile = File.createTempFile("temp-", ".eoc"); //$NON-NLS-1$ //$NON-NLS-2$
+			final File tempFile = File.createTempFile(TEMP_FILE_PREFIX, OPERATION_FILE_SUFFIX);
 			tempFile.deleteOnExit();
 			changePackage.initialize(tempFile.getAbsolutePath());
 		} catch (final IOException ex) {
-			// TODO
-			ex.printStackTrace();
+			throw new IllegalStateException(ex);
 		}
 		final ESCloseableIterable<AbstractOperation> operationsHandle = operations();
 		try {
@@ -595,20 +604,27 @@
 	 */
 	public int size() {
 		int counter = 0;
-		ReversedLinesFileReader reversedLinesFileReader = null;
+		Optional<ReversedLinesFileReader> maybeReversedReader = Optional.absent();
 		try {
-			reversedLinesFileReader = new ReversedLinesFileReader(new File(getTempFilePath()));
+			final ReversedLinesFileReader reversedReader = new ReversedLinesFileReader(new File(getTempFilePath()));
+			maybeReversedReader = Optional.of(reversedReader);
 			String line;
-			while ((line = reversedLinesFileReader.readLine()) != null) {
+			while ((line = reversedReader.readLine()) != null) {
 				if (line.contains(XmlTags.OPERATIONS_END_TAG)) {
 					counter++;
 				}
 			}
 		} catch (final IOException ex) {
-			// TODO
-			ex.printStackTrace();
+			// ESException not available
+			throw new IllegalStateException(ex);
 		} finally {
-			IOUtils.closeQuietly(reversedLinesFileReader);
+			if (maybeReversedReader.isPresent()) {
+				try {
+					maybeReversedReader.get().close();
+				} catch (final IOException ex) {
+					ModelUtil.logException(ex);
+				}
+			}
 		}
 		return counter;
 
@@ -629,27 +645,28 @@
 	 * @see org.eclipse.emf.emfstore.internal.server.model.versioning.AbstractChangePackage#isEmpty()
 	 */
 	public boolean isEmpty() {
-		BufferedReader reader = null;
+		Optional<BufferedReader> maybeReader = Optional.absent();
 		try {
 			final File file = new File(getTempFilePath());
 			if (!file.exists()) {
 				return true;
 			}
-			// TODO: move reader into operationemitter
-			reader = new BufferedReader(new FileReader(file));
+			// FIXME: move reader into OperationEmitter?
+			maybeReader = Optional.of(new BufferedReader(new FileReader(file)));
 			final OperationEmitter operationEmitter = new OperationEmitter(Direction.Forward);
-			final ReadLineCapable create = ReadLineCapable.INSTANCE.create(reader);
-			return !operationEmitter.tryEmit(create).isPresent();
+			final ReadLineCapable create = ReadLineCapable.INSTANCE.create(maybeReader.get());
+			// check if we have at least one operation
+			final Optional<AbstractOperation> maybeOp = operationEmitter.tryEmit(create);
+			return !maybeOp.isPresent();
 		} catch (final IOException ex) {
 			throw new RuntimeException(ex);
 		} finally {
 			try {
-				if (reader != null) {
-					reader.close();
+				if (maybeReader.isPresent()) {
+					maybeReader.get().close();
 				}
 			} catch (final IOException ex) {
-				// TODO Auto-generated catch block
-				ex.printStackTrace();
+				ModelUtil.logException(ex);
 			}
 		}
 	}
@@ -660,30 +677,31 @@
 	 * @see org.eclipse.emf.emfstore.internal.server.model.versioning.AbstractChangePackage#removeAtEnd(int)
 	 */
 	public List<AbstractOperation> removeAtEnd(int n) {
-		ReversedLinesFileReader reversedLinesFileReader = null;
+		final List<AbstractOperation> ops = new ArrayList<AbstractOperation>();
+		final OperationEmitter operationEmitter = new OperationEmitter(Direction.Backward);
+		Optional<ReversedLinesFileReader> maybeReversedReader = Optional.absent();
 		int counter = n;
 
 		try {
-			final String filePath = getTempFilePath();
-			reversedLinesFileReader = new ReversedLinesFileReader(new File(filePath));
-			final OperationEmitter operationEmitter = new OperationEmitter(Direction.Backward);
+			final ReversedLinesFileReader reversedReader = new ReversedLinesFileReader(new File(getTempFilePath()));
+			maybeReversedReader = Optional.of(reversedReader);
 			AbstractOperation operation;
-			final List<AbstractOperation> ops = new ArrayList<AbstractOperation>();
-			final ReadLineCapable reader = ReadLineCapable.INSTANCE.create(reversedLinesFileReader);
-			final Optional<AbstractOperation> optionalOperation = operationEmitter.tryEmit(reader);
-			while (counter > 0 && optionalOperation.isPresent()) {
-				operation = optionalOperation.get();
+			final ReadLineCapable reader = ReadLineCapable.INSTANCE.create(reversedReader);
+			final Optional<AbstractOperation> maybeOperation = operationEmitter.tryEmit(reader);
+
+			while (counter > 0 && maybeOperation.isPresent()) {
+				operation = maybeOperation.get();
 				ops.add(operation);
 				counter -= 1;
 			}
-			// TODO: reuse readlinecapable?
+
+			// FIXME: reuse ReadLineCapable?
 			final long offset = operationEmitter.getOffset();
 
-			final RandomAccessFile raf = new RandomAccessFile(filePath, "rw"); //$NON-NLS-1$
+			final RandomAccessFile raf = new RandomAccessFile(getTempFilePath(), "rw"); //$NON-NLS-1$
 			final long skip = raf.length() + 1 - offset;
 			raf.seek(skip);
-			// TODO: duplicate code
-			final byte[] bytes = (XmlTags.NEWLINE + XmlTags.CHANGE_PACKAGE_END).getBytes();
+			final byte[] bytes = asBytes(XmlTags.NEWLINE + XmlTags.CHANGE_PACKAGE_END);
 			raf.write(bytes);
 			raf.setLength(skip + bytes.length);
 			raf.close();
@@ -691,13 +709,17 @@
 			return ops;
 
 		} catch (final IOException ex) {
-			ex.printStackTrace();
+			// ESException not available
+			throw new IllegalStateException(ex);
 		} finally {
-			IOUtils.closeQuietly(reversedLinesFileReader);
+			if (maybeReversedReader.isPresent()) {
+				try {
+					maybeReversedReader.get().close();
+				} catch (final IOException ex) {
+					ModelUtil.logException(ex);
+				}
+			}
 		}
-
-		return null;
-
 	}
 
 	/**
@@ -706,24 +728,23 @@
 	 * @see org.eclipse.emf.emfstore.internal.server.model.versioning.AbstractChangePackage#clear()
 	 */
 	public void clear() {
-		RandomAccessFile raf = null;
+		Optional<RandomAccessFile> maybeRandomAccessFile = Optional.absent();
 		try {
-			raf = new RandomAccessFile(getTempFilePath(), "rw"); //$NON-NLS-1$
-			raf.seek(0);
-			final String emptyChangePackage = XmlTags.XML_HEADER + XmlTags.CHANGE_PACKAGE_START
-				+ XmlTags.CHANGE_PACKAGE_END;
-			raf.write(emptyChangePackage.getBytes());
-			raf.setLength(emptyChangePackage.length());
+			final RandomAccessFile randomAccessFile = new RandomAccessFile(getTempFilePath(), "rw"); //$NON-NLS-1$
+			maybeRandomAccessFile = Optional.of(randomAccessFile);
+			randomAccessFile.seek(0);
+			randomAccessFile.write(asBytes(EMPTY_CHANGE_PACKAGE));
+			randomAccessFile.setLength(EMPTY_CHANGE_PACKAGE.length());
 		} catch (final FileNotFoundException ex) {
 			throw new RuntimeException(ex);
 		} catch (final IOException ex) {
 			throw new RuntimeException(ex);
 		} finally {
-			if (raf != null) {
+			if (maybeRandomAccessFile.isPresent()) {
 				try {
-					raf.close();
+					maybeRandomAccessFile.get().close();
 				} catch (final IOException ex) {
-					ex.printStackTrace();
+					ModelUtil.logException(ex);
 				}
 			}
 		}
@@ -735,12 +756,9 @@
 	 * @see org.eclipse.emf.emfstore.internal.server.model.versioning.AbstractChangePackage#attachToProjectSpace(org.eclipse.emf.emfstore.internal.server.model.versioning.impl.persistent.ChangePackageContainer)
 	 */
 	public void attachToProjectSpace(ChangePackageContainer changePackageHolder) {
-		// final URI operationsURI = ESClientURIUtil.createOperationsURI(getProjectSpace());
-		// final URI normalizedOperationUri = ESWorkspaceProviderImpl.getInstance().getInternalWorkspace()
-		// .getResourceSet().getURIConverter().normalize(operationsURI);
 		final URI changePackageUri = changePackageHolder.getChangePackageUri();
 		final String operationFileString = changePackageUri.toFileString();
-		final File operationFile = new File(operationFileString + ".temp");
+		final File operationFile = new File(operationFileString + TEMP_SUFFIX);
 		// operationFile.delete();
 		final File thisFile = new File(getTempFilePath());
 		try {
@@ -749,11 +767,18 @@
 			setFilePath(operationFileString);
 			changePackageHolder.setChangePackage(this);
 		} catch (final IOException ex) {
-			// TODO: LCP
-			ex.printStackTrace();
+			// ESException not available
+			throw new IllegalStateException(ex);
 		}
 	}
 
+	public void delete() {
+		final File opFile = new File(getFilePath());
+		final File tempOpFile = new File(getTempFilePath());
+		opFile.delete();
+		tempOpFile.delete();
+	}
+
 	/**
 	 * {@inheritDoc}
 	 *
@@ -770,15 +795,27 @@
 	 */
 	public void initialize(String filePath) {
 		setFilePath(filePath);
+		initializeEmptyChangePackage();
+	}
+
+	private void initializeEmptyChangePackage() {
 		needsInit = false;
+		Optional<FileWriter> maybeWriter = Optional.absent();
 		try {
-			final FileWriter writer = new FileWriter(getTempFilePath());
-			writer.write(XmlTags.XML_HEADER + XmlTags.CHANGE_PACKAGE_START);
-			writer.write(XmlTags.CHANGE_PACKAGE_END);
-			writer.close();
+			final FileWriter fileWriter = new FileWriter(getTempFilePath());
+			maybeWriter = Optional.of(fileWriter);
+			fileWriter.write(EMPTY_CHANGE_PACKAGE);
 		} catch (final IOException ex) {
-			// TODO LCP
-			ex.printStackTrace();
+			// ESException not available
+			throw new IllegalStateException(ex);
+		} finally {
+			if (maybeWriter.isPresent()) {
+				try {
+					maybeWriter.get().close();
+				} catch (final IOException ex) {
+					ModelUtil.logException(ex);
+				}
+			}
 		}
 	}