@emfts/codegen 0.0.1-next.8 → 0.0.2-next.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/cli/commands/generate.d.ts.map +1 -1
- package/dist/cli/commands/generate.js +12 -12
- package/dist/cli/commands/generate.js.map +1 -1
- package/dist/cli/commands/init.d.ts +6 -0
- package/dist/cli/commands/init.d.ts.map +1 -1
- package/dist/cli/commands/init.js +69 -16
- package/dist/cli/commands/init.js.map +1 -1
- package/dist/cli/import-mappings.d.ts +5 -0
- package/dist/cli/import-mappings.d.ts.map +1 -0
- package/dist/cli/import-mappings.js +16 -0
- package/dist/cli/import-mappings.js.map +1 -0
- package/dist/genconfig/GenConfig.d.ts +14 -0
- package/dist/genconfig/GenConfig.d.ts.map +1 -1
- package/dist/genconfig/GenConfig.js.map +1 -1
- package/dist/genconfig/GenConfigConverter.d.ts.map +1 -1
- package/dist/genconfig/GenConfigConverter.js +4 -1
- package/dist/genconfig/GenConfigConverter.js.map +1 -1
- package/dist/genconfig/GenConfigLoader.d.ts +4 -4
- package/dist/genconfig/GenConfigLoader.d.ts.map +1 -1
- package/dist/genconfig/GenConfigLoader.js +38 -27
- package/dist/genconfig/GenConfigLoader.js.map +1 -1
- package/dist/genconfig/model/ClassDefaults.d.ts +12 -0
- package/dist/genconfig/model/ClassDefaults.d.ts.map +1 -0
- package/dist/genconfig/model/ClassDefaults.js +8 -0
- package/dist/genconfig/model/ClassDefaults.js.map +1 -0
- package/dist/genconfig/model/ClassDefaultsImpl.d.ts +46 -0
- package/dist/genconfig/model/ClassDefaultsImpl.d.ts.map +1 -0
- package/dist/genconfig/model/ClassDefaultsImpl.js +205 -0
- package/dist/genconfig/model/ClassDefaultsImpl.js.map +1 -0
- package/dist/genconfig/model/ClassOverride.d.ts +15 -0
- package/dist/genconfig/model/ClassOverride.d.ts.map +1 -0
- package/dist/genconfig/model/ClassOverride.js +8 -0
- package/dist/genconfig/model/ClassOverride.js.map +1 -0
- package/dist/genconfig/model/ClassOverrideImpl.d.ts +53 -0
- package/dist/genconfig/model/ClassOverrideImpl.d.ts.map +1 -0
- package/dist/genconfig/model/ClassOverrideImpl.js +248 -0
- package/dist/genconfig/model/ClassOverrideImpl.js.map +1 -0
- package/dist/genconfig/model/FeatureDefaults.d.ts +11 -0
- package/dist/genconfig/model/FeatureDefaults.d.ts.map +1 -0
- package/dist/genconfig/model/FeatureDefaults.js +8 -0
- package/dist/genconfig/model/FeatureDefaults.js.map +1 -0
- package/dist/genconfig/model/FeatureDefaultsImpl.d.ts +39 -0
- package/dist/genconfig/model/FeatureDefaultsImpl.d.ts.map +1 -0
- package/dist/genconfig/model/FeatureDefaultsImpl.js +136 -0
- package/dist/genconfig/model/FeatureDefaultsImpl.js.map +1 -0
- package/dist/genconfig/model/FeatureOverride.d.ts +14 -0
- package/dist/genconfig/model/FeatureOverride.d.ts.map +1 -0
- package/dist/genconfig/model/FeatureOverride.js +8 -0
- package/dist/genconfig/model/FeatureOverride.js.map +1 -0
- package/dist/genconfig/model/FeatureOverrideImpl.d.ts +51 -0
- package/dist/genconfig/model/FeatureOverrideImpl.d.ts.map +1 -0
- package/dist/genconfig/model/FeatureOverrideImpl.js +241 -0
- package/dist/genconfig/model/FeatureOverrideImpl.js.map +1 -0
- package/dist/genconfig/model/GenConfig.d.ts +21 -0
- package/dist/genconfig/model/GenConfig.d.ts.map +1 -0
- package/dist/genconfig/model/GenConfig.js +8 -0
- package/dist/genconfig/model/GenConfig.js.map +1 -0
- package/dist/genconfig/model/GenConfigFactory.d.ts +56 -0
- package/dist/genconfig/model/GenConfigFactory.d.ts.map +1 -0
- package/dist/genconfig/model/GenConfigFactory.js +108 -0
- package/dist/genconfig/model/GenConfigFactory.js.map +1 -0
- package/dist/genconfig/model/GenConfigImpl.d.ts +62 -0
- package/dist/genconfig/model/GenConfigImpl.d.ts.map +1 -0
- package/dist/genconfig/model/GenConfigImpl.js +283 -0
- package/dist/genconfig/model/GenConfigImpl.js.map +1 -0
- package/dist/genconfig/model/GenConfigPackage.d.ts +68 -0
- package/dist/genconfig/model/GenConfigPackage.d.ts.map +1 -0
- package/dist/genconfig/model/GenConfigPackage.js +463 -0
- package/dist/genconfig/model/GenConfigPackage.js.map +1 -0
- package/dist/genconfig/model/GenerationMode.d.ts +19 -0
- package/dist/genconfig/model/GenerationMode.d.ts.map +1 -0
- package/dist/genconfig/model/GenerationMode.js +34 -0
- package/dist/genconfig/model/GenerationMode.js.map +1 -0
- package/dist/genconfig/model/GenerationSettings.d.ts +14 -0
- package/dist/genconfig/model/GenerationSettings.d.ts.map +1 -0
- package/dist/genconfig/model/GenerationSettings.js +8 -0
- package/dist/genconfig/model/GenerationSettings.js.map +1 -0
- package/dist/genconfig/model/GenerationSettingsImpl.d.ts +51 -0
- package/dist/genconfig/model/GenerationSettingsImpl.d.ts.map +1 -0
- package/dist/genconfig/model/GenerationSettingsImpl.js +241 -0
- package/dist/genconfig/model/GenerationSettingsImpl.js.map +1 -0
- package/dist/genconfig/model/PackageSettings.d.ts +13 -0
- package/dist/genconfig/model/PackageSettings.d.ts.map +1 -0
- package/dist/genconfig/model/PackageSettings.js +8 -0
- package/dist/genconfig/model/PackageSettings.js.map +1 -0
- package/dist/genconfig/model/PackageSettingsImpl.d.ts +50 -0
- package/dist/genconfig/model/PackageSettingsImpl.d.ts.map +1 -0
- package/dist/genconfig/model/PackageSettingsImpl.js +240 -0
- package/dist/genconfig/model/PackageSettingsImpl.js.map +1 -0
- package/dist/genconfig/model/PropertyMode.d.ts +19 -0
- package/dist/genconfig/model/PropertyMode.d.ts.map +1 -0
- package/dist/genconfig/model/PropertyMode.js +34 -0
- package/dist/genconfig/model/PropertyMode.js.map +1 -0
- package/dist/genconfig/model/ReferencedPackage.d.ts +10 -0
- package/dist/genconfig/model/ReferencedPackage.d.ts.map +1 -0
- package/dist/genconfig/model/ReferencedPackage.js +8 -0
- package/dist/genconfig/model/ReferencedPackage.js.map +1 -0
- package/dist/genconfig/model/ReferencedPackageImpl.d.ts +38 -0
- package/dist/genconfig/model/ReferencedPackageImpl.d.ts.map +1 -0
- package/dist/genconfig/model/ReferencedPackageImpl.js +135 -0
- package/dist/genconfig/model/ReferencedPackageImpl.js.map +1 -0
- package/dist/genconfig/model/index.d.ts +21 -0
- package/dist/genconfig/model/index.d.ts.map +1 -0
- package/dist/genconfig/model/index.js +22 -0
- package/dist/genconfig/model/index.js.map +1 -0
- package/dist/generator/CodeGenerator.d.ts.map +1 -1
- package/dist/generator/CodeGenerator.js +2 -1
- package/dist/generator/CodeGenerator.js.map +1 -1
- package/dist/generator/ImportResolver.d.ts.map +1 -1
- package/dist/generator/ImportResolver.js +28 -5
- package/dist/generator/ImportResolver.js.map +1 -1
- package/dist/generator/TypeMapper.d.ts +2 -0
- package/dist/generator/TypeMapper.d.ts.map +1 -1
- package/dist/generator/TypeMapper.js +48 -3
- package/dist/generator/TypeMapper.js.map +1 -1
- package/dist/generator/modes/BaseGenerator.d.ts +6 -0
- package/dist/generator/modes/BaseGenerator.d.ts.map +1 -1
- package/dist/generator/modes/BaseGenerator.js +21 -1
- package/dist/generator/modes/BaseGenerator.js.map +1 -1
- package/dist/generator/modes/DecoratorGenerator.d.ts +5 -0
- package/dist/generator/modes/DecoratorGenerator.d.ts.map +1 -1
- package/dist/generator/modes/DecoratorGenerator.js +11 -2
- package/dist/generator/modes/DecoratorGenerator.js.map +1 -1
- package/dist/generator/modes/EmfGenerator.d.ts +1 -0
- package/dist/generator/modes/EmfGenerator.d.ts.map +1 -1
- package/dist/generator/modes/EmfGenerator.js +12 -4
- package/dist/generator/modes/EmfGenerator.js.map +1 -1
- package/dist/genmodel/GenModel.d.ts +2 -0
- package/dist/genmodel/GenModel.d.ts.map +1 -1
- package/dist/genmodel/GenModel.js.map +1 -1
- package/dist/index.js +15 -2
- package/dist/index.js.map +1 -1
- package/dist/loader/EcoreLoader.d.ts +4 -0
- package/dist/loader/EcoreLoader.d.ts.map +1 -1
- package/dist/loader/EcoreLoader.js +20 -0
- package/dist/loader/EcoreLoader.js.map +1 -1
- package/dist/templates/partials/decorator/class-file.ejs +99 -27
- package/dist/templates/partials/decorator/enum-file.ejs +1 -1
- package/dist/templates/partials/decorator/interface-file.ejs +1 -7
- package/dist/templates/partials/decorator/model-annotations.ejs +7 -6
- package/dist/templates/partials/decorator/package-file.ejs +4 -2
- package/dist/templates/partials/emf/class-file.ejs +97 -17
- package/dist/templates/partials/emf/factory-file.ejs +3 -3
- package/dist/templates/partials/emf/index-file.ejs +12 -6
- package/dist/templates/partials/emf/interface-file.ejs +5 -0
- package/dist/templates/partials/emf/package-file.ejs +42 -12
- package/dist/templates/partials/plain/class-file.ejs +1 -7
- package/dist/templates/partials/plain/interface-file.ejs +1 -7
- package/dist/templates/partials/plain/package-file.ejs +1 -1
- package/model/genconfig.ecore +21 -0
- package/model/genconfig.genconfig.xmi +11 -0
- package/package.json +3 -2
|
@@ -2,17 +2,87 @@
|
|
|
2
2
|
|
|
3
3
|
<%# Generate imports for referenced types -%>
|
|
4
4
|
<%
|
|
5
|
+
// GenModel documentation of a model element (class, feature, ...)
|
|
6
|
+
function getDocumentation(element) {
|
|
7
|
+
const ann = element?.getEAnnotation?.('http://www.eclipse.org/emf/2002/GenModel');
|
|
8
|
+
const doc = ann?.getDetails?.()?.getByKey?.('documentation');
|
|
9
|
+
return typeof doc === 'string' && doc.length > 0 ? doc : null;
|
|
10
|
+
}
|
|
11
|
+
// Custom decorator annotations (#31): an eAnnotation source of the form
|
|
12
|
+
// '<importable-specifier>/<DecoratorName>' (not an EMF source URI) becomes an
|
|
13
|
+
// import plus a decorator application with the details as options object
|
|
14
|
+
function getCustomDecorators(element) {
|
|
15
|
+
const decorators = [];
|
|
16
|
+
for (const ann of element?.getEAnnotations?.() ?? []) {
|
|
17
|
+
const source = ann.getSource?.();
|
|
18
|
+
if (!source || source.startsWith('http://') || source.startsWith('https://')) continue;
|
|
19
|
+
const slashIdx = source.lastIndexOf('/');
|
|
20
|
+
if (slashIdx <= 0) continue;
|
|
21
|
+
const name = source.substring(slashIdx + 1);
|
|
22
|
+
if (!/^[A-Za-z_$][A-Za-z0-9_$]*$/.test(name)) continue;
|
|
23
|
+
const options = [];
|
|
24
|
+
for (const entry of ann.getDetails?.() ?? []) {
|
|
25
|
+
const key = entry.eGet?.(entry.eClass().getEStructuralFeature('key'));
|
|
26
|
+
const value = entry.eGet?.(entry.eClass().getEStructuralFeature('value'));
|
|
27
|
+
if (key == null) continue;
|
|
28
|
+
const keyOut = /^[A-Za-z_$][A-Za-z0-9_$]*$/.test(key) ? key : JSON.stringify(key);
|
|
29
|
+
options.push(`${keyOut}: ${JSON.stringify(value ?? '')}`);
|
|
30
|
+
}
|
|
31
|
+
decorators.push({ name, specifier: source.substring(0, slashIdx), options: `{${options.join(', ')}}` });
|
|
32
|
+
}
|
|
33
|
+
return decorators;
|
|
34
|
+
}
|
|
35
|
+
// Determine which of the annotation decorators the class actually uses (#32)
|
|
36
|
+
const classDoc = getDocumentation(eClass);
|
|
37
|
+
let usesDocumentation = !!classDoc;
|
|
38
|
+
let usesAttribute = false, usesReference = false, usesEnum = false;
|
|
39
|
+
for (const genFeature of features) {
|
|
40
|
+
const f = genFeature.ecoreFeature;
|
|
41
|
+
if (getDocumentation(f)) usesDocumentation = true;
|
|
42
|
+
if (f.getEType() && typeMapper.isEEnum(f.getEType())) usesEnum = true;
|
|
43
|
+
else if (typeMapper.isReference(f)) usesReference = true;
|
|
44
|
+
else usesAttribute = true;
|
|
45
|
+
}
|
|
46
|
+
for (const genOp of operations) {
|
|
47
|
+
if (getDocumentation(genOp.ecoreOperation)) usesDocumentation = true;
|
|
48
|
+
}
|
|
49
|
+
const annotationNames = [
|
|
50
|
+
...(usesDocumentation ? ['Documentation'] : []),
|
|
51
|
+
...(usesAttribute ? ['Attribute'] : []),
|
|
52
|
+
'ModelClass',
|
|
53
|
+
...(usesReference ? ['Reference'] : []),
|
|
54
|
+
...(usesEnum ? ['Enum'] : [])
|
|
55
|
+
];
|
|
56
|
+
|
|
57
|
+
// Merge all imports per module specifier: resolved type imports, the used
|
|
58
|
+
// annotation decorators, and custom decorator imports (#31, #32)
|
|
59
|
+
const mergedImports = new Map();
|
|
60
|
+
function addImport(specifier, name) {
|
|
61
|
+
if (!mergedImports.has(specifier)) mergedImports.set(specifier, new Set());
|
|
62
|
+
mergedImports.get(specifier).add(name);
|
|
63
|
+
}
|
|
5
64
|
const imports = importResolver.resolveImportsForClass(eClass, genPackage, 'decorator');
|
|
6
65
|
for (const imp of imports) {
|
|
7
66
|
if (imp.typeName !== className && !imp.typeName.includes(',')) {
|
|
67
|
+
addImport(imp.importPath, imp.typeName);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
for (const name of annotationNames) addImport(annotationsImport, name);
|
|
71
|
+
for (const genOp of operations) {
|
|
72
|
+
for (const dec of getCustomDecorators(genOp.ecoreOperation)) {
|
|
73
|
+
addImport(dec.specifier, dec.name);
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
for (const [specifier, names] of mergedImports) {
|
|
8
77
|
-%>
|
|
9
|
-
import { <%-
|
|
78
|
+
import { <%- [...names].join(', ') %> } from '<%- specifier %>';
|
|
10
79
|
<%
|
|
11
|
-
}
|
|
12
80
|
}
|
|
13
81
|
-%>
|
|
14
|
-
import { Documentation, Attribute, ModelClass, Reference, Enum } from './ModelAnnotations';
|
|
15
82
|
|
|
83
|
+
<% if (classDoc) { -%>
|
|
84
|
+
@Documentation(<%- JSON.stringify(classDoc) %>)
|
|
85
|
+
<% } -%>
|
|
16
86
|
@ModelClass({ type: '<%- nsURI %>#//<%- className %>' })
|
|
17
87
|
export <% if (isAbstract) { %>abstract <% } %>class <%- className %><%
|
|
18
88
|
if (typeParameters && typeParameters.length > 0) {
|
|
@@ -25,8 +95,11 @@ if (typeParameters && typeParameters.length > 0) {
|
|
|
25
95
|
if (superTypes && superTypes.length > 0) {
|
|
26
96
|
const superNames = [];
|
|
27
97
|
for (const st of superTypes) {
|
|
28
|
-
|
|
29
|
-
|
|
98
|
+
// getName helper also resolves the name of an unresolved proxy from its
|
|
99
|
+
// URI fragment - a cross-package supertype must not lose its extends (#30)
|
|
100
|
+
const stName = getName(st);
|
|
101
|
+
if (stName) {
|
|
102
|
+
superNames.push(stName);
|
|
30
103
|
}
|
|
31
104
|
}
|
|
32
105
|
if (superNames.length > 0) {
|
|
@@ -38,37 +111,31 @@ if (superTypes && superTypes.length > 0) {
|
|
|
38
111
|
const feature = genFeature.ecoreFeature;
|
|
39
112
|
const featureName = feature.getName();
|
|
40
113
|
const featureType = typeMapper.mapFeatureBaseType(feature);
|
|
114
|
+
// Decorator argument is a runtime type NAME for metadata lookups -
|
|
115
|
+
// generic type arguments must not leak into it (#29). Derived from the
|
|
116
|
+
// mapped type, because an unresolved cross-package eType proxy has no getName
|
|
117
|
+
const decoratorTypeName = featureType.split('<')[0];
|
|
41
118
|
const fullType = typeMapper.mapFeature(feature);
|
|
42
119
|
const defaultValue = typeMapper.getDefaultValue(feature);
|
|
43
120
|
const isMany = feature.isMany();
|
|
44
121
|
const isRef = typeMapper.isReference(feature);
|
|
45
122
|
const isEnum = feature.getEType() && typeMapper.isEEnum(feature.getEType());
|
|
46
123
|
|
|
47
|
-
//
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
for (const ann of feature.getEAnnotations()) {
|
|
51
|
-
const annSource = typeof ann.getSource === 'function' ? ann.getSource() : ann.source;
|
|
52
|
-
if (annSource === 'http://www.eclipse.org/emf/2002/GenModel') {
|
|
53
|
-
const details = typeof ann.getDetails === 'function' ? ann.getDetails() : ann.details;
|
|
54
|
-
if (details && details.get) {
|
|
55
|
-
doc = details.get('documentation');
|
|
56
|
-
}
|
|
57
|
-
}
|
|
58
|
-
}
|
|
59
|
-
}
|
|
124
|
+
// GenModel documentation as @Documentation decorator; JSON.stringify keeps
|
|
125
|
+
// multiline values and quotes a valid string literal
|
|
126
|
+
const doc = getDocumentation(feature);
|
|
60
127
|
if (doc) {
|
|
61
128
|
-%>
|
|
62
|
-
@Documentation(
|
|
129
|
+
@Documentation(<%- JSON.stringify(doc) %>)
|
|
63
130
|
<%
|
|
64
131
|
}
|
|
65
132
|
if (isEnum) {
|
|
66
133
|
-%>
|
|
67
|
-
@Enum('<%-
|
|
134
|
+
@Enum('<%- decoratorTypeName %>')
|
|
68
135
|
<%
|
|
69
136
|
} else if (isRef) {
|
|
70
137
|
-%>
|
|
71
|
-
@Reference('<%-
|
|
138
|
+
@Reference('<%- decoratorTypeName %>')
|
|
72
139
|
<%
|
|
73
140
|
} else {
|
|
74
141
|
-%>
|
|
@@ -83,14 +150,19 @@ if (superTypes && superTypes.length > 0) {
|
|
|
83
150
|
const op = genOp.ecoreOperation;
|
|
84
151
|
const opName = op.getName();
|
|
85
152
|
const returnType = op.getEType() ? typeMapper.mapClassifier(op.getEType()) : 'void';
|
|
86
|
-
const
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
153
|
+
const opDoc = getDocumentation(op);
|
|
154
|
+
if (opDoc) {
|
|
155
|
+
-%>
|
|
156
|
+
@Documentation(<%- JSON.stringify(opDoc) %>)
|
|
157
|
+
<%
|
|
158
|
+
}
|
|
159
|
+
for (const dec of getCustomDecorators(op)) {
|
|
160
|
+
-%>
|
|
161
|
+
@<%- dec.name %>(<%- dec.options %>)
|
|
162
|
+
<%
|
|
91
163
|
}
|
|
92
164
|
-%>
|
|
93
|
-
<%- opName %>(<%-
|
|
165
|
+
<%- opName %>(<%- mapParams(op) %>): <%- returnType %> {
|
|
94
166
|
throw new Error('<%- opName %> not implemented');
|
|
95
167
|
}
|
|
96
168
|
|
|
@@ -28,7 +28,7 @@ export enum <%- enumName %> {
|
|
|
28
28
|
const literal = literals[i];
|
|
29
29
|
const literalName = getLiteralProp(literal, 'literal') || getLiteralProp(literal, 'name');
|
|
30
30
|
const literalValue = getLiteralProp(literal, 'value');
|
|
31
|
-
const value = useStringValues ?
|
|
31
|
+
const value = useStringValues ? JSON.stringify(literalName) : literalValue;
|
|
32
32
|
-%>
|
|
33
33
|
<%- getLiteralProp(literal, 'name') %> = <%- value %><% if (i < literals.length - 1) { %>,<% } %>
|
|
34
34
|
<% } -%>
|
|
@@ -49,13 +49,7 @@ if (superTypes && superTypes.length > 0) {
|
|
|
49
49
|
const op = genOp.ecoreOperation;
|
|
50
50
|
const opName = op.getName();
|
|
51
51
|
const returnType = op.getEType() ? typeMapper.mapClassifier(op.getEType()) : 'void';
|
|
52
|
-
const params = [];
|
|
53
|
-
for (const param of op.getEParameters()) {
|
|
54
|
-
const paramName = param.getName();
|
|
55
|
-
const paramType = typeMapper.mapClassifier(param.getEType());
|
|
56
|
-
params.push(`${paramName}: ${paramType}`);
|
|
57
|
-
}
|
|
58
52
|
-%>
|
|
59
|
-
<%- opName %>(<%-
|
|
53
|
+
<%- opName %>(<%- mapParams(op) %>): <%- returnType %>;
|
|
60
54
|
<% } -%>
|
|
61
55
|
}
|
|
@@ -2,12 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
import 'reflect-metadata';
|
|
4
4
|
|
|
5
|
-
// Metadata keys
|
|
6
|
-
|
|
7
|
-
const
|
|
8
|
-
const
|
|
9
|
-
const
|
|
10
|
-
const
|
|
5
|
+
// Metadata keys: Symbol.for() so every generated copy of this file shares
|
|
6
|
+
// the same identities and cross-package metadata readers see all models (#26)
|
|
7
|
+
const MODEL_CLASS_KEY = Symbol.for('emfts.modelClass');
|
|
8
|
+
const ATTRIBUTE_KEY = Symbol.for('emfts.attribute');
|
|
9
|
+
const REFERENCE_KEY = Symbol.for('emfts.reference');
|
|
10
|
+
const ENUM_KEY = Symbol.for('emfts.enum');
|
|
11
|
+
const DOCUMENTATION_KEY = Symbol.for('emfts.documentation');
|
|
11
12
|
|
|
12
13
|
/**
|
|
13
14
|
* Decorator for model classes
|
|
@@ -2,6 +2,8 @@
|
|
|
2
2
|
|
|
3
3
|
// Re-export all types from this package
|
|
4
4
|
<% for (const exp of exports) { -%>
|
|
5
|
-
export * from './<%- exp
|
|
5
|
+
export * from './<%- exp %>.js';
|
|
6
|
+
<% } -%>
|
|
7
|
+
<% if (!annotationsPackage) { -%>
|
|
8
|
+
export * from './ModelAnnotations.js';
|
|
6
9
|
<% } -%>
|
|
7
|
-
export * from './ModelAnnotations';
|
|
@@ -4,9 +4,43 @@
|
|
|
4
4
|
const imports = importResolver.resolveImportsForClass(eClass, genPackage, 'emf');
|
|
5
5
|
const hardcodedCoreTypes = ['BasicEObject', 'EClass', 'EStructuralFeature'];
|
|
6
6
|
const coreTypeImports = ['EClass', 'EStructuralFeature'];
|
|
7
|
+
const coreValueImports = [];
|
|
7
8
|
const typeOnlyImports = [];
|
|
8
9
|
const valueImports = [];
|
|
9
10
|
const importedNames = new Set();
|
|
11
|
+
// Check if any feature is many-valued (needs EList imports)
|
|
12
|
+
const useEList = typeMapper.useEList;
|
|
13
|
+
const hasManyFeature = features.some(gf => isMany(gf.ecoreFeature));
|
|
14
|
+
const hasManyMixin = (mixinFeatures || []).some(mf => isMany(mf.feature));
|
|
15
|
+
if (useEList && (hasManyFeature || hasManyMixin)) {
|
|
16
|
+
coreTypeImports.push('EList', 'EReference');
|
|
17
|
+
// Determine which factory functions are needed
|
|
18
|
+
const needsContainment = features.some(gf => isMany(gf.ecoreFeature) && isContainment(gf.ecoreFeature))
|
|
19
|
+
|| (mixinFeatures || []).some(mf => isMany(mf.feature) && isContainment(mf.feature));
|
|
20
|
+
const needsEObjectList = features.some(gf => isMany(gf.ecoreFeature) && !isContainment(gf.ecoreFeature) && typeMapper.isReference(gf.ecoreFeature))
|
|
21
|
+
|| (mixinFeatures || []).some(mf => isMany(mf.feature) && !isContainment(mf.feature) && typeMapper.isReference(mf.feature));
|
|
22
|
+
const needsBasicList = features.some(gf => isMany(gf.ecoreFeature) && typeMapper.isAttribute(gf.ecoreFeature))
|
|
23
|
+
|| (mixinFeatures || []).some(mf => isMany(mf.feature) && typeMapper.isAttribute(mf.feature));
|
|
24
|
+
if (needsContainment) coreValueImports.push('createContainmentEList');
|
|
25
|
+
if (needsEObjectList) coreValueImports.push('createEObjectEList');
|
|
26
|
+
if (needsBasicList) coreValueImports.push('createBasicEList');
|
|
27
|
+
}
|
|
28
|
+
// A type that appears in a value position of a field initializer needs a
|
|
29
|
+
// value import - `import type` is erased and `new T()` would throw at
|
|
30
|
+
// runtime (#35). Value positions: enum member access and instantiation
|
|
31
|
+
const allFeatures = [
|
|
32
|
+
...features.map(gf => gf.ecoreFeature),
|
|
33
|
+
...(mixinFeatures || []).map(mf => mf.feature)
|
|
34
|
+
];
|
|
35
|
+
function isUsedAsValue(typeName) {
|
|
36
|
+
return allFeatures.some(f => {
|
|
37
|
+
const dv = typeMapper.getDefaultValue(f);
|
|
38
|
+
if (dv === null || typeof dv !== 'string') return false;
|
|
39
|
+
return dv.startsWith(typeName + '.')
|
|
40
|
+
|| dv.startsWith('new ' + typeName + '(')
|
|
41
|
+
|| dv.startsWith('new ' + typeName + '<');
|
|
42
|
+
});
|
|
43
|
+
}
|
|
10
44
|
for (const imp of imports) {
|
|
11
45
|
if (imp.typeName === className || imp.typeName === interfaceName || imp.typeName === extendsClass) continue;
|
|
12
46
|
if (hardcodedCoreTypes.includes(imp.typeName)) continue;
|
|
@@ -16,12 +50,7 @@ for (const imp of imports) {
|
|
|
16
50
|
}
|
|
17
51
|
continue;
|
|
18
52
|
}
|
|
19
|
-
|
|
20
|
-
const usedAsValue = features.some(gf => {
|
|
21
|
-
const dv = typeMapper.getDefaultValue(gf.ecoreFeature);
|
|
22
|
-
return dv !== null && typeof dv === 'string' && dv.startsWith(imp.typeName + '.');
|
|
23
|
-
});
|
|
24
|
-
if (usedAsValue) {
|
|
53
|
+
if (isUsedAsValue(imp.typeName)) {
|
|
25
54
|
valueImports.push(imp);
|
|
26
55
|
} else {
|
|
27
56
|
typeOnlyImports.push(imp);
|
|
@@ -39,13 +68,20 @@ for (const imp of (mixinImports || [])) {
|
|
|
39
68
|
}
|
|
40
69
|
continue;
|
|
41
70
|
}
|
|
42
|
-
|
|
71
|
+
if (isUsedAsValue(imp.typeName)) {
|
|
72
|
+
valueImports.push(imp);
|
|
73
|
+
} else {
|
|
74
|
+
typeOnlyImports.push(imp);
|
|
75
|
+
}
|
|
43
76
|
importedNames.add(imp.typeName);
|
|
44
77
|
}
|
|
45
78
|
-%>
|
|
46
79
|
<% if (!extendsImport) { -%>
|
|
47
80
|
import { BasicEObject } from '@emfts/core';
|
|
48
81
|
<% } -%>
|
|
82
|
+
<% if (coreValueImports.length > 0) { -%>
|
|
83
|
+
import { <%- coreValueImports.join(', ') %> } from '@emfts/core';
|
|
84
|
+
<% } -%>
|
|
49
85
|
import type { <%- coreTypeImports.join(', ') %> } from '@emfts/core';
|
|
50
86
|
<% for (const imp of typeOnlyImports) { -%>
|
|
51
87
|
import type { <%- imp.typeName %> } from '<%- imp.importPath %>';
|
|
@@ -56,8 +92,8 @@ import { <%- imp.typeName %> } from '<%- imp.importPath %>';
|
|
|
56
92
|
<% if (extendsImport) { -%>
|
|
57
93
|
import { <%- extendsClass %> } from '<%- extendsImport %>';
|
|
58
94
|
<% } -%>
|
|
59
|
-
import type { <%- interfaceName %> } from './<%- interfaceName
|
|
60
|
-
import { <%- packagePrefix %>Package } from './<%- packagePrefix %>Package';
|
|
95
|
+
import type { <%- interfaceName %> } from './<%- interfaceName %>.js';
|
|
96
|
+
import { <%- packagePrefix %>Package } from './<%- packagePrefix %>Package.js';
|
|
61
97
|
|
|
62
98
|
/**
|
|
63
99
|
* Implementation of <%- interfaceName %>
|
|
@@ -80,14 +116,14 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
80
116
|
const defaultValue = typeMapper.getDefaultValue(feature);
|
|
81
117
|
const featureIsMany = isMany(feature);
|
|
82
118
|
-%>
|
|
83
|
-
private _<%- featureName %><% if (!featureIsMany && defaultValue === null) { %>?<% } %>: <%- featureType %><% if (defaultValue !== null) { %> = <%- defaultValue %><% } %>;
|
|
119
|
+
private _<%- featureName %><% if (useEList && featureIsMany) { %>!<% } else if (!featureIsMany && defaultValue === null) { %>?<% } %>: <%- featureType %><% if (defaultValue !== null) { %> = <%- defaultValue %><% } %>;
|
|
84
120
|
<% } -%>
|
|
85
121
|
<% for (const mf of (mixinFeatures || [])) {
|
|
86
122
|
const featureType = typeMapper.mapFeature(mf.feature);
|
|
87
123
|
const defaultValue = typeMapper.getDefaultValue(mf.feature);
|
|
88
124
|
const featureIsMany = isMany(mf.feature);
|
|
89
125
|
-%>
|
|
90
|
-
private _<%- mf.name %><% if (!featureIsMany && defaultValue === null) { %>?<% } %>: <%- featureType %><% if (defaultValue !== null) { %> = <%- defaultValue %><% } %>;
|
|
126
|
+
private _<%- mf.name %><% if (useEList && featureIsMany) { %>!<% } else if (!featureIsMany && defaultValue === null) { %>?<% } %>: <%- featureType %><% if (defaultValue !== null) { %> = <%- defaultValue %><% } %>;
|
|
91
127
|
<% } -%>
|
|
92
128
|
|
|
93
129
|
/**
|
|
@@ -104,7 +140,28 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
104
140
|
const featureType = typeMapper.mapFeature(feature);
|
|
105
141
|
const featureIsMany = isMany(feature);
|
|
106
142
|
const upperName = toUpperSnake(featureName);
|
|
143
|
+
-%>
|
|
144
|
+
<% if (useEList && featureIsMany) {
|
|
145
|
+
// EList lazy-init getter: creates the right EList on first access
|
|
146
|
+
const isRef = typeMapper.isReference(feature);
|
|
147
|
+
const isCont = isRef && isContainment(feature);
|
|
148
|
+
let factoryCall;
|
|
149
|
+
if (isCont) {
|
|
150
|
+
factoryCall = `createContainmentEList<any>(this, this.eClass().getEStructuralFeature('${featureName}') as EReference)`;
|
|
151
|
+
} else if (isRef) {
|
|
152
|
+
factoryCall = `createEObjectEList(this, this.eClass().getEStructuralFeature('${featureName}') as EReference) as unknown as ${featureType}`;
|
|
153
|
+
} else {
|
|
154
|
+
factoryCall = `createBasicEList<any>(this, this.eClass().getEStructuralFeature('${featureName}')!)`;
|
|
155
|
+
}
|
|
107
156
|
-%>
|
|
157
|
+
get <%- featureName %>(): <%- featureType %> {
|
|
158
|
+
if (!this._<%- featureName %>) {
|
|
159
|
+
this._<%- featureName %> = <%- factoryCall %>;
|
|
160
|
+
}
|
|
161
|
+
return this._<%- featureName %>;
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
<% } else { -%>
|
|
108
165
|
get <%- featureName %>(): <%- featureType %> {
|
|
109
166
|
return this._<%- featureName %><% if (!featureIsMany) { %>!<% } %>;
|
|
110
167
|
}
|
|
@@ -134,6 +191,7 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
134
191
|
<% } -%>
|
|
135
192
|
}
|
|
136
193
|
|
|
194
|
+
<% } -%>
|
|
137
195
|
<% } -%>
|
|
138
196
|
<% } -%>
|
|
139
197
|
<% for (const mf of (mixinFeatures || [])) {
|
|
@@ -177,18 +235,32 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
177
235
|
const featureID = this.eClass().getFeatureID(feature);
|
|
178
236
|
switch (featureID) {
|
|
179
237
|
<% for (const fid of featureIds) {
|
|
180
|
-
const
|
|
238
|
+
const feat = fid.feature.ecoreFeature;
|
|
239
|
+
const featureType = typeMapper.mapFeature(feat);
|
|
240
|
+
const featureName = getName(feat);
|
|
241
|
+
const featureIsMany = isMany(feat);
|
|
181
242
|
-%>
|
|
182
243
|
case <%- className %>.<%- fid.name %>:
|
|
183
|
-
|
|
244
|
+
<% if (useEList && featureIsMany) { -%>
|
|
245
|
+
this.<%- featureName %>.clear();
|
|
246
|
+
this.<%- featureName %>.addAll(newValue as any[]);
|
|
247
|
+
<% } else { -%>
|
|
248
|
+
this.<%- featureName %> = newValue as <%- featureType %>;
|
|
249
|
+
<% } -%>
|
|
184
250
|
super.eSet(feature, newValue);
|
|
185
251
|
break;
|
|
186
252
|
<% } -%>
|
|
187
253
|
<% for (const mf of (mixinFeatures || [])) {
|
|
188
254
|
const featureType = typeMapper.mapFeature(mf.feature);
|
|
255
|
+
const featureIsMany = isMany(mf.feature);
|
|
189
256
|
-%>
|
|
190
257
|
case <%- className %>.<%- mf.upperName %>:
|
|
258
|
+
<% if (useEList && featureIsMany) { -%>
|
|
259
|
+
this.<%- mf.name %>.clear();
|
|
260
|
+
this.<%- mf.name %>.addAll(newValue as any[]);
|
|
261
|
+
<% } else { -%>
|
|
191
262
|
this.<%- mf.name %> = newValue as <%- featureType %>;
|
|
263
|
+
<% } -%>
|
|
192
264
|
super.eSet(feature, newValue);
|
|
193
265
|
break;
|
|
194
266
|
<% } -%>
|
|
@@ -210,7 +282,9 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
210
282
|
const featureName = getName(feature);
|
|
211
283
|
-%>
|
|
212
284
|
case <%- className %>.<%- fid.name %>:
|
|
213
|
-
<% if (featureIsMany) { -%>
|
|
285
|
+
<% if (useEList && featureIsMany) { -%>
|
|
286
|
+
return this._<%- featureName %> !== undefined && !this._<%- featureName %>.isEmpty();
|
|
287
|
+
<% } else if (featureIsMany) { -%>
|
|
214
288
|
return this._<%- featureName %> !== undefined && this._<%- featureName %>.length > 0;
|
|
215
289
|
<% } else if (defaultValue !== null) { -%>
|
|
216
290
|
return this._<%- featureName %> !== <%- defaultValue %>;
|
|
@@ -223,7 +297,9 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
223
297
|
const defaultValue = typeMapper.getDefaultValue(mf.feature);
|
|
224
298
|
-%>
|
|
225
299
|
case <%- className %>.<%- mf.upperName %>:
|
|
226
|
-
<% if (featureIsMany) { -%>
|
|
300
|
+
<% if (useEList && featureIsMany) { -%>
|
|
301
|
+
return this._<%- mf.name %> !== undefined && !this._<%- mf.name %>.isEmpty();
|
|
302
|
+
<% } else if (featureIsMany) { -%>
|
|
227
303
|
return this._<%- mf.name %> !== undefined && this._<%- mf.name %>.length > 0;
|
|
228
304
|
<% } else if (defaultValue !== null) { -%>
|
|
229
305
|
return this._<%- mf.name %> !== <%- defaultValue %>;
|
|
@@ -249,7 +325,9 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
249
325
|
const featureName = getName(feature);
|
|
250
326
|
-%>
|
|
251
327
|
case <%- className %>.<%- fid.name %>:
|
|
252
|
-
<% if (featureIsMany) { -%>
|
|
328
|
+
<% if (useEList && featureIsMany) { -%>
|
|
329
|
+
if (this._<%- featureName %>) this._<%- featureName %>.clear();
|
|
330
|
+
<% } else if (featureIsMany) { -%>
|
|
253
331
|
this._<%- featureName %> = [];
|
|
254
332
|
<% } else if (defaultValue !== null) { -%>
|
|
255
333
|
this._<%- featureName %> = <%- defaultValue %>;
|
|
@@ -263,7 +341,9 @@ export <% if (isAbstract) { %>abstract <% } %>class <%- className %> extends <%-
|
|
|
263
341
|
const defaultValue = typeMapper.getDefaultValue(mf.feature);
|
|
264
342
|
-%>
|
|
265
343
|
case <%- className %>.<%- mf.upperName %>:
|
|
266
|
-
<% if (featureIsMany) { -%>
|
|
344
|
+
<% if (useEList && featureIsMany) { -%>
|
|
345
|
+
if (this._<%- mf.name %>) this._<%- mf.name %>.clear();
|
|
346
|
+
<% } else if (featureIsMany) { -%>
|
|
267
347
|
this._<%- mf.name %> = [];
|
|
268
348
|
<% } else if (defaultValue !== null) { -%>
|
|
269
349
|
this._<%- mf.name %> = <%- defaultValue %>;
|
|
@@ -2,13 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
import { BasicEFactory } from '@emfts/core';
|
|
4
4
|
import type { EClass, EObject } from '@emfts/core';
|
|
5
|
-
import { <%- packageName %>Package } from './<%- packageName %>Package';
|
|
5
|
+
import { <%- packageName %>Package } from './<%- packageName %>Package.js';
|
|
6
6
|
<% for (const genClass of concreteClasses) {
|
|
7
7
|
const className = genClass.ecoreClass.getName();
|
|
8
8
|
const implName = genClass.implClassName || (className + 'Impl');
|
|
9
9
|
-%>
|
|
10
|
-
import type { <%- className %> } from './<%- className
|
|
11
|
-
import { <%- implName %> } from './<%- implName
|
|
10
|
+
import type { <%- className %> } from './<%- className %>.js';
|
|
11
|
+
import { <%- implName %> } from './<%- implName %>.js';
|
|
12
12
|
<% } -%>
|
|
13
13
|
|
|
14
14
|
/**
|
|
@@ -1,29 +1,35 @@
|
|
|
1
1
|
<%- header %>
|
|
2
2
|
|
|
3
|
-
// Package and Factory
|
|
4
|
-
export { <%- packageName %>Package } from './<%- packageName %>Package';
|
|
5
|
-
|
|
3
|
+
// Package<% if (generateFactory) { %> and Factory<% } %>
|
|
4
|
+
export { <%- packageName %>Package } from './<%- packageName %>Package.js';
|
|
5
|
+
<% if (generateFactory) { -%>
|
|
6
|
+
export { <%- packageName %>Factory } from './<%- packageName %>Factory.js';
|
|
7
|
+
<% } -%>
|
|
6
8
|
|
|
9
|
+
<% if (generateInterfaces) { -%>
|
|
7
10
|
// Interfaces
|
|
8
11
|
<% for (const genClass of genClasses) {
|
|
9
12
|
const name = getName(genClass.ecoreClass);
|
|
10
13
|
-%>
|
|
11
|
-
export type { <%- name %> } from './<%- name
|
|
14
|
+
export type { <%- name %> } from './<%- name %>.js';
|
|
15
|
+
<% } -%>
|
|
12
16
|
<% } -%>
|
|
13
17
|
|
|
18
|
+
<% if (generateClasses) { -%>
|
|
14
19
|
// Implementations (including abstract classes, as they're extended by subclasses)
|
|
15
20
|
<% for (const genClass of genClasses) {
|
|
16
21
|
if (!checkIsInterface(genClass.ecoreClass)) {
|
|
17
22
|
const implName = genClass.implClassName || (getName(genClass.ecoreClass) + 'Impl');
|
|
18
23
|
-%>
|
|
19
|
-
export { <%- implName %> } from './<%- implName
|
|
24
|
+
export { <%- implName %> } from './<%- implName %>.js';
|
|
20
25
|
<%
|
|
21
26
|
}
|
|
22
27
|
} -%>
|
|
28
|
+
<% } -%>
|
|
23
29
|
|
|
24
30
|
// Enums
|
|
25
31
|
<% for (const genEnum of genEnums) {
|
|
26
32
|
const name = getName(genEnum.ecoreEnum);
|
|
27
33
|
-%>
|
|
28
|
-
export { <%- name %>, get<%- name %>, get<%- name %>ByLiteral } from './<%- name
|
|
34
|
+
export { <%- name %>, get<%- name %>, get<%- name %>ByLiteral } from './<%- name %>.js';
|
|
29
35
|
<% } -%>
|
|
@@ -4,6 +4,11 @@
|
|
|
4
4
|
const imports = importResolver.resolveImportsForClass(eClass, genPackage, 'emf');
|
|
5
5
|
const coreTypeImports = ['EObject'];
|
|
6
6
|
const otherTypeImports = [];
|
|
7
|
+
// Add EList import if any feature is many-valued and useEList is on
|
|
8
|
+
const useEList = typeMapper.useEList;
|
|
9
|
+
if (useEList && features.some(gf => isMany(gf.ecoreFeature))) {
|
|
10
|
+
coreTypeImports.push('EList');
|
|
11
|
+
}
|
|
7
12
|
for (const imp of imports) {
|
|
8
13
|
if (imp.typeName === interfaceName) continue;
|
|
9
14
|
if (imp.importPath === '@emfts/core') {
|
|
@@ -62,7 +62,7 @@ function typeRefExpr(classifier, castTo) {
|
|
|
62
62
|
// External dependency package — resolve via EPackageRegistry
|
|
63
63
|
const depNsURI = getClassifierNsURI(classifier);
|
|
64
64
|
if (depNsURI) {
|
|
65
|
-
return "
|
|
65
|
+
return "requireEPackage('" + depNsURI + "').getEClassifier('" + typeName + "')!" + cast;
|
|
66
66
|
}
|
|
67
67
|
return "getEcorePackage().getEClassifier('" + typeName + "')!" + cast;
|
|
68
68
|
}
|
|
@@ -80,7 +80,7 @@ for (const genClass of genClasses) {
|
|
|
80
80
|
}
|
|
81
81
|
for (const genFeature of genClass.genFeatures) {
|
|
82
82
|
const eType = getEType(genFeature.ecoreFeature);
|
|
83
|
-
if (eType &&
|
|
83
|
+
if (eType && !isLocalClassifier(eType)) {
|
|
84
84
|
if (isEcoreClassifier(eType)) { needsEcoreImport = true; }
|
|
85
85
|
else { needsRegistryImport = true; }
|
|
86
86
|
}
|
|
@@ -88,12 +88,30 @@ for (const genClass of genClasses) {
|
|
|
88
88
|
}
|
|
89
89
|
-%>
|
|
90
90
|
<%
|
|
91
|
-
|
|
91
|
+
// EPackageRegistry is always needed: the package registers itself under its
|
|
92
|
+
// nsURI so that other generated packages can resolve their references (#36)
|
|
93
|
+
const coreImports = ['BasicEPackage', 'BasicEClass', 'BasicEAttribute', 'BasicEReference', 'EPackageRegistry'];
|
|
92
94
|
if (needsEcoreImport) coreImports.push('getEcorePackage');
|
|
93
|
-
if (needsRegistryImport) coreImports.push('EPackageRegistry');
|
|
94
95
|
-%>
|
|
95
96
|
import { <%- coreImports.join(', ') %> } from '@emfts/core';
|
|
96
97
|
import type { EClass, EAttribute, EReference, EEnum } from '@emfts/core';
|
|
98
|
+
<% if (generateFactory) { -%>
|
|
99
|
+
import { <%- packageName %>Factory } from './<%- packageName %>Factory.js';
|
|
100
|
+
<% } -%>
|
|
101
|
+
<% if (needsRegistryImport) { -%>
|
|
102
|
+
|
|
103
|
+
/**
|
|
104
|
+
* Resolve a dependency package from the registry, failing with an actionable
|
|
105
|
+
* message instead of a null dereference when it is not registered yet
|
|
106
|
+
*/
|
|
107
|
+
function requireEPackage(nsURI: string) {
|
|
108
|
+
const pkg = EPackageRegistry.INSTANCE.getEPackage(nsURI);
|
|
109
|
+
if (!pkg) {
|
|
110
|
+
throw new Error(`EPackage '${nsURI}' is not registered. Access the eINSTANCE of that model's generated package (or register it via EPackageRegistry.INSTANCE.registerPackage) before initializing <%- packageName %>Package.`);
|
|
111
|
+
}
|
|
112
|
+
return pkg;
|
|
113
|
+
}
|
|
114
|
+
<% } -%>
|
|
97
115
|
|
|
98
116
|
/**
|
|
99
117
|
* <%- packageName %> Package
|
|
@@ -138,6 +156,15 @@ export class <%- packageName %>Package extends BasicEPackage {
|
|
|
138
156
|
* Initialize package contents
|
|
139
157
|
*/
|
|
140
158
|
private init(): void {
|
|
159
|
+
// Register this package under its nsURI so other generated packages can
|
|
160
|
+
// resolve their cross-package references from the registry (#36).
|
|
161
|
+
// eINSTANCE is already assigned at this point
|
|
162
|
+
EPackageRegistry.INSTANCE.set(<%- packageName %>Package.eNS_URI, this);
|
|
163
|
+
<% if (generateFactory) { -%>
|
|
164
|
+
// Wire the generated factory so loaded/created instances are typed Impls.
|
|
165
|
+
this.setEFactoryInstance(<%- packageName %>Factory.eINSTANCE);
|
|
166
|
+
<% } -%>
|
|
167
|
+
|
|
141
168
|
<% for (const genClass of genClasses) {
|
|
142
169
|
const eClass = genClass.ecoreClass;
|
|
143
170
|
const className = getName(eClass);
|
|
@@ -195,7 +222,9 @@ export class <%- packageName %>Package extends BasicEPackage {
|
|
|
195
222
|
} -%>
|
|
196
223
|
|
|
197
224
|
// ============================================
|
|
198
|
-
// Set ETypes for
|
|
225
|
+
// Set ETypes for all features (must be done after all classes are created).
|
|
226
|
+
// An EAttribute without eType leaves the XMI reader no EDataType to
|
|
227
|
+
// convert against - every value would arrive as a raw string (#37)
|
|
199
228
|
// ============================================
|
|
200
229
|
<% for (const genClass of genClasses) {
|
|
201
230
|
const eClass = genClass.ecoreClass;
|
|
@@ -206,14 +235,15 @@ export class <%- packageName %>Package extends BasicEPackage {
|
|
|
206
235
|
const featureName = getName(feature);
|
|
207
236
|
const featureUpperName = featureName.replace(/([A-Z])/g, '_$1').toUpperCase().replace(/^_/, '');
|
|
208
237
|
const isRef = typeMapper.isReference(feature);
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
238
|
+
const eType = getEType(feature);
|
|
239
|
+
if (!eType) continue;
|
|
240
|
+
// Local enums and datatypes have no initialized Literals entry yet
|
|
241
|
+
// (see the enum TODO above) - only class literals exist locally
|
|
242
|
+
if (!isRef && isLocalClassifier(eType)) continue;
|
|
243
|
+
const castType = isRef ? 'BasicEReference' : 'BasicEAttribute';
|
|
212
244
|
-%>
|
|
213
|
-
(<%- packageName %>Package.Literals.<%- upperName %>__<%- featureUpperName %> as
|
|
214
|
-
<%
|
|
215
|
-
}
|
|
216
|
-
}
|
|
245
|
+
(<%- packageName %>Package.Literals.<%- upperName %>__<%- featureUpperName %> as <%- castType %>).setEType(<%- typeRefExpr(eType) %>);
|
|
246
|
+
<% }
|
|
217
247
|
} -%>
|
|
218
248
|
|
|
219
249
|
// ============================================
|
|
@@ -60,14 +60,8 @@ if (superTypes && superTypes.length > 0) {
|
|
|
60
60
|
const op = genOp.ecoreOperation;
|
|
61
61
|
const opName = op.getName();
|
|
62
62
|
const returnType = op.getEType() ? typeMapper.mapClassifier(op.getEType()) : 'void';
|
|
63
|
-
const params = [];
|
|
64
|
-
for (const param of op.getEParameters()) {
|
|
65
|
-
const paramName = param.getName();
|
|
66
|
-
const paramType = typeMapper.mapClassifier(param.getEType());
|
|
67
|
-
params.push(`${paramName}: ${paramType}`);
|
|
68
|
-
}
|
|
69
63
|
-%>
|
|
70
|
-
<%- opName %>(<%-
|
|
64
|
+
<%- opName %>(<%- mapParams(op) %>): <%- returnType %> {
|
|
71
65
|
throw new Error('<%- opName %> not implemented');
|
|
72
66
|
}
|
|
73
67
|
|