[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Newsgroup Home]
|
[news.eclipse.modeling.mdt.uml2] Re: Preserving uuid to xmi:id mapping converting uml2 to eCore
|
Kenn Hussey wrote:
Kenn,
Many thanks, I tried as you suggest and it seems to work fine, like in the
following code:
package test;
import java.io.IOException;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import org.eclipse.emf.common.util.BasicDiagnostic;
import org.eclipse.emf.common.util.DiagnosticChain;
import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.ecore.EModelElement;
import org.eclipse.emf.ecore.ENamedElement;
import org.eclipse.emf.ecore.EObject;
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.emf.ecore.xmi.XMIResource;
import org.eclipse.uml2.uml.Element;
import org.eclipse.uml2.uml.UMLPackage;
import org.eclipse.uml2.uml.resource.UMLResource;
import org.eclipse.uml2.uml.util.UMLUtil;
import org.eclipse.uml2.uml.util.UMLUtil.UML2EcoreConverter;
import com.pjsoft.ecore.plus.ECorePlus.util.ECorePlusResourceFactoryImpl;
public class UML2ECorePlus {
private static String filePath = "/uml/test.uml";
protected static final ResourceSet RESOURCE_SET = new ResourceSetImpl();
public UML2ECorePlus() {}
class MyUML2EcoreConverter extends UML2EcoreConverter{
Map<Element, EModelElement> getElementToEModelElementMap(){
return elementToEModelElementMap;
}
};
protected static void registerResourceFactories()
{ RESOURCE_SET.getResourceFactoryRegistry().getExtensionToFactoryMap().put(
UMLResource.FILE_EXTENSION, UMLResource.Factory.INSTANCE);
RESOURCE_SET.getPackageRegistry().put(UMLPackage.eNS_URI,
UMLPackage.eINSTANCE);
RESOURCE_SET.getResourceFactoryRegistry().getExtensionToFactoryMap().put(
"ecore", new ECorePlusResourceFactoryImpl());
}
private void mkSchema(URI umlUri, URI ecoreUri) throws IOException {
UMLResource umlRes = (UMLResource)RESOURCE_SET.getResource(umlUri, true);
XMIResource ecoreRes =
(XMIResource)RESOURCE_SET.createResource(ecoreUri);
org.eclipse.uml2.uml.Model umlPkg = (org.eclipse.uml2.uml.Model)
EcoreUtil
.getObjectByType(umlRes.getContents(), UMLPackage.Literals.MODEL);
DiagnosticChain dc=new BasicDiagnostic();
Map<String, String> options=new HashMap<String, String>();
Map<Object, Object> cache=new HashMap<Object, Object>();
options.put(UML2EcoreConverter.OPTION__ECORE_TAGGED_VALUES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__REDEFINING_OPERATIONS,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__REDEFINING_PROPERTIES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__SUBSETTING_PROPERTIES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__UNION_PROPERTIES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__DERIVED_FEATURES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__DUPLICATE_OPERATIONS,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__DUPLICATE_OPERATION_INHERITANCE,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__DUPLICATE_FEATURES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__DUPLICATE_FEATURE_INHERITANCE,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__SUPER_CLASS_ORDER,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__ANNOTATION_DETAILS,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__INVARIANT_CONSTRAINTS,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__OPERATION_BODIES,
UMLUtil.OPTION__REPORT);
options.put(UML2EcoreConverter.OPTION__COMMENTS, UMLUtil.OPTION__REPORT);
MyUML2EcoreConverter conv=new MyUML2EcoreConverter();
Collection<? extends EObject>
ret=conv.convert(Collections.singleton(umlPkg), options, dc, cache);
System.out.println(cache);
for(Element el: conv.getElementToEModelElementMap().keySet()){
ENamedElement enel=(ENamedElement)
conv.getElementToEModelElementMap().get(el);
ecoreRes.setID(enel, "UML.UUID:"+umlRes.getID(el));
}
for(EObject obj: ret)
ecoreRes.getContents().add(obj);
ecoreRes.save(Collections.EMPTY_MAP);
}
public static void main(String[] args) throws IOException {
UML2ECorePlus reader = new UML2ECorePlus();
registerResourceFactories();
reader.mkSchema(URI.createFileURI(filePath),
URI.createFileURI(filePath).trimFileExtension().appendFileExtension("ecore"));
}
}
Piergiuseppe,
I do think is makes sense to use UUIDs in computing differences between two
versions of a model (indeed that's in part why they were introduced). I
don't see a problem with using smilar (but not the same) IDs for different
representations (e.g. UML, Ecore) of the "same" element. See my response to
your other post regarding how to accomplish this. Basically, you need to use
a resource implementation for your Ecore models which supports UUIDs and
you'll need to do some post-processing once a UML model is converted to an
Ecore model (and before the target model is saved) to set the desired IDs.
Kenn
"Piergiuseppe Spinelli" <piergiuseppe.spinelli@xxxxxx> wrote in message
news:ef53ef1f0d4dc07897aaffcf7c389bd0$1@xxxxxxxxxxxxxxxxxx
Kenn Hussey wrote:
Piergiuseppe,
It isn't technically mandatory for UUIDs to be globally unique (and
there's no way to enforce that), but that's certainly the spirit with
which support for them was introduced. In fact, if you move an object
between two resource implementations for which UUIDs are enabled, the ID
for that object is preserved. The intent is that once an object has been
assigned a UUID, it keeps that UUID (regardless of which resource it's
attached to) until it is destroyed, regardless of how it changes over
time.
Kenn
Many thanks Kenn: that's very clear and it confirms UUIDs were introduced
not as a simple technicality but as true universal identifiers keeping
their validity along time and versions.
So, in your opinion does it make sense to use them:
- In computing differences between two versions of a model (instead than
URI fragments)?
- Preserving them in different translations of the same model (i.e. the
case could be generating eCore XMI:IDs from UML UUIDs)?
And if it could make some sense (at least in some situation), what is
(here you are the expert and I am asking for help) the simplest way to get
that?
Again many thanks
Piero
"Piergiuseppe Spinelli" <piergiuseppe.spinelli@xxxxxx> wrote in message
news:67ca18393826cdbe003eebf8851e0ebd$1@xxxxxxxxxxxxxxxxxx
Hi Kenn,
I apologize if I return again on this point, just to ask one
clarification (not to argue, really just to better undertand)
You said: "Given that UUIDs are supposed to be globally unique (that's
why they're useful), I'm not sure it would be a good idea to assign the
IDs of UML elements to the resulting Ecore elements"
Now this made me wander a couple of things:
- does "UUIDs are globally unique" mean than every time you serialize
the same uml document to different files it is mandatory to generate new
UUIDs?
In my opinion this is not required, since the role of UUIDs should be to
sign with an unique value, w/o any business meaning by itself, the
unique identity of an element (i.e. an UML Class or Property).
So, when the same element it is serialized again & again (and this
means, the same identity, even if some of its properties has been
modified or its position in the document has changed) it could be right
to use the same UUID since it is the only thing granting the identity of
the element along the time.
Using URI fragments, instead (in my opinion, but I ask for yours),
identify an elements just in a specific context and are not always able
to keep its identity along the time (i.e. when some other sibling is
inserted before it, or it is renamed or moved under onother package, and
so on)
Finally, the unicity of an UUIDs shoud be granted just in the space of
all the UUIDs: this shoud not refrain to use the same value (or a
derived one) in the space of XMI:ID of its ecore translation, since (1)
XMI:IDs are not UUIDs (2) they need to be unique just inside a model.
At the end, a concrete example: I've been involved in these last years,
on the behalf of the bigger italian Telco, in the processes for adopting
the SID (the reference model for the Telcos by the Tele Management
Forum).
SID is a very (really very) large UML document that needs to be extended
in order to be adopted in the real word, and it can be used in a lot of
ways: one of them is as an hub in the semantic reconciliation among the
different models used in the enterprise. This task requires a map
between the SID entities and each matching element in the different data
sources.
Now, every time the extended SID is modified (or a new version is
released by the TMF), all this huge mass of work should be revisited:
this would make the governance impossible in facts.
Now, if the impact analysis of a new SID version takes care of UUIDs and
they are preserved across the successive versions, the job becomes
possible!
As you see, this could be a very important and not "philosophical"
question.
Since I have choosed Eclipse and EMF as the best among the current
tecnologies to gring models and metadata, I look forward for opinions
about that from you and every other guy interested in this matter.
Thanks,
Piero
Kenn Hussey wrote:
Piergiuseppe,
Given that UUIDs are supposed to be globally unique (that's why they're
useful), I'm not sure it would be a good idea to assign the IDs of UML
elements to the resulting Ecore elements (although it would be possible
by calling the conversion utility programmatically, using a custom
resource to load the Ecore model, and setting the XMI IDs of the Ecore
elements based on the UML element on which they were based). I would
suggest producing a mapping from UML element URI fragment (GUID) to
Ecore element URI fragment (name-based path) by processing the map that
is returned after the conversion and doing a reverse look-up to assign
the desired IDs to UML elements if/when the Ecore representation is
ever converted back to UML...
Kenn
"Piergiuseppe Spinelli" <piergiuseppe.spinelli@xxxxxx> wrote in message
news:66dcd6dc89d0595eed9e551934c1185b$1@xxxxxxxxxxxxxxxxxx
Hi,
I'm building an EMF based Eclipse application and I am currently using
the existing UML to EMF converter from the ide.
How can I preserve the uuids in the original uml file forcing them to
be the xmi:id of the generated EClasses, and EStructuralFeatures?
My UML tool assures to preserve the same uuid for the same element
(even if it is, let's say, moved to another package) across different
exports, so using uuids it is possible to perform more accurated
comparisons of generated eCore models that, i.e., do not exange a
moving operation for two unrelated operations (delete of the existing
element and creation of a new one).
Thank for any help