Skip to content

Commit 3410252

Browse files
committed
ST6RI-897 Moved the setting of elementIds to ElementAdapter.
- Creation of IDs overridden in NamespaceAdapter, LibraryPackageAdapter and OwningMembershipAdapter. - Updated CustomUML2EcoreConverter to add SysML EAnnotation to the Element::elementID EAttribute, so that a setting delegation is generated.
1 parent 0a8801c commit 3410252

15 files changed

Lines changed: 292 additions & 143 deletions

File tree

org.omg.sysml.uml.ecore.importer/src/org/omg/sysml/uml/ecore/importer/CustomUML2EcoreConverter.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,9 @@ private void customConvert(DiagnosticChain diagnostics) {
4343
for (Entry<Element, EModelElement> entry : elementToEModelElementMap.entrySet()) {
4444
Element element = entry.getKey();
4545
EModelElement modelElement = entry.getValue();
46-
if (element instanceof Property && ((Property)element).isDerived() && !((Property)element).isDerivedUnion() && modelElement instanceof EStructuralFeature ||
46+
if (element instanceof Property && modelElement instanceof EStructuralFeature &&
47+
(((Property)element).isDerived() && !((Property)element).isDerivedUnion() ||
48+
"elementId".equals(((Property)element).getName())) ||
4749
element instanceof Operation && modelElement instanceof EOperation) {
4850
String qualifiedName = ((NamedElement)element).getQualifiedName();
4951
addSysMLAnnotation(qualifiedName.substring(qualifiedName.indexOf("::") + 2), modelElement);

org.omg.sysml/model/SysML.ecore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -979,6 +979,7 @@
979979
<eAnnotations source="http://www.eclipse.org/emf/2002/GenModel">
980980
<details key="documentation" value="&lt;p>The globally unique identifier for this Element. This is intended to be set by tooling, and it must not change during the lifetime of the Element.&lt;/p>"/>
981981
</eAnnotations>
982+
<eAnnotations source="http://www.omg.org/spec/SysML"/>
982983
</eStructuralFeatures>
983984
<eStructuralFeatures xsi:type="ecore:EReference" name="owner" ordered="false"
984985
eType="#//Element" volatile="true" transient="true" derived="true" eOpposite="#//Element/ownedElement">

org.omg.sysml/src/org/omg/sysml/adapter/ElementAdapter.java

Lines changed: 42 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
/*******************************************************************************
22
* SysML 2 Pilot Implementation
3-
* Copyright (c) 2021-2022 Model Driven Solutions, Inc.
3+
* Copyright (c) 2021-2022, 2026 Model Driven Solutions, Inc.
44
*
55
* This program is free software: you can redistribute it and/or modify
66
* it under the terms of the GNU Lesser General Public License as published by
@@ -21,11 +21,14 @@
2121

2222
package org.omg.sysml.adapter;
2323

24+
import java.util.UUID;
25+
2426
import org.eclipse.emf.common.notify.impl.AdapterImpl;
2527
import org.omg.sysml.lang.sysml.Annotation;
2628
import org.omg.sysml.lang.sysml.Element;
2729
import org.omg.sysml.lang.sysml.FeatureTyping;
2830
import org.omg.sysml.lang.sysml.MetadataFeature;
31+
import org.omg.sysml.lang.sysml.Namespace;
2932
import org.omg.sysml.lang.sysml.SysMLFactory;
3033
import org.omg.sysml.lang.sysml.Type;
3134
import org.omg.sysml.util.ElementUtil;
@@ -37,6 +40,8 @@ public class ElementAdapter extends AdapterImpl {
3740

3841
private MetadataFeature metaclassFeature = null;
3942

43+
private String elementId;
44+
4045
public ElementAdapter(Element element) {
4146
super();
4247
kind = element.getClass();
@@ -51,6 +56,39 @@ public boolean isAdapterForType(Object object) {
5156
return kind.isInstance(object);
5257
}
5358

59+
// Element IDs
60+
61+
public String getElementId() {
62+
if (elementId == null) {
63+
elementId = createElementId();
64+
}
65+
return elementId;
66+
}
67+
68+
public void setElementId(String elementId) {
69+
this.elementId = elementId;
70+
}
71+
72+
/**
73+
* If the Element is not a standard library Element, create a random UUID.
74+
* If the Element is a standard library Element, create a name-based UUID using the Element's path.
75+
*/
76+
protected String createElementId() {
77+
Element target = getTarget();
78+
UUID uuid = UUID.randomUUID();
79+
if (ElementUtil.isStandardLibraryElement(target)) {
80+
String path = target.path();
81+
if (path != null) {
82+
Namespace libraryNamespace = target.libraryNamespace();
83+
if (target != libraryNamespace) {
84+
UUID namespaceUUID = UUID.fromString(libraryNamespace.getElementId());
85+
uuid = ElementUtil.constructNameUUID(namespaceUUID, path);
86+
}
87+
}
88+
}
89+
return uuid.toString();
90+
}
91+
5492
// Metaclass Feature
5593

5694
public MetadataFeature getMetaclassFeature() {
@@ -78,14 +116,15 @@ public void postProcess() {
78116
target.setDeclaredName(ElementUtil.unescapeString(target.getDeclaredName()));
79117
target.setDeclaredShortName(ElementUtil.unescapeString(target.getDeclaredShortName()));
80118
}
81-
119+
82120
// Transformation
83-
121+
84122
public boolean isTransformed() {
85123
return isTransformed;
86124
}
87125

88126
public void clearCaches() {
127+
elementId = null;
89128
}
90129

91130
public void transform() {

org.omg.sysml/src/org/omg/sysml/adapter/ElementAdapterFactory.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -367,6 +367,11 @@ public ElementAdapter caseItemUsage(ItemUsage element) {
367367
return new ItemUsageAdapter(element);
368368
}
369369

370+
@Override
371+
public ElementAdapter caseLibraryPackage(LibraryPackage element) {
372+
return new LibraryPackageAdapter(element);
373+
}
374+
370375
@Override
371376
public ElementAdapter caseLiteralString(LiteralString element) {
372377
return new LiteralStringAdapter(element);
@@ -437,6 +442,11 @@ public ElementAdapter caseOperatorExpression(OperatorExpression element) {
437442
return new OperatorExpressionAdapter(element);
438443
}
439444

445+
@Override
446+
public ElementAdapter caseOwningMembership(OwningMembership element) {
447+
return new OwningMembershipAdapter(element);
448+
}
449+
440450
@Override
441451
public ElementAdapter casePackage(Package element) {
442452
return new PackageAdapter(element);
Lines changed: 68 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
/*******************************************************************************
2+
* SysML 2 Pilot Implementation
3+
* Copyright (c) 2026 Model Driven Solutions, Inc.
4+
*
5+
* This program is free software: you can redistribute it and/or modify
6+
* it under the terms of the GNU Lesser General Public License as published by
7+
* the Free Software Foundation, either version 3 of the License, or
8+
* (at your option) any later version.
9+
*
10+
* This program is distributed in the hope that it will be useful,
11+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
12+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13+
* GNU Lesser General Public License for more details.
14+
*
15+
* You should have received a copy of the GNU Lesser General Public License
16+
* along with this program. If not, see <https://www.gnu.org/licenses/>.
17+
*
18+
* @license LGPL-3.0-or-later <http://spdx.org/licenses/LGPL-3.0-or-later>
19+
*
20+
*******************************************************************************/
21+
22+
package org.omg.sysml.adapter;
23+
24+
import java.util.UUID;
25+
26+
import org.eclipse.emf.ecore.resource.Resource;
27+
import org.omg.sysml.util.ElementUtil;
28+
import org.omg.sysml.lang.sysml.LibraryPackage;
29+
30+
public class LibraryPackageAdapter extends PackageAdapter {
31+
32+
public final String KERML_LIBRARY_BASE_URI = "https://www.omg.org/spec/KerML/";
33+
public final String SYSML_LIBRARY_BASE_URI = "https://www.omg.org/spec/SysML/";
34+
35+
// UUID for "NameSpace_URL", per ITU-T Rec. X.667 (10/2012), Annex D.9
36+
public final UUID UUID_NAMESPACE_URL = UUID.fromString("6ba7b811-9dad-11d1-80b4-00c04fd430c8");
37+
38+
public LibraryPackageAdapter(LibraryPackage element) {
39+
super(element);
40+
}
41+
42+
public LibraryPackage getTarget() {
43+
return (LibraryPackage)super.getTarget();
44+
}
45+
46+
/**
47+
* If this is a standard library Package, then create the elementId as a named-based UUID
48+
* using a URL constructed from the KerML or SysML base URI and the Package's name.
49+
*/
50+
@Override
51+
public String createElementId() {
52+
LibraryPackage target = getTarget();
53+
54+
if (target.isStandard()) {
55+
Resource resource = target.eResource();
56+
if (resource != null) {
57+
String uri = resource.getURI().toString().contains("Kernel")? KERML_LIBRARY_BASE_URI: SYSML_LIBRARY_BASE_URI;
58+
String qualifiedName = target.getQualifiedName();
59+
if (qualifiedName != null) {
60+
return ElementUtil.constructNameUUID(UUID_NAMESPACE_URL, uri + qualifiedName).toString();
61+
}
62+
}
63+
}
64+
65+
return super.createElementId();
66+
}
67+
68+
}

org.omg.sysml/src/org/omg/sysml/adapter/NamespaceAdapter.java

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
/*******************************************************************************
22
* SysML 2 Pilot Implementation
3-
* Copyright (c) 2021, 2024, 2025 Model Driven Solutions, Inc.
3+
* Copyright (c) 2021, 2024, 2025, 2026 Model Driven Solutions, Inc.
44
*
55
* This program is free software: you can redistribute it and/or modify
66
* it under the terms of the GNU Lesser General Public License as published by
@@ -22,6 +22,7 @@
2222
package org.omg.sysml.adapter;
2323

2424
import java.util.Set;
25+
import java.util.UUID;
2526
import java.util.stream.Collectors;
2627

2728
import org.eclipse.emf.common.util.BasicEList;
@@ -34,6 +35,7 @@
3435
import org.omg.sysml.lang.sysml.Namespace;
3536
import org.omg.sysml.lang.sysml.SysMLPackage;
3637
import org.omg.sysml.lang.sysml.VisibilityKind;
38+
import org.omg.sysml.util.ElementUtil;
3739
import org.omg.sysml.util.NamespaceUtil;
3840
import org.omg.sysml.util.NonNotifyingEObjectEList;
3941

@@ -49,6 +51,31 @@ public Namespace getTarget() {
4951

5052
// Additional operations
5153

54+
/**
55+
* If the Namespace is the root Namespace of a standard library package, then give it a stable elementId.
56+
*/
57+
@Override
58+
protected String createElementId() {
59+
Namespace target = getTarget();
60+
61+
if (target.getOwningRelationship() == null) {
62+
EList<Element> ownedMembers = target.getOwnedMember();
63+
if (!ownedMembers.isEmpty()) {
64+
Element firstOwnedMember = ownedMembers.get(0);
65+
if (ElementUtil.isStandardLibraryElement(firstOwnedMember) &&
66+
firstOwnedMember.libraryNamespace() == firstOwnedMember) {
67+
String qualifiedName = firstOwnedMember.getQualifiedName();
68+
if (qualifiedName != null) {
69+
UUID namespaceUUID = UUID.fromString(firstOwnedMember.getElementId());
70+
return ElementUtil.constructNameUUID(namespaceUUID, qualifiedName + "/owner").toString();
71+
}
72+
}
73+
}
74+
}
75+
76+
return super.createElementId();
77+
}
78+
5279
public EList<Membership> getMembershipsOfVisibility(VisibilityKind visibility, Set<Namespace> excluded) {
5380
Namespace target = getTarget();
5481

@@ -127,6 +154,7 @@ public EList<Membership> setImportedMembership(EList<Membership> importedMembers
127154

128155
@Override
129156
public void clearCaches() {
157+
super.clearCaches();
130158
importedMembership = null;
131159
}
132160

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
/*******************************************************************************
2+
* SysML 2 Pilot Implementation
3+
* Copyright (c) 2026 Model Driven Solutions, Inc.
4+
*
5+
* This program is free software: you can redistribute it and/or modify
6+
* it under the terms of the GNU Lesser General Public License as published by
7+
* the Free Software Foundation, either version 3 of the License, or
8+
* (at your option) any later version.
9+
*
10+
* This program is distributed in the hope that it will be useful,
11+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
12+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13+
* GNU Lesser General Public License for more details.
14+
*
15+
* You should have received a copy of theGNU Lesser General Public License
16+
* along with this program. If not, see <https://www.gnu.org/licenses/>.
17+
*
18+
* @license LGPL-3.0-or-later <http://spdx.org/licenses/LGPL-3.0-or-later>
19+
*
20+
*******************************************************************************/
21+
22+
package org.omg.sysml.adapter;
23+
24+
import java.util.UUID;
25+
26+
import org.omg.sysml.lang.sysml.Element;
27+
import org.omg.sysml.lang.sysml.OwningMembership;
28+
import org.omg.sysml.util.ElementUtil;
29+
30+
public class OwningMembershipAdapter extends MembershipAdapter {
31+
32+
public OwningMembershipAdapter(OwningMembership element) {
33+
super(element);
34+
}
35+
36+
@Override
37+
public OwningMembership getTarget() {
38+
return (OwningMembership)super.getTarget();
39+
}
40+
41+
/**
42+
* If the OwningMembership is not itself a standard library Element, but its ownedMemberElement
43+
* is a standard library Package, then give the OwningMembership a stable elementId anyway.
44+
* (This will give a stable elementID to the owningMembership of a top-level standard library Package.)
45+
*/
46+
@Override
47+
public String createElementId() {
48+
OwningMembership target = getTarget();
49+
50+
Element ownedMemberElement = target.getOwnedMemberElement();
51+
if (!ElementUtil.isStandardLibraryElement(target) &&
52+
ElementUtil.isStandardLibraryElement(ownedMemberElement) &&
53+
ownedMemberElement.libraryNamespace() == ownedMemberElement) {
54+
String path = target.path();
55+
if (path != null) {
56+
UUID namespaceUUID = UUID.fromString(ownedMemberElement.getElementId());
57+
return ElementUtil.constructNameUUID(namespaceUUID, path).toString();
58+
}
59+
}
60+
61+
return super.createElementId();
62+
}
63+
64+
}
Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,46 @@
1+
/*******************************************************************************
2+
* SysML 2 Pilot Implementation
3+
* Copyright (c) 2022, 2023, 2026 Model Driven Solutions, Inc.
4+
* Copyright (c) 2022 Siemens AG
5+
*
6+
* This program is free software: you can redistribute it and/or modify
7+
* it under the terms of the GNU Lesser General Public License as published by
8+
* the Free Software Foundation, either version 3 of the License, or
9+
* (at your option) any later version.
10+
*
11+
* This program is distributed in the hope that it will be useful,
12+
* but WITHOUT ANY WARRANTY; without even the implied warranty of
13+
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14+
* GNU Lesser General Public License for more details.
15+
*
16+
* You should have received a copy of the GNU Lesser General Public License
17+
* along with this program. If not, see <https://www.gnu.org/licenses/>.
18+
*
19+
* @license LGPL-3.0-or-later <http://spdx.org/licenses/LGPL-3.0-or-later>
20+
*
21+
*******************************************************************************/
22+
23+
package org.omg.sysml.delegate.setting;
24+
25+
import org.eclipse.emf.ecore.EStructuralFeature;
26+
import org.eclipse.emf.ecore.InternalEObject;
27+
import org.omg.sysml.lang.sysml.Element;
28+
import org.omg.sysml.util.ElementUtil;
29+
30+
public class Element_elementId_SettingDelegate extends BasicDerivedPropertySettingDelegate {
31+
32+
public Element_elementId_SettingDelegate(EStructuralFeature eStructuralFeature) {
33+
super(eStructuralFeature);
34+
}
35+
36+
@Override
37+
protected Object basicGet(InternalEObject owner) {
38+
return ElementUtil.getElementIdOf((Element) owner);
39+
}
40+
41+
@Override
42+
public void set(InternalEObject owner, Object elementId) {
43+
ElementUtil.setElementIdOf((Element)owner, (String)elementId);
44+
}
45+
46+
}

org.omg.sysml/src/org/omg/sysml/util/ElementUtil.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -323,6 +323,16 @@ public static MetadataFeature getMetaclassFeatureFor(Element element) {
323323
return element == null? null: getElementAdapter(element).getMetaclassFeature();
324324
}
325325

326+
// Element ID
327+
328+
public static String getElementIdOf(Element element) {
329+
return getElementAdapter(element).getElementId();
330+
}
331+
332+
public static void setElementIdOf(Element element, String elementId) {
333+
getElementAdapter(element).setElementId(elementId);
334+
}
335+
326336
// Parse post-processing
327337

328338
public static void postProcess(Element element) {

0 commit comments

Comments
 (0)