@komaci/common-shared 240.1.5 → 242.1.1

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.
@@ -0,0 +1,646 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.isTemplateImport = exports.upliftFakePropsFromTemplate = exports.reconcileDefaultAdg = exports.isImportInvalid = exports.reconcilePrimingAdapater = exports.reconcileWireReference = exports.composeWireFunctionMetadata = exports.addTemplateUsageForAdg = exports.mapExportNamesToAdgs = exports.initalizeAdgMetadata = exports.collectImportMetadataFromAst = exports.getImportTemplateKomaciDocByResourceName = exports.updateAliasForImport = exports.addNewImportFromAst = exports.reconcileImport = exports.reconcileNamespace = exports.traverseAstImports = exports.composeImportMetadata = exports.initializeImportMetdataFromKomaciDocument = exports.initAdgMetadataObject = exports.initModuleMetadataObject = exports.NO_KOMACI_DOC_REF = void 0;
4
+ const allowlistNamespaces_1 = require("./allowlistNamespaces");
5
+ const komaciDocumentIntrospection_1 = require("./komaciDocumentIntrospection");
6
+ const types_1 = require("./types");
7
+ const wires_1 = require("./wires");
8
+ const utils_1 = require("./utils");
9
+ /** not all imports are consumed in a statically analyzable way. when we add their metadata, we use this to ack that the komaciDocImportRef for this import is nil */
10
+ exports.NO_KOMACI_DOC_REF = 'nil';
11
+ /**
12
+ * establish a base object for module metadata
13
+ * @returns A structured object for module metadata
14
+ */
15
+ const initModuleMetadataObject = () => ({
16
+ importGeneratorIndex: 0,
17
+ adgGeneratorIndex: 0,
18
+ importsByNamespace: new Map(),
19
+ importsByName: new Map(),
20
+ importIndexReference: new Map(),
21
+ adgs: new Map(),
22
+ exports: {},
23
+ templateKomaciDocMap: {},
24
+ });
25
+ exports.initModuleMetadataObject = initModuleMetadataObject;
26
+ /**
27
+ * establish an empty object for adg metadata
28
+ * @param defaultGeneratedName a generated name for this object
29
+ * @returns an empty metadata object
30
+ */
31
+ const initAdgMetadataObject = (defaultGeneratedName) => ({
32
+ defaultGeneratedName,
33
+ properties: new Map(),
34
+ functions: [],
35
+ propertiesUsedInTemplate: new Set(),
36
+ requiredAdgFactoryFunctions: new Set(),
37
+ requiredCompositionFactoryFunctions: new Set(),
38
+ hasSourceFile: false,
39
+ });
40
+ exports.initAdgMetadataObject = initAdgMetadataObject;
41
+ /**
42
+ * Process import references from komaci document
43
+ * @param doc the KomaciDocument itself
44
+ * @param moduleMetadata data structure representing metadata about the module we are working on
45
+ * @param templateAdgIndex the index of the template adg
46
+ */
47
+ const initializeImportMetdataFromKomaciDocument = (doc, moduleMetadata, templateAdgIndex) => {
48
+ const namespaces = doc.imports || [];
49
+ for (let i = 0; i < namespaces.length; i++) {
50
+ const importNamespace = namespaces[i];
51
+ const names = new Set(importNamespace.names);
52
+ const isSupported = (0, allowlistNamespaces_1.isSupportedNamespace)(importNamespace.resourceName);
53
+ const namespace = {
54
+ names,
55
+ isSupported,
56
+ resourceName: importNamespace.resourceName,
57
+ isDefaultSpecifier: names.has('default'),
58
+ isNamespaceSpecifier: names.has('*'),
59
+ };
60
+ moduleMetadata.importsByNamespace.set(importNamespace.resourceName, namespace);
61
+ for (let j = 0; j < importNamespace.names.length; j++) {
62
+ const name = importNamespace.names[j];
63
+ const komaciDocImportRef = `${i}/names/${j}`;
64
+ const importAlias = moduleMetadata.importsByName.has(name)
65
+ ? `${name}-${importNamespace.resourceName}`
66
+ : undefined;
67
+ (0, exports.composeImportMetadata)(name, importNamespace.resourceName, isSupported, templateAdgIndex !== undefined
68
+ ? `t${templateAdgIndex}-` + komaciDocImportRef
69
+ : komaciDocImportRef, // to prevent collision in references
70
+ moduleMetadata, importAlias);
71
+ }
72
+ /*
73
+ * For imports from other resolvable modules we know that they will always be only a default import.
74
+ * as such if we see one of these special imports we should snag the component id for this resolvable module
75
+ */
76
+ const firstItem = templateAdgIndex !== undefined
77
+ ? `t${templateAdgIndex}-${i}/names/0`
78
+ : `${i}/names/0`;
79
+ const adgImportName = moduleMetadata.importIndexReference.get(firstItem);
80
+ if (namespace.resourceName.startsWith('@salesforce/komaci') && adgImportName) {
81
+ // name reference and the object map are built along side eachother so if one exists so does the ohter
82
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
83
+ const adgImport = moduleMetadata.importsByName.get(adgImportName);
84
+ adgImport.componentId = (0, komaciDocumentIntrospection_1.importToComponentId)(namespace.resourceName);
85
+ }
86
+ }
87
+ };
88
+ exports.initializeImportMetdataFromKomaciDocument = initializeImportMetdataFromKomaciDocument;
89
+ /**
90
+ * Update module metadata with information about the given import.
91
+ * @param name import name
92
+ * @param resourceName import path
93
+ * @param isSupported if it's from a valid namespace
94
+ * @param komaciDocImportRef reference index in komaci document
95
+ * @param moduleMetadata the metadata object
96
+ *
97
+ * @return the import metadata object in case anything needs to be modified
98
+ */
99
+ const composeImportMetadata = (name, resourceName, isSupported, komaciDocImportRef, moduleMetadata, importAlias) => {
100
+ const generatorIndex = isSupported
101
+ ? moduleMetadata.importGeneratorIndex++
102
+ : moduleMetadata.importGeneratorIndex;
103
+ let importKey = name;
104
+ if (importAlias) {
105
+ importKey = importAlias;
106
+ }
107
+ else if (name === 'default') {
108
+ importKey = `default-${resourceName}`;
109
+ importAlias = importKey;
110
+ }
111
+ else if (name === '*') {
112
+ importKey = `namespace-${resourceName}`;
113
+ importAlias = importKey;
114
+ }
115
+ let currentImport = {
116
+ name,
117
+ komaciDocImportRef,
118
+ importAlias,
119
+ generatorAlias: `i${generatorIndex}`,
120
+ resourceName: resourceName,
121
+ isFromInternalNamespace: isSupported,
122
+ isFromSupportedLibrary: (0, allowlistNamespaces_1.isLibraryValid)(resourceName),
123
+ usedInPriming: false,
124
+ staticallyAnalyzable: true,
125
+ };
126
+ if (allowlistNamespaces_1.isLocalHtmlImportReference.test(resourceName)) {
127
+ const templateKomaciDoc = getImportTemplateKomaciDocByResourceName(resourceName, moduleMetadata.templateKomaciDocMap);
128
+ if (templateKomaciDoc) {
129
+ const templateImport = {
130
+ ...currentImport,
131
+ templateKomaciDoc: templateKomaciDoc,
132
+ };
133
+ currentImport = templateImport;
134
+ }
135
+ else {
136
+ currentImport.isFromSupportedLibrary = false;
137
+ }
138
+ }
139
+ moduleMetadata.importsByName.set(importKey, currentImport);
140
+ // no komaci doc ref means import is not referenced in the komaci document but was from the ast
141
+ if (komaciDocImportRef !== exports.NO_KOMACI_DOC_REF) {
142
+ moduleMetadata.importIndexReference.set(komaciDocImportRef, importKey);
143
+ }
144
+ return currentImport;
145
+ };
146
+ exports.composeImportMetadata = composeImportMetadata;
147
+ /**
148
+ * collect all the imports for a given ast and then execute a callback with information about the import
149
+ * @param ast The babel ast
150
+ * @param cb function to call for acting on import information
151
+ */
152
+ const traverseAstImports = (ast, cb) => {
153
+ const program = ast.program;
154
+ const body = program.body;
155
+ const importDeclarations = body.filter((currentDec) => currentDec.type === 'ImportDeclaration');
156
+ importDeclarations.forEach((currentDec) => {
157
+ const specifiers = currentDec.specifiers;
158
+ const resourceName = currentDec.source.value;
159
+ specifiers.forEach((specifier) => {
160
+ let referencedName;
161
+ let originalImportName;
162
+ let lookupName;
163
+ if ((specifier.type === 'ImportSpecifier' &&
164
+ (0, utils_1.getFromIdentifierOrStringLiteral)(specifier.local) !==
165
+ (0, utils_1.getFromIdentifierOrStringLiteral)(specifier.imported)) ||
166
+ specifier.type !== 'ImportSpecifier') {
167
+ referencedName = (0, utils_1.getFromIdentifierOrStringLiteral)(specifier.local);
168
+ lookupName = referencedName;
169
+ if (specifier.type === 'ImportSpecifier') {
170
+ originalImportName = (0, utils_1.getFromIdentifierOrStringLiteral)(specifier.imported);
171
+ lookupName = originalImportName;
172
+ }
173
+ else if (specifier.type === 'ImportDefaultSpecifier') {
174
+ lookupName = `default-${resourceName}`;
175
+ originalImportName = 'default';
176
+ }
177
+ else if (specifier.type === 'ImportNamespaceSpecifier') {
178
+ lookupName = `namespace-${resourceName}`;
179
+ originalImportName = '*';
180
+ }
181
+ }
182
+ else {
183
+ referencedName = (0, utils_1.getFromIdentifierOrStringLiteral)(specifier.imported);
184
+ lookupName = referencedName;
185
+ }
186
+ cb(lookupName, referencedName, resourceName, originalImportName);
187
+ });
188
+ });
189
+ };
190
+ exports.traverseAstImports = traverseAstImports;
191
+ /**
192
+ * given the name of a resource see if we have information about it. if we don't compose the base object for later reference.
193
+ * @param resourceName The import path
194
+ * @param moduleMetadata Metadata about this module
195
+ * @returns The namespace metadata object
196
+ */
197
+ const reconcileNamespace = (resourceName, moduleMetadata) => {
198
+ let namespace = moduleMetadata.importsByNamespace.get(resourceName);
199
+ if (!namespace) {
200
+ namespace = {
201
+ names: new Set(),
202
+ isSupported: allowlistNamespaces_1.isLocalHtmlImportReference.exec(resourceName)
203
+ ? (0, allowlistNamespaces_1.isSupportedNamespace)(resourceName)
204
+ : (0, allowlistNamespaces_1.isNamespaceInternal)((0, allowlistNamespaces_1.getNamespaceFromImport)(resourceName)),
205
+ resourceName: resourceName,
206
+ isDefaultSpecifier: false,
207
+ isNamespaceSpecifier: false,
208
+ };
209
+ moduleMetadata.importsByNamespace.set(resourceName, namespace);
210
+ }
211
+ return namespace;
212
+ };
213
+ exports.reconcileNamespace = reconcileNamespace;
214
+ /**
215
+ * When looking for an import if it it doesn't exist and we'd have
216
+ * to just make it anyway this function will do that for you
217
+ *
218
+ * @param name identifier of import you're looking for
219
+ * @param importPath resource path for the import
220
+ * @param moduleMetadata module metadata instance
221
+ * @returns The import metadata for this import (as much as we know)
222
+ */
223
+ const reconcileImport = (name, importPath, moduleMetadata) => {
224
+ const existingImport = moduleMetadata.importsByName.get(name);
225
+ if (existingImport) {
226
+ return existingImport;
227
+ }
228
+ else {
229
+ const newImport = (0, exports.composeImportMetadata)(name, importPath, (0, allowlistNamespaces_1.isNamespaceInternal)((0, allowlistNamespaces_1.getNamespaceFromImport)(importPath)), exports.NO_KOMACI_DOC_REF, moduleMetadata);
230
+ const namespace = (0, exports.reconcileNamespace)(importPath, moduleMetadata);
231
+ namespace.names.add(newImport.name);
232
+ return newImport;
233
+ }
234
+ };
235
+ exports.reconcileImport = reconcileImport;
236
+ /**
237
+ * add a new import that is only found in the ast. sometimes imports are not statically analyzable but we still want to collect info on them so we do this.
238
+ * @param referencedName the name used to reference this import in code
239
+ * @param namespace the metadata about the import namespace
240
+ * @param moduleMetadata the metadata about the module
241
+ * @param originalImportName (optional) the original name of the import that has been aliases. undefined if no alias.
242
+ */
243
+ const addNewImportFromAst = (referencedName, namespace, moduleMetadata, originalImportName) => {
244
+ const importAlias = originalImportName && referencedName !== originalImportName
245
+ ? referencedName
246
+ : undefined;
247
+ const importMetadata = (0, exports.composeImportMetadata)(originalImportName || referencedName, namespace.resourceName, namespace.isSupported, exports.NO_KOMACI_DOC_REF, moduleMetadata, importAlias);
248
+ importMetadata.staticallyAnalyzable = false;
249
+ if (originalImportName && referencedName !== originalImportName) {
250
+ importMetadata.importAlias = referencedName;
251
+ }
252
+ moduleMetadata.importsByName.set(referencedName, importMetadata);
253
+ namespace.names.add(referencedName);
254
+ };
255
+ exports.addNewImportFromAst = addNewImportFromAst;
256
+ /**
257
+ * Komaci Documents don't keep track of import aliases but sometimes they're referenced in code so we want to makes sure we have them.
258
+ * @param lookupName the name used as the holdover key tor eference this import
259
+ * @param referencedName the name used to reference this import in code
260
+ * @param namespace the import namespace metadata
261
+ * @param moduleMetadata metadata about this module
262
+ * @param originalImportName (optional) the original name of the import that has been aliases. undefined if no alias.
263
+ */
264
+ const updateAliasForImport = (lookupName, referencedName, namespace, moduleMetadata, originalImportName) => {
265
+ const importMetadata = moduleMetadata.importsByName.get(lookupName);
266
+ if (originalImportName && referencedName !== originalImportName && importMetadata) {
267
+ const isDefaultOrNamespace = originalImportName === '*' || originalImportName === 'default';
268
+ importMetadata.importAlias = referencedName;
269
+ moduleMetadata.importsByName.set(referencedName, importMetadata);
270
+ moduleMetadata.importsByName.delete(lookupName);
271
+ namespace.names.delete(isDefaultOrNamespace ? originalImportName : lookupName);
272
+ namespace.names.add(referencedName);
273
+ if (importMetadata.komaciDocImportRef !== exports.NO_KOMACI_DOC_REF) {
274
+ moduleMetadata.importIndexReference.set(importMetadata.komaciDocImportRef, referencedName);
275
+ }
276
+ }
277
+ };
278
+ exports.updateAliasForImport = updateAliasForImport;
279
+ /**
280
+ * Searches the provided tempalte komaci doc map for a document that corresponds to the provided namesapce.
281
+ * @param resourceName am imports resource name
282
+ * @param templateKomaciDocMap a map of template komaci docs.
283
+ */
284
+ function getImportTemplateKomaciDocByResourceName(resourceName, templateKomaciDocMap) {
285
+ let templateImportKomaciDoc;
286
+ if (allowlistNamespaces_1.isLocalHtmlImportReference.test(resourceName)) {
287
+ const segments = (0, utils_1.getFilepathSegments)(resourceName);
288
+ const moduleName = segments[1].slice(1);
289
+ if (templateKomaciDocMap && templateKomaciDocMap[moduleName]) {
290
+ templateImportKomaciDoc = templateKomaciDocMap[moduleName];
291
+ }
292
+ }
293
+ return templateImportKomaciDoc;
294
+ }
295
+ exports.getImportTemplateKomaciDocByResourceName = getImportTemplateKomaciDocByResourceName;
296
+ /**
297
+ * pull all needful import metadata we can from the ast
298
+ * for the most part, we can grab data from the komaci document for imports but sometimes
299
+ * imports are consumed in non statically analyzable ways like inside of a getter or template string
300
+ * so we need to collect that info seperately
301
+ *
302
+ * also, the Komaci Document doesn't maintain the local alias for default or namespaced imports. so if we
303
+ * have previously collected information about one of these imports from the Komaci Document then we want
304
+ * to make sure the alias is consumed and the maps properly represent the way the import is consumed.
305
+ *
306
+ * @param moduleMetadata metadata data structure to modify
307
+ * @param ast ast for the given component
308
+ */
309
+ const collectImportMetadataFromAst = (ast, moduleMetadata) => {
310
+ (0, exports.traverseAstImports)(ast, (lookupName, referencedName, resourceName, originalImportName) => {
311
+ const namespace = (0, exports.reconcileNamespace)(resourceName, moduleMetadata);
312
+ if (!moduleMetadata.importsByName.has(lookupName)) {
313
+ (0, exports.addNewImportFromAst)(referencedName, namespace, moduleMetadata, originalImportName);
314
+ }
315
+ else {
316
+ (0, exports.updateAliasForImport)(lookupName, referencedName, namespace, moduleMetadata, originalImportName);
317
+ }
318
+ });
319
+ };
320
+ exports.collectImportMetadataFromAst = collectImportMetadataFromAst;
321
+ /**
322
+ * From a given adg, collect as much metadata as possible ONLY from the komaci document
323
+ *
324
+ * This would include:
325
+ * - property initialization (any info we can collect ONLY from the komaci document)
326
+ * - function initialization
327
+ * - default generation name setup
328
+ * @param docAdgIndex the index of the adg in the KomaciDocument
329
+ * @param doc the KomaciDocument itself
330
+ * @param moduleMetadata data structure representing metadata about the module we are working on
331
+ */
332
+ const initalizeAdgMetadata = (docAdgIndex, doc, moduleMetadata, hasSourceFile, isBundle = true) => {
333
+ (0, komaciDocumentIntrospection_1.traverseParentAdgs)(doc.adgs?.[docAdgIndex], docAdgIndex, doc, moduleMetadata, (adg, index) => {
334
+ // if we have data for an adg already then we can assume that it's already been processed
335
+ if (!moduleMetadata.adgs.has(index)) {
336
+ const functions = adg.functions;
337
+ const adgMetadata = {
338
+ hasSourceFile,
339
+ defaultGeneratedName: `adg${moduleMetadata.adgGeneratorIndex++}`,
340
+ requiredAdgFactoryFunctions: new Set(),
341
+ requiredCompositionFactoryFunctions: new Set(),
342
+ propertiesUsedInTemplate: new Set(),
343
+ properties: new Map(),
344
+ functions: [],
345
+ parentReference: adg.parentClass,
346
+ };
347
+ if (isBundle) {
348
+ adgMetadata.compositions = [];
349
+ }
350
+ if (adgMetadata.parentReference?.type === 'ImportReference') {
351
+ const importName = moduleMetadata.importIndexReference.get(adgMetadata.parentReference.value);
352
+ const importMetadata = importName
353
+ ? moduleMetadata.importsByName.get(importName)
354
+ : undefined;
355
+ if (!importMetadata ||
356
+ !importMetadata.isFromInternalNamespace ||
357
+ !importMetadata.isFromSupportedLibrary) {
358
+ adgMetadata.parentReference = {
359
+ type: 'Unresolved',
360
+ value: '',
361
+ };
362
+ }
363
+ if (importMetadata) {
364
+ importMetadata.usedInPriming = true;
365
+ }
366
+ }
367
+ if (adgMetadata.parentReference?.type === 'Unresolved') {
368
+ adgMetadata.requiredAdgFactoryFunctions.add(types_1.IdKeys.UNRESOLVED_VALUE);
369
+ }
370
+ adgMetadata.requiredAdgFactoryFunctions.add(types_1.IdKeys.ADG_FUNC);
371
+ moduleMetadata.adgs.set(index, adgMetadata);
372
+ adgMetadata.properties = (0, komaciDocumentIntrospection_1.initializePropertiesMap)(adg.properties, functions, index, doc, moduleMetadata, adgMetadata.properties);
373
+ (0, komaciDocumentIntrospection_1.processFreestandingFunctions)(functions, adgMetadata, moduleMetadata);
374
+ adg.functions
375
+ ?.filter((func) => func.type === types_1.FunctionTypes.WIRE_FUNCTION && func.input)
376
+ // we've filtered out functions where the input isn't defined already
377
+ .forEach((func) =>
378
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
379
+ (0, komaciDocumentIntrospection_1.traverseInput)(func.input, (value) => {
380
+ if (value.type === 'PropertyReference' &&
381
+ adgMetadata.properties.has(value.value)) {
382
+ const property = adgMetadata.properties.get(value.value);
383
+ if (property) {
384
+ property.usedInPriming = true;
385
+ }
386
+ }
387
+ else if (value.type === 'Unresolved') {
388
+ adgMetadata.requiredAdgFactoryFunctions.add(types_1.IdKeys.UNRESOLVED_VALUE);
389
+ }
390
+ else if (value.type === 'ImportReference' &&
391
+ moduleMetadata.importIndexReference.has(value.value)) {
392
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
393
+ const importMetadata = moduleMetadata.importsByName.get(
394
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
395
+ moduleMetadata.importIndexReference.get(value.value));
396
+ importMetadata.usedInPriming = true;
397
+ if (!importMetadata.isFromInternalNamespace) {
398
+ adgMetadata.requiredAdgFactoryFunctions.add(types_1.IdKeys.UNRESOLVED_VALUE);
399
+ const undefinedValue = value;
400
+ undefinedValue.type = 'Unresolved';
401
+ undefinedValue.value = types_1.IdKeys.UNRESOLVED_VALUE;
402
+ }
403
+ }
404
+ return false;
405
+ }));
406
+ }
407
+ });
408
+ };
409
+ exports.initalizeAdgMetadata = initalizeAdgMetadata;
410
+ /**
411
+ * Update exports key in module metadata mapping the export name to associated adg object
412
+ * @param doc the KomaciDocument itself
413
+ * @param moduleMetadata data structure representing metadata about the module we are working on
414
+ */
415
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
416
+ const mapExportNamesToAdgs = (exports, moduleMetadata) => {
417
+ if (exports) {
418
+ Object.entries(exports).forEach(([exportName, exportReference]) => {
419
+ if (exportReference?.type === 'AdgReference') {
420
+ const adg = moduleMetadata.adgs.get(exportReference.value);
421
+ if (adg) {
422
+ adg.exportName = exportName;
423
+ moduleMetadata.exports[exportName] = adg;
424
+ }
425
+ }
426
+ });
427
+ }
428
+ };
429
+ exports.mapExportNamesToAdgs = mapExportNamesToAdgs;
430
+ /**
431
+ * Walk the compositions to see what props are being used, add this information to the adg metadata
432
+ * @param doc the template KomaciDocument
433
+ * @param adgIndex the index of the default adg
434
+ * @param moduleMetadata data structure representing metadata about the module we are working on
435
+ */
436
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
437
+ const addTemplateUsageForAdg = (doc, adgIndex, moduleMetadata) => {
438
+ if (moduleMetadata.adgs.has(adgIndex)) {
439
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
440
+ const adg = moduleMetadata.adgs.get(adgIndex);
441
+ if (doc?.exports?.default?.type === 'CompositionReference' &&
442
+ doc.compositions?.[doc.exports.default.value]) {
443
+ const composition = doc.compositions[doc.exports.default.value];
444
+ adg.compositions = [composition];
445
+ (0, komaciDocumentIntrospection_1.traverseComposition)(composition, (comp, iterationContext) => {
446
+ (0, komaciDocumentIntrospection_1.updatePropertiesForComposition)(comp, adg.properties, adg.propertiesUsedInTemplate, iterationContext);
447
+ if (comp && comp.isActive) {
448
+ adg.requiredCompositionFactoryFunctions.add(types_1.IdKeys.UNRESOLVED_FUNC);
449
+ }
450
+ if ((0, komaciDocumentIntrospection_1.isCompositionAComposedAdg)(comp)) {
451
+ adg.requiredCompositionFactoryFunctions.add(types_1.IdKeys.COMPOSED_GRAPH_FUNC);
452
+ if (comp.input.type === 'ImportReference') {
453
+ const visitedImportForTemplate = comp.input.value.startsWith(`t${adgIndex}`);
454
+ const importName = moduleMetadata.importIndexReference.get(visitedImportForTemplate
455
+ ? comp.input.value
456
+ : `t${adgIndex}-${comp.input.value}`);
457
+ const importInfo = importName
458
+ ? moduleMetadata.importsByName.get(importName)
459
+ : undefined;
460
+ if (importInfo) {
461
+ importInfo.usedInPriming = true;
462
+ }
463
+ //changing the comp node to be what t is referencing
464
+ if (!visitedImportForTemplate) {
465
+ comp.input.value = `t${adgIndex}-${comp.input.value}`;
466
+ }
467
+ }
468
+ }
469
+ else if ((0, komaciDocumentIntrospection_1.isCompositionASlot)(comp)) {
470
+ adg.requiredCompositionFactoryFunctions.add(types_1.IdKeys.SLOT_FUNC);
471
+ }
472
+ else if ((0, komaciDocumentIntrospection_1.isCompositionAnIteration)(comp)) {
473
+ adg.requiredCompositionFactoryFunctions.add(types_1.IdKeys.ITERATION_FUNC);
474
+ }
475
+ else if ((0, komaciDocumentIntrospection_1.isCompositionAnImage)(comp)) {
476
+ adg.requiredCompositionFactoryFunctions.add(types_1.IdKeys.IMG_FUNC);
477
+ }
478
+ else if ((0, komaciDocumentIntrospection_1.isCompositionAContainer)(comp) && (comp.key || comp.slot)) {
479
+ adg.requiredCompositionFactoryFunctions.add(types_1.IdKeys.ELEMENT_FUNC);
480
+ }
481
+ return false;
482
+ });
483
+ }
484
+ }
485
+ };
486
+ exports.addTemplateUsageForAdg = addTemplateUsageForAdg;
487
+ /**
488
+ * Collect functional metadata for a wire this includes
489
+ * - wire function details (name, batch / reducer if priming function)
490
+ * - input
491
+ * - required properties
492
+ *
493
+ * all bundled up into one readily available package for later composition
494
+ *
495
+ * @param functionDetails
496
+ * @param wireImport
497
+ * @param moduleMetadata
498
+ * @returns
499
+ */
500
+ const composeWireFunctionMetadata = (functionDetails, wireImport, moduleMetadata) => {
501
+ const isSupported = (0, wires_1.isSupportedWireAdapter)(wireImport.resourceName, wireImport.name);
502
+ const functionMetadata = {
503
+ input: functionDetails.input,
504
+ type: types_1.FunctionTypes.WIRE_FUNCTION,
505
+ requiredProperties: [],
506
+ importReference: {
507
+ functionName: isSupported
508
+ ? wireImport.importAlias || wireImport.name
509
+ : types_1.IdKeys.UNRESOLVED_VALUE,
510
+ },
511
+ };
512
+ // compose required properties
513
+ if (functionDetails.input && functionDetails.input.length > 0) {
514
+ if (functionDetails.input.length !== 1 ||
515
+ functionDetails.input[0].type !== 'ObjectValue') {
516
+ // Only valid input according to Wire Adapter Protocol.
517
+ throw new Error(types_1.ERROR_PREFIX + 'WireFunction has invalid input');
518
+ }
519
+ const inputObject = functionDetails.input[0];
520
+ functionMetadata.requiredProperties = Object.values(inputObject.value)
521
+ .filter(komaciDocumentIntrospection_1.isValueProperty)
522
+ .map((input) => (0, komaciDocumentIntrospection_1.stripChildReferenceFromValue)(input.value));
523
+ }
524
+ const primingAdapterDef = (0, wires_1.getPrimingAdapter)(wireImport.resourceName, wireImport.name);
525
+ if (primingAdapterDef) {
526
+ (0, exports.reconcilePrimingAdapater)(functionMetadata, primingAdapterDef, moduleMetadata);
527
+ functionMetadata.type = types_1.FunctionTypes.PRIMING_FUNCTION;
528
+ wireImport.usedInPriming = false;
529
+ }
530
+ else {
531
+ wireImport.usedInPriming = isSupported;
532
+ }
533
+ return functionMetadata;
534
+ };
535
+ exports.composeWireFunctionMetadata = composeWireFunctionMetadata;
536
+ /**
537
+ * A Wire Function can only have one valid type of reference, an import. if we see an import we should collect the info for that
538
+ * otherwise, we should mark the reference as unresolved and make sure we are accounting for it in factory functions
539
+ * @param func The details about a function from the komaci doc
540
+ * @param adg metadata about the adg this function is in
541
+ * @param moduleMetadata general module metadata (imports mostly)
542
+ * @returns import metadata if this wire references a valid one, undefined otherwise
543
+ */
544
+ const reconcileWireReference = (func, adg, moduleMetadata) => {
545
+ let importMetadata;
546
+ if (func.reference.type === 'ImportReference' &&
547
+ moduleMetadata.importIndexReference.has(func?.reference.value) &&
548
+ moduleMetadata.importsByName.has(
549
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
550
+ moduleMetadata.importIndexReference.get(func?.reference.value))) {
551
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
552
+ importMetadata = moduleMetadata.importsByName.get(
553
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
554
+ moduleMetadata.importIndexReference.get(func?.reference.value));
555
+ }
556
+ else {
557
+ func.reference = {
558
+ type: 'Unresolved',
559
+ value: '',
560
+ };
561
+ adg.requiredAdgFactoryFunctions.add(types_1.IdKeys.UNRESOLVED_VALUE);
562
+ }
563
+ return importMetadata;
564
+ };
565
+ exports.reconcileWireReference = reconcileWireReference;
566
+ /**
567
+ * Some wires have associated priming adapters. if we do have one of those then we want to use it instead of the
568
+ * original wire adapter referenced in the komaci document. as part of this we have to make sure the new imports
569
+ * are made and appropriately referenced inside module metadata
570
+ *
571
+ * @param functionMetadata Details about a wire function
572
+ * @param primingAdapterDef Details about the priming adapter associated for this wire
573
+ * @param moduleMetadata Instance of module metadata data structure
574
+ */
575
+ const reconcilePrimingAdapater = (functionMetadata, primingAdapterDef, moduleMetadata) => {
576
+ const importMetadata = (0, exports.reconcileImport)(primingAdapterDef.prime.identifier, primingAdapterDef.prime.importPath, moduleMetadata);
577
+ importMetadata.usedInPriming = true;
578
+ functionMetadata.importReference.functionName = importMetadata.name;
579
+ if (primingAdapterDef.batch) {
580
+ if (primingAdapterDef.batch.prime.importPath ===
581
+ primingAdapterDef.prime.importPath &&
582
+ primingAdapterDef.batch.prime.identifier ===
583
+ primingAdapterDef.prime.identifier) {
584
+ functionMetadata.importReference.batchingName = importMetadata.name;
585
+ }
586
+ else {
587
+ const batchImport = (0, exports.reconcileImport)(primingAdapterDef.batch.prime.identifier, primingAdapterDef.batch.prime.importPath, moduleMetadata);
588
+ batchImport.usedInPriming = true;
589
+ functionMetadata.importReference.batchingName = batchImport.name;
590
+ }
591
+ const reducerImport = (0, exports.reconcileImport)(primingAdapterDef.batch.reducer.identifier, primingAdapterDef.batch.reducer.importPath, moduleMetadata);
592
+ reducerImport.usedInPriming = true;
593
+ functionMetadata.importReference.reducer = reducerImport.name;
594
+ }
595
+ };
596
+ exports.reconcilePrimingAdapater = reconcilePrimingAdapater;
597
+ function isImportInvalid(importMetadata) {
598
+ return (!importMetadata.isFromInternalNamespace || !importMetadata.isFromSupportedLibrary);
599
+ }
600
+ exports.isImportInvalid = isImportInvalid;
601
+ /**
602
+ * in specific cases, mainly template only compositions, we may not have a default adg already but need one to compose the resolvable module.
603
+ * @param currentDefaultAdgIndex The current index of the default adg if it exists
604
+ * @param moduleMetadata metadata about the module
605
+ * @returns the index of the default adg
606
+ */
607
+ function reconcileDefaultAdg(currentDefaultAdgIndex, moduleMetadata) {
608
+ let componentDefaultAdgIndex = currentDefaultAdgIndex;
609
+ if (componentDefaultAdgIndex === undefined && moduleMetadata.adgs.size === 0) {
610
+ componentDefaultAdgIndex = moduleMetadata.adgGeneratorIndex++;
611
+ const fakeDefaultAdg = (0, exports.initAdgMetadataObject)(`adg${componentDefaultAdgIndex}`);
612
+ fakeDefaultAdg.requiredAdgFactoryFunctions.add(types_1.IdKeys.ADG_FUNC);
613
+ moduleMetadata.adgs.set(componentDefaultAdgIndex, fakeDefaultAdg);
614
+ moduleMetadata.exports.default = fakeDefaultAdg;
615
+ }
616
+ return componentDefaultAdgIndex;
617
+ }
618
+ exports.reconcileDefaultAdg = reconcileDefaultAdg;
619
+ /**
620
+ * If we process a template and see it has some props we don't know about we can uplift them to the adgs props using this.
621
+ * this is only currently used for template only bundles
622
+ * @param adg The metadata object for a given adg
623
+ */
624
+ function upliftFakePropsFromTemplate(adg) {
625
+ for (const prop of adg?.propertiesUsedInTemplate.values()) {
626
+ if (!adg.properties.has(prop)) {
627
+ adg.properties.set(prop, {
628
+ type: types_1.PropertyTypes.BASE,
629
+ isPublic: true,
630
+ usedInPriming: true,
631
+ });
632
+ }
633
+ }
634
+ }
635
+ exports.upliftFakePropsFromTemplate = upliftFakePropsFromTemplate;
636
+ /**
637
+ * Helper function to determine if an importMetadata object is an instance of a TemplateImportMetadata
638
+ * @param importMetadata the import metadata object
639
+ * @returns true or false;
640
+ */
641
+ function isTemplateImport(importMetadata) {
642
+ const temp = importMetadata.templateKomaciDoc;
643
+ return temp != undefined;
644
+ }
645
+ exports.isTemplateImport = isTemplateImport;
646
+ //# sourceMappingURL=moduleMetadata.js.map