From da6dfefe10ed83dc74009c7424832d4d6f91cb7b Mon Sep 17 00:00:00 2001 From: Caspar De Groot Date: Mon, 18 Jan 2010 10:09:01 +0000 Subject: [298561] Uncommitted dangling references not removed on passiveUpdate/refresh https://bugs.eclipse.org/bugs/show_bug.cgi?id=298561 --- .../cdo/transaction/CDOTransactionImpl.java | 42 ++++++++++++++++++++++ 1 file changed, 42 insertions(+) (limited to 'plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal') diff --git a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/transaction/CDOTransactionImpl.java b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/transaction/CDOTransactionImpl.java index 7e889328d9..8cc3e29f1b 100644 --- a/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/transaction/CDOTransactionImpl.java +++ b/plugins/org.eclipse.emf.cdo/src/org/eclipse/emf/internal/cdo/transaction/CDOTransactionImpl.java @@ -77,7 +77,14 @@ import org.eclipse.net4j.util.options.OptionsEvent; import org.eclipse.net4j.util.transaction.TransactionException; import org.eclipse.emf.common.util.URI; +import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EPackage; +import org.eclipse.emf.ecore.EReference; +import org.eclipse.emf.ecore.InternalEObject; +import org.eclipse.emf.ecore.EStructuralFeature.Setting; +import org.eclipse.emf.ecore.util.EContentsEList; +import org.eclipse.emf.ecore.util.EcoreUtil; +import org.eclipse.emf.ecore.util.EContentsEList.FeatureIterator; import org.eclipse.emf.spi.cdo.CDOTransactionStrategy; import org.eclipse.emf.spi.cdo.InternalCDOObject; import org.eclipse.emf.spi.cdo.InternalCDOSavepoint; @@ -1580,6 +1587,41 @@ public class CDOTransactionImpl extends CDOViewImpl implements InternalCDOTransa super.doDeactivate(); } + /** + * @since 3.0 + */ + @Override + public Set handleInvalidationWithoutNotification(Set dirtyOIDs, + Collection detachedOIDs, Set dirtyObjects, Set detachedObjects) + { + // Bugzilla 298561: This override removes references to remotely + // detached objects that are present in any DIRTY or NEW objects + + removeCrossReferences(getDirtyObjects().values(), detachedOIDs); + removeCrossReferences(getNewObjects().values(), detachedOIDs); + + return super.handleInvalidationWithoutNotification(dirtyOIDs, detachedOIDs, dirtyObjects, detachedObjects); + } + + private void removeCrossReferences(Collection objects, Collection referencedOIDs) + { + for (CDOObject object : objects) + { + for (EContentsEList.FeatureIterator it = (FeatureIterator)object.eCrossReferences().iterator(); it + .hasNext();) + { + EObject crossReferencedObject = it.next(); + if (crossReferencedObject instanceof CDOObject + && referencedOIDs.contains(((CDOObject)crossReferencedObject).cdoID())) + { + EReference eReference = (EReference)it.feature(); + Setting setting = ((InternalEObject)object).eSetting(eReference); + EcoreUtil.remove(setting, crossReferencedObject); + } + } + } + } + /** * @author Simon McDuff */ -- cgit v1.2.3