Skip to content
Snippets Groups Projects
Commit c60bec1c authored by Andreas Bayha's avatar Andreas Bayha
Browse files

Merge branch '4346' into 'master'

4346

Closes af3#4346

See merge request !219
parents 76b90e1c 30d69098
No related branches found
No related tags found
1 merge request!2194346
IReuseProvider.java 18d293f7f1f072883188f16fb6eeb52c8d6042cf GREEN IReuseProvider.java 18d293f7f1f072883188f16fb6eeb52c8d6042cf GREEN
IReuseProviderService.java bcc70de0bb8d39c330e3a25d884abc7092dc1b7e GREEN IReuseProviderService.java bcc70de0bb8d39c330e3a25d884abc7092dc1b7e GREEN
LayoutedReuseProviderBase.java b0e4ce3cda818b0723ec37b925a4c4c3d0c41909 GREEN LayoutedReuseProviderBase.java b0e4ce3cda818b0723ec37b925a4c4c3d0c41909 GREEN
ReuseProviderBase.java ac47f5ecafed0bdef6ef5183c7194aa756f723fd GREEN ReuseProviderBase.java b324d23be4deffbc97e587a76b527be2573942d1 GREEN
ReuseProviderService.java c4ef33283002d6dac6167f9c6c8f71d2c2ce39d1 GREEN ReuseProviderService.java c4ef33283002d6dac6167f9c6c8f71d2c2ce39d1 GREEN
...@@ -17,12 +17,16 @@ package org.fortiss.tooling.ext.reuse.service; ...@@ -17,12 +17,16 @@ package org.fortiss.tooling.ext.reuse.service;
import static org.eclipse.emf.ecore.util.EcoreUtil.replace; import static org.eclipse.emf.ecore.util.EcoreUtil.replace;
import static org.fortiss.tooling.ext.variability.util.VariabilityUtils.getOptVarPointSpecification; import static org.fortiss.tooling.ext.variability.util.VariabilityUtils.getOptVarPointSpecification;
import static org.fortiss.tooling.kernel.utils.EcoreUtils.getChildrenWithType;
import static org.fortiss.tooling.kernel.utils.EcoreUtils.replaceEObjectReferences; import static org.fortiss.tooling.kernel.utils.EcoreUtils.replaceEObjectReferences;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.HashSet;
import java.util.List; import java.util.List;
import java.util.Set;
import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EObject;
import org.eclipse.emf.ecore.EReference;
import org.fortiss.tooling.base.model.element.IHierarchicElement; import org.fortiss.tooling.base.model.element.IHierarchicElement;
import org.fortiss.tooling.base.model.element.IHierarchicElementContainer; import org.fortiss.tooling.base.model.element.IHierarchicElementContainer;
import org.fortiss.tooling.base.model.element.IModelElement; import org.fortiss.tooling.base.model.element.IModelElement;
...@@ -48,6 +52,9 @@ public class ReuseProviderBase<T extends EObject> implements IReuseProvider<T> { ...@@ -48,6 +52,9 @@ public class ReuseProviderBase<T extends EObject> implements IReuseProvider<T> {
if(reuseElement instanceof IModelElement) { if(reuseElement instanceof IModelElement) {
removeVariabilitySpecifications((IModelElement)reuseElement); removeVariabilitySpecifications((IModelElement)reuseElement);
} }
removeExternalReferences(reuseElement);
return true; return true;
} }
...@@ -124,4 +131,63 @@ public class ReuseProviderBase<T extends EObject> implements IReuseProvider<T> { ...@@ -124,4 +131,63 @@ public class ReuseProviderBase<T extends EObject> implements IReuseProvider<T> {
} }
} }
} }
/**
* Recursively removes all external (i.e., non-containment) reference targets from this and all
* contained {@link EObject}s.
*
* FIXME #4150 (https://git.fortiss.org/af3/af3/-/issues/4150): This functionality should be
* removed, as soon as there is a dedicated management of external references.
*
* @param element
* The {@link EObject} for which all reference targets shall be removed.
*/
private void removeExternalReferences(EObject element) {
// Whitelist all contained elements as legal references (since they will also be copied).
Set<EObject> whitelist = new HashSet<EObject>(getChildrenWithType(element, EObject.class));
whitelist.add(element);
removeReferences(element, whitelist);
}
/**
* Recursively removes all reference targets from this and all contained {@link EObject}s which
* are not contained in the given whitelist.
*
* FIXME #4150 (https://git.fortiss.org/af3/af3/-/issues/4150): This functionality should be
* removed, as soon as there is a dedicated management of external references.
*/
@SuppressWarnings("unchecked")
private void removeReferences(EObject element, Set<EObject> whitelist) {
for(EReference ref : element.eClass().getEAllReferences()) {
Object refTarget = element.eGet(ref);
if(refTarget == null) {
continue;
}
if(refTarget instanceof List<?>) {
List<EObject> refTargetList = (List<EObject>)refTarget;
if(ref.isContainment()) {
// Containment relations must not be removed. Yet, references of children need
// to be removed recursively.
refTargetList.stream().forEach(target -> removeReferences(target, whitelist));
} else {
refTargetList.removeIf(t -> !whitelist.contains(t));
}
} else {
if(ref.isContainment()) {
// Keep reference target and make recursive call.
removeReferences((EObject)refTarget, whitelist);
} else {
if(!whitelist.contains(refTarget)) {
element.eSet(ref, null);
}
}
}
}
}
} }
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment