diff --git a/tools.descartes.prisma.agent.generic/src/tools/descartes/prisma/agent/generic/GenericAgent.java b/tools.descartes.prisma.agent.generic/src/tools/descartes/prisma/agent/generic/GenericAgent.java index cc58e35e4dbe04a1847d399ff27bea1c30e5b9f1..dd26b8a7fa35d9597064ce7ce9624fbca4f32810 100644 --- a/tools.descartes.prisma.agent.generic/src/tools/descartes/prisma/agent/generic/GenericAgent.java +++ b/tools.descartes.prisma.agent.generic/src/tools/descartes/prisma/agent/generic/GenericAgent.java @@ -1,23 +1,28 @@ package tools.descartes.prisma.agent.generic; import java.io.File; +import java.util.Collection; import java.util.Collections; import java.util.HashMap; -import java.util.List; +import java.util.HashSet; import java.util.Map; +import java.util.Set; import org.apache.commons.cli.CommandLine; import org.apache.commons.cli.CommandLineParser; import org.apache.commons.cli.GnuParser; import org.apache.commons.cli.HelpFormatter; import org.apache.commons.cli.Options; +import org.eclipse.emf.cdo.CDOObject; import org.eclipse.emf.common.util.TreeIterator; import org.eclipse.emf.common.util.URI; import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EReference; +import org.eclipse.emf.ecore.EStructuralFeature.Setting; import org.eclipse.emf.ecore.resource.Resource; import org.eclipse.emf.ecore.resource.ResourceSet; import org.eclipse.emf.ecore.resource.impl.ResourceSetImpl; +import org.eclipse.emf.ecore.util.EcoreUtil; import org.eclipse.equinox.app.IApplication; import org.eclipse.equinox.app.IApplicationContext; @@ -26,13 +31,14 @@ import edu.kit.ipd.descartes.mm.resourcetype.ResourceType; import edu.kit.ipd.descartes.mm.resourcetype.ResourceTypeRepository; import edu.kit.ipd.descartes.mm.resourcetype.ResourcetypePackage; import tools.descartes.prisma.agent.generic.genericagent.GenericAgentConfiguration; +import tools.descartes.prisma.agent.generic.genericagent.RequiredObject; import tools.descartes.prisma.core.ModelRepository; import tools.descartes.prisma.core.adapter.ModelSkeletonAdapter; +import tools.descartes.prisma.core.adapter.ObjectMatcher; import tools.descartes.prisma.core.agent.AgentController; import tools.descartes.prisma.core.agent.DelegationProvider; import tools.descartes.prisma.core.impl.CDOModelRepository; import tools.descartes.prisma.model.scope.DelegatedObject; -import tools.descartes.prisma.model.scope.ScopeConfiguration; import tools.descartes.prisma.model.skeleton.ModelSkeleton; public class GenericAgent implements IApplication { @@ -41,19 +47,37 @@ public class GenericAgent implements IApplication { private ModelSkeleton skeleton; + private final Set<EObject> delegatedObjects = new HashSet<>(); + public GenericAgentController(ModelRepository repository, GenericAgentConfiguration configuration) { super(repository, configuration.getScope().getPath(), configuration.getId()); } + + @Override + protected void notifyAddDelegatedElement(EObject newElement, Map<String, String> additionalProperties) { + delegatedObjects.add(newElement); + } + + @Override + protected void notifyRemoveDelegatedElement(EObject oldElement, Map<String, String> additionalProperties) { + delegatedObjects.remove(oldElement); + } + + public Set<EObject> getDelegatedObjects() { + return delegatedObjects; + } + } private class GenericDelegationProvider implements DelegationProvider { private final Map<String, Map<String, String>> elements = new HashMap<>(); - public GenericDelegationProvider(ScopeConfiguration configuration) { + public GenericDelegationProvider(GenericAgentConfiguration configuration) { for (DelegatedObject curElement : configuration.getDelegatedObjects()) { - if (curElement.getObject() instanceof Identifier) { - elements.put(((Identifier) curElement).getId(), curElement.getAdditionalProperties().map()); + EObject object = curElement.getObject(); + if (object instanceof Identifier) { + elements.put(((Identifier) object).getId(), curElement.getAdditionalProperties().map()); } } } @@ -114,11 +138,16 @@ public class GenericAgent implements IApplication { ModelRepository repository = new CDOModelRepository(repositoryURL); GenericAgentController agent = new GenericAgentController(repository, configuration); + + agent.setDelegationProvider(new GenericDelegationProvider(configuration)); + agent.start().get(); replacePublicResources(agent, configuration.getSkeleton()); - agent.apply(configuration.getSkeleton()); + if (resolveRequiredObjects(agent, configuration)) { + agent.apply(configuration.getSkeleton()); + } agent.stop().get(); @@ -128,31 +157,27 @@ public class GenericAgent implements IApplication { @Override public void stop() { // TODO Auto-generated method stub - } private GenericAgentConfiguration loadConfiguration(String configurationPath) { ResourceSet set = new ResourceSetImpl(); Resource res = set.getResource(URI.createFileURI(new File(configurationPath).getAbsolutePath()), true); GenericAgentConfiguration configuration = (GenericAgentConfiguration) res.getContents().get(0); - return configuration; - } - private void integrateIntoSkeleton(ModelSkeleton skeleton, EObject root) { - for (EReference curReference : skeleton.eClass().getEAllContainments()) { - if (curReference.getEReferenceType().isSuperTypeOf(root.eClass())) { - if (curReference.isMany()) { - @SuppressWarnings("unchecked") - List<EObject> values = (List<EObject>) skeleton.eGet(curReference); - values.add(root); - } else { - skeleton.eSet(curReference, root); - } - return; + // IMPORTANT: resolve all cross-references + EcoreUtil.resolveAll(set); + Map<EObject, Collection<Setting>> unresolved = EcoreUtil.UnresolvedProxyCrossReferencer.find(set); + for (EObject problemObject : unresolved.keySet()) { + Collection<Setting> unresolvedSettings = unresolved.get(problemObject); + for (Setting curSetting : unresolvedSettings) { + System.out.println("Unresolved proxy: " + curSetting.getEStructuralFeature()); } } + + return configuration; } + private void replacePublicResources(GenericAgentController agent, ModelSkeleton skeleton) { // Resource types (e.g., CPU, HDD, DELAY) which are defined globally are // not included in the model skeleton. @@ -183,4 +208,30 @@ public class GenericAgent implements IApplication { } } + private boolean resolveRequiredObjects(GenericAgentController agent, GenericAgentConfiguration configuration) { + Set<RequiredObject> notResolved = new HashSet<>(configuration.getRequiredObjects()); + for (EObject curDelegate : agent.getDelegatedObjects()) { + for (RequiredObject reqObject : notResolved) { + if (ObjectMatcher.matches(curDelegate, reqObject.getObject())) { + // Connect the two objects with each other + ModelSkeletonAdapter adapter = agent.getModelRepository().adapt(reqObject, + ModelSkeletonAdapter.class); + adapter.setRepositoryObject((CDOObject) curDelegate); + + // Requirement is fulfilled + notResolved.remove(reqObject); + break; + } + } + } + + if (!notResolved.isEmpty()) { + for (RequiredObject unresolvedObject : notResolved) { + System.err.println("Could not resolve required object: " + unresolvedObject.getObject()); + } + return false; + } + return true; + } + }