@veloceapps/sdk 8.0.0-99 → 9.0.0-1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (156) hide show
  1. package/cms/README.md +0 -20
  2. package/cms/cms.actions.d.ts +9 -1
  3. package/cms/components/preview/preview.component.d.ts +2 -3
  4. package/cms/components/preview/preview.types.d.ts +4 -0
  5. package/cms/index.d.ts +1 -0
  6. package/cms/modules/runtime/services/runtime.service.d.ts +1 -1
  7. package/cms/services/index.d.ts +0 -1
  8. package/cms/services/resources.service.d.ts +2 -0
  9. package/cms/types/index.d.ts +0 -1
  10. package/cms/utils/element-metadata-worker.d.ts +11 -0
  11. package/cms/utils/elements-resolver.d.ts +0 -2
  12. package/cms/utils/index.d.ts +3 -0
  13. package/cms/utils/transpilation-worker.d.ts +13 -0
  14. package/cms/vendor-map.d.ts +21 -18
  15. package/core/README.md +20 -0
  16. package/core/modules/configuration/configuration.module.d.ts +2 -1
  17. package/core/modules/configuration/helpers.d.ts +2 -1
  18. package/core/modules/configuration/index.d.ts +1 -1
  19. package/core/modules/configuration/services/configuration-state.service.d.ts +54 -0
  20. package/core/modules/configuration/services/configuration.service.d.ts +6 -6
  21. package/core/modules/configuration/types/configuration.types.d.ts +4 -0
  22. package/core/modules/flow-configuration/flow-configuration.module.d.ts +2 -1
  23. package/core/modules/flow-configuration/services/flow-configuration.service.d.ts +5 -0
  24. package/core/services/context.service.d.ts +2 -0
  25. package/core/services/flow-info.service.d.ts +29 -0
  26. package/core/services/flow-state-configuration.service.d.ts +19 -0
  27. package/core/services/flow-state.service.d.ts +80 -0
  28. package/core/services/index.d.ts +4 -1
  29. package/core/services/quote-draft.service.d.ts +12 -28
  30. package/core/types/flow-customization.types.d.ts +22 -0
  31. package/core/types/flow-state.types.d.ts +11 -0
  32. package/core/types/index.d.ts +3 -1
  33. package/{cms → core}/types/integration.types.d.ts +0 -1
  34. package/core/utils/line-item.utils.d.ts +1 -3
  35. package/esm2020/cms/cms.actions.mjs +11 -1
  36. package/esm2020/cms/components/element-renderer/element-renderer.component.mjs +3 -3
  37. package/esm2020/cms/components/element-tools-panel/element-tools-panel.component.mjs +3 -3
  38. package/esm2020/cms/components/preview/preview.component.mjs +10 -10
  39. package/esm2020/cms/components/preview/preview.module.mjs +2 -2
  40. package/esm2020/cms/components/preview/preview.types.mjs +1 -1
  41. package/esm2020/cms/index.mjs +2 -1
  42. package/esm2020/cms/launcher.module.mjs +4 -4
  43. package/esm2020/cms/modules/migrations/migrations.mjs +2 -2
  44. package/esm2020/cms/modules/migrations/services/migrations.service.mjs +6 -2
  45. package/esm2020/cms/modules/runtime/services/compilation.service.mjs +8 -8
  46. package/esm2020/cms/modules/runtime/services/runtime.service.mjs +4 -4
  47. package/esm2020/cms/plugins/configuration.plugin.mjs +8 -4
  48. package/esm2020/cms/services/index.mjs +1 -2
  49. package/esm2020/cms/services/io-provider.service.mjs +10 -9
  50. package/esm2020/cms/services/resources.service.mjs +10 -6
  51. package/esm2020/cms/services/templates.service.mjs +10 -9
  52. package/esm2020/cms/types/index.mjs +1 -2
  53. package/esm2020/cms/utils/element-metadata-worker.mjs +31 -0
  54. package/esm2020/cms/utils/elements-resolver.mjs +13 -27
  55. package/esm2020/cms/utils/encoding.utils.mjs +3 -2
  56. package/esm2020/cms/utils/index.mjs +4 -1
  57. package/esm2020/cms/utils/path.utils.mjs +3 -3
  58. package/esm2020/cms/utils/script.utils.mjs +19 -15
  59. package/esm2020/cms/utils/transpilation-worker.mjs +52 -0
  60. package/esm2020/cms/vendor-map.mjs +10 -5
  61. package/esm2020/core/core.module.mjs +19 -3
  62. package/esm2020/core/modules/configuration/configuration.module.mjs +7 -23
  63. package/esm2020/core/modules/configuration/helpers.mjs +21 -1
  64. package/esm2020/core/modules/configuration/index.mjs +2 -2
  65. package/esm2020/core/modules/configuration/services/configuration-state.service.mjs +335 -0
  66. package/esm2020/core/modules/configuration/services/configuration.service.mjs +56 -50
  67. package/esm2020/core/modules/configuration/types/configuration.types.mjs +1 -1
  68. package/esm2020/core/modules/flow-configuration/flow-configuration.module.mjs +6 -6
  69. package/esm2020/core/modules/flow-configuration/services/flow-configuration.service.mjs +12 -9
  70. package/esm2020/core/services/context.service.mjs +17 -5
  71. package/esm2020/core/services/flow-info.service.mjs +99 -0
  72. package/esm2020/core/services/flow-state-configuration.service.mjs +53 -0
  73. package/esm2020/core/services/flow-state.service.mjs +512 -0
  74. package/esm2020/core/services/index.mjs +5 -2
  75. package/esm2020/core/services/integration.state.mjs +36 -0
  76. package/esm2020/core/services/product-images.service.mjs +4 -5
  77. package/esm2020/core/services/quote-draft.service.mjs +39 -91
  78. package/esm2020/core/services/runtime-settings.service.mjs +7 -5
  79. package/esm2020/core/types/flow-customization.types.mjs +3 -0
  80. package/esm2020/core/types/flow-state.types.mjs +2 -0
  81. package/esm2020/core/types/index.mjs +4 -2
  82. package/esm2020/core/types/integration.types.mjs +2 -0
  83. package/esm2020/core/utils/line-item.utils.mjs +33 -32
  84. package/esm2020/src/components/doc-gen/doc-gen.component.mjs +44 -51
  85. package/esm2020/src/components/flow-header/flow-header.component.mjs +36 -47
  86. package/esm2020/src/components/guided-selling/guided-selling.component.mjs +35 -46
  87. package/esm2020/src/flow-routing.module.mjs +5 -18
  88. package/esm2020/src/flow.component.mjs +22 -37
  89. package/esm2020/src/guards/context.guard.mjs +6 -11
  90. package/esm2020/src/guards/flow.guard.mjs +23 -9
  91. package/esm2020/src/pages/assets/assets.component.mjs +30 -34
  92. package/esm2020/src/pages/catalog/catalog.component.mjs +30 -34
  93. package/esm2020/src/pages/debug/debug.component.mjs +2 -2
  94. package/esm2020/src/pages/product/product.component.mjs +34 -20
  95. package/esm2020/src/pages/record-not-found/record-not-found.component.mjs +6 -3
  96. package/esm2020/src/pages/remote/remote.component.mjs +15 -14
  97. package/esm2020/src/pages/shopping-cart/shopping-cart.component.mjs +31 -35
  98. package/esm2020/src/resolvers/flow.resolver.mjs +37 -55
  99. package/esm2020/src/resolvers/quote.resolver.mjs +55 -67
  100. package/esm2020/src/services/doc-gen.service.mjs +4 -3
  101. package/esm2020/src/services/flow-dialog.service.mjs +17 -6
  102. package/esm2020/src/services/flow-router.service.mjs +42 -15
  103. package/esm2020/src/services/flow.service.mjs +67 -52
  104. package/esm2020/src/services/guided-selling.service.mjs +5 -4
  105. package/esm2020/src/types/index.mjs +1 -2
  106. package/fesm2015/veloceapps-sdk-cms.mjs +270 -191
  107. package/fesm2015/veloceapps-sdk-cms.mjs.map +1 -1
  108. package/fesm2015/veloceapps-sdk-core.mjs +1195 -427
  109. package/fesm2015/veloceapps-sdk-core.mjs.map +1 -1
  110. package/fesm2015/veloceapps-sdk.mjs +776 -826
  111. package/fesm2015/veloceapps-sdk.mjs.map +1 -1
  112. package/fesm2020/veloceapps-sdk-cms.mjs +275 -206
  113. package/fesm2020/veloceapps-sdk-cms.mjs.map +1 -1
  114. package/fesm2020/veloceapps-sdk-core.mjs +1176 -454
  115. package/fesm2020/veloceapps-sdk-core.mjs.map +1 -1
  116. package/fesm2020/veloceapps-sdk.mjs +899 -945
  117. package/fesm2020/veloceapps-sdk.mjs.map +1 -1
  118. package/package.json +8 -7
  119. package/src/components/doc-gen/doc-gen.component.d.ts +7 -10
  120. package/src/components/flow-header/flow-header.component.d.ts +6 -9
  121. package/src/components/guided-selling/guided-selling.component.d.ts +6 -9
  122. package/src/flow-routing.module.d.ts +1 -2
  123. package/src/flow.component.d.ts +7 -12
  124. package/src/guards/context.guard.d.ts +0 -1
  125. package/src/guards/flow.guard.d.ts +1 -1
  126. package/src/pages/assets/assets.component.d.ts +5 -7
  127. package/src/pages/catalog/catalog.component.d.ts +5 -7
  128. package/src/pages/product/product.component.d.ts +8 -7
  129. package/src/pages/record-not-found/record-not-found.component.d.ts +2 -0
  130. package/src/pages/remote/remote.component.d.ts +2 -3
  131. package/src/pages/shopping-cart/shopping-cart.component.d.ts +5 -7
  132. package/src/resolvers/flow.resolver.d.ts +6 -9
  133. package/src/resolvers/quote.resolver.d.ts +7 -14
  134. package/src/services/doc-gen.service.d.ts +1 -1
  135. package/src/services/flow-dialog.service.d.ts +4 -2
  136. package/src/services/flow-router.service.d.ts +6 -3
  137. package/src/services/flow.service.d.ts +10 -14
  138. package/src/services/guided-selling.service.d.ts +1 -1
  139. package/src/types/index.d.ts +0 -1
  140. package/core/modules/configuration/services/configuration.state.d.ts +0 -30
  141. package/core/services/metric-calculation/metric-calculation.service.d.ts +0 -25
  142. package/core/services/metric-calculation/metric-calculation.types.d.ts +0 -1
  143. package/core/services/metric-calculation/metric-calculation.utils.d.ts +0 -5
  144. package/esm2020/cms/services/integration.state.mjs +0 -37
  145. package/esm2020/cms/types/integration.types.mjs +0 -2
  146. package/esm2020/core/modules/configuration/services/configuration.state.mjs +0 -142
  147. package/esm2020/core/services/metric-calculation/metric-calculation.service.mjs +0 -85
  148. package/esm2020/core/services/metric-calculation/metric-calculation.types.mjs +0 -2
  149. package/esm2020/core/services/metric-calculation/metric-calculation.utils.mjs +0 -42
  150. package/esm2020/src/pages/empty-account/empty-account.component.mjs +0 -12
  151. package/esm2020/src/pages/empty-account/empty-account.module.mjs +0 -20
  152. package/esm2020/src/types/flow-customization.types.mjs +0 -3
  153. package/src/pages/empty-account/empty-account.component.d.ts +0 -5
  154. package/src/pages/empty-account/empty-account.module.d.ts +0 -10
  155. package/src/types/flow-customization.types.d.ts +0 -12
  156. /package/{cms → core}/services/integration.state.d.ts +0 -0
@@ -1,16 +1,16 @@
1
1
  import * as i0 from '@angular/core';
2
- import { Injectable, InjectionToken, NgModule, inject, Directive, Input, LOCALE_ID, Pipe } from '@angular/core';
3
- import { UUID, ConfigurationContextMode, ConfigurationContext, DEFAULT_CURRENCY_ISO_CODE, DEFAULT_CURRENCY_SYMBOL, validateDateFormat, DEFAULT_DATE_FORMAT, DEFAULT_DECIMALS_COUNT, getSupportedDateFormats, DEFAULT_DECIMAL_SEPARATOR, DEFAULT_THOUSANDS_SEPARATOR, DEFAULT_ACTION_CODE_LABELS, parseJsonSafely, ConfigurationMode, ConfigurationTranslatorUtils, ChargeGroupUtils, RuntimeModel, isNotLegacyUIDefinition, SalesforceIdUtils, EntityUtil, DEFAULT_TIME_FORMAT, formatNumber } from '@veloceapps/core';
2
+ import { Injectable, InjectionToken, Optional, Inject, NgModule, inject, Directive, Input, LOCALE_ID, Pipe } from '@angular/core';
3
+ import { UUID, ConfigurationContextMode, ConfigurationContext, UITemplateType, isDefined, ConfigurationProcessorTypes, EntityUtil, DEFAULT_CURRENCY_ISO_CODE, DEFAULT_CURRENCY_SYMBOL, validateDateFormat, DEFAULT_DATE_FORMAT, DEFAULT_DECIMALS_COUNT, getSupportedDateFormats, DEFAULT_DECIMAL_SEPARATOR, DEFAULT_THOUSANDS_SEPARATOR, DEFAULT_ACTION_CODE_LABELS, parseJsonSafely, ConfigurationMode, ConfigurationTranslatorUtils, ChargeGroupUtils, RuntimeModel, isNotLegacyUIDefinition, SalesforceIdUtils, DEFAULT_TIME_FORMAT, formatNumber } from '@veloceapps/core';
4
4
  import * as i1 from '@veloceapps/api';
5
- import { PriceApiService, ContextApiService, ProductModelApiService, ConfigurationApiService } from '@veloceapps/api';
6
- import { BehaviorSubject, zip, noop, combineLatest, map as map$2, tap as tap$1, throwError, shareReplay as shareReplay$1, of, switchMap as switchMap$1, catchError as catchError$1, Subject, take as take$1, distinctUntilChanged } from 'rxjs';
7
- import { map, filter, tap, switchMap, skip, take, shareReplay, catchError, finalize, first } from 'rxjs/operators';
8
- import { merge, isEqual, flatten, sortBy, map as map$1, uniqBy, transform, omit, cloneDeep, uniq } from 'lodash';
9
- import { HttpErrorResponse } from '@angular/common/http';
10
- import * as i4 from '@veloceapps/components';
5
+ import { ApiModule } from '@veloceapps/api';
6
+ import { BehaviorSubject, switchMap, map as map$1, tap as tap$1, noop, catchError, throwError, of, forkJoin, zip, combineLatest, Subject, filter as filter$1, shareReplay as shareReplay$1, finalize, takeUntil, buffer, debounceTime, share, take as take$1, distinctUntilChanged } from 'rxjs';
7
+ import { map, filter, tap, switchMap as switchMap$1, skip, take, shareReplay, catchError as catchError$1, finalize as finalize$1, first } from 'rxjs/operators';
8
+ import { merge, isEmpty, isEqual, cloneDeep, assign, flatten, entries, sortBy, map as map$2, uniqBy, omit, transform } from 'lodash';
9
+ import * as i6 from '@veloceapps/components';
11
10
  import { ToastType, ConfirmationComponent, ConfirmationDialogModule } from '@veloceapps/components';
11
+ import { HttpErrorResponse } from '@angular/common/http';
12
12
  import * as i5 from 'primeng/api';
13
- import * as i6 from 'primeng/dynamicdialog';
13
+ import * as i6$1 from 'primeng/dynamicdialog';
14
14
  import moment from 'moment';
15
15
  import { NgControl } from '@angular/forms';
16
16
  import 'primeng/calendar';
@@ -67,6 +67,26 @@ const getGuidedSellingConfigurationRequest = (data, context) => {
67
67
  },
68
68
  };
69
69
  };
70
+ const generateConfigurationLineItem = (props, qty = 1) => {
71
+ const id = UUID.UUID();
72
+ const attributes = Object.entries(props.attributesMap ?? {}).map(([name, value]) => ({
73
+ name,
74
+ value,
75
+ cfgStatus: 'User',
76
+ }));
77
+ const lineItems = [];
78
+ return {
79
+ id,
80
+ type: props.product.typeName ?? '',
81
+ cfgStatus: 'Default',
82
+ actionCode: 'ADD',
83
+ qty,
84
+ attributes,
85
+ lineItems,
86
+ productName: props.product.name,
87
+ productId: props.product.id ?? '',
88
+ };
89
+ };
70
90
 
71
91
  class ContextService {
72
92
  constructor(contextApiService) {
@@ -80,7 +100,20 @@ class ContextService {
80
100
  return this.context.pipe(map(Boolean));
81
101
  }
82
102
  get mode() {
83
- return this.resolve().properties.mode;
103
+ return this.resolve().properties['#mode'];
104
+ }
105
+ get isEditMode$() {
106
+ return this.resolve$().pipe(map(() => this.isEditMode));
107
+ }
108
+ get isEditMode() {
109
+ const context = this.resolve();
110
+ if (context.properties['#mode'] === ConfigurationContextMode.ACCOUNT) {
111
+ return true;
112
+ }
113
+ if (context.properties['#mode'] === ConfigurationContextMode.QUOTE) {
114
+ return context.properties.Status === 'Draft';
115
+ }
116
+ return false;
84
117
  }
85
118
  resolve() {
86
119
  if (!this.context.value) {
@@ -133,13 +166,128 @@ class ContextService {
133
166
  }
134
167
  }
135
168
  ContextService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ContextService, deps: [{ token: i1.ContextApiService }], target: i0.ɵɵFactoryTarget.Injectable });
136
- ContextService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ContextService, providedIn: 'root' });
169
+ ContextService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ContextService });
137
170
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ContextService, decorators: [{
138
- type: Injectable,
139
- args: [{ providedIn: 'root' }]
171
+ type: Injectable
140
172
  }], ctorParameters: function () { return [{ type: i1.ContextApiService }]; } });
141
173
 
174
+ const FLOW_CUSTOMIZATION = new InjectionToken('FLOW_CUSTOMIZATION');
175
+
176
+ const FORMATTING_SETTINGS_TOKEN = new InjectionToken('Summary of formatting settings for variant types of data, e.g. numbers, text, dates, etc');
177
+
178
+ var RuntimeMode;
179
+ (function (RuntimeMode) {
180
+ RuntimeMode[RuntimeMode["TEST"] = 0] = "TEST";
181
+ RuntimeMode[RuntimeMode["PROD"] = 1] = "PROD";
182
+ })(RuntimeMode || (RuntimeMode = {}));
183
+ var RuntimeOperation;
184
+ (function (RuntimeOperation) {
185
+ RuntimeOperation["INIT"] = "INIT";
186
+ RuntimeOperation["UPDATE"] = "UPDATE";
187
+ })(RuntimeOperation || (RuntimeOperation = {}));
188
+ var RuntimeStep;
189
+ (function (RuntimeStep) {
190
+ RuntimeStep["START"] = "START";
191
+ RuntimeStep["UPDATE"] = "UPDATE";
192
+ })(RuntimeStep || (RuntimeStep = {}));
193
+
194
+ const UI_DEFINITION_VERSION = 3;
195
+
196
+ class FlowInfoService {
197
+ get flow() {
198
+ return this.flowSubj$.value;
199
+ }
200
+ set flow(value) {
201
+ this.flowSubj$.next(value);
202
+ }
203
+ get isLegacy() {
204
+ return !!this.flow && this.flow?.properties.stateful == null;
205
+ }
206
+ get isStateful() {
207
+ return !!this.flow?.properties.stateful;
208
+ }
209
+ constructor(flowsApiService, templatesApiService, customizationService) {
210
+ this.flowsApiService = flowsApiService;
211
+ this.templatesApiService = templatesApiService;
212
+ this.customizationService = customizationService;
213
+ this.templates = {};
214
+ this.defaultTemplates = {
215
+ flowEngine: 'Flow Engine',
216
+ };
217
+ this.flowSubj$ = new BehaviorSubject(null);
218
+ this.flow$ = this.flowSubj$.asObservable();
219
+ }
220
+ init$(flowId, params) {
221
+ this.params = params;
222
+ return this.flowsApiService.getFlow(flowId).pipe(switchMap(flow => this.initFlowTemplates$(flow).pipe(map$1(() => flow))), tap$1(flow => this.flowSubj$.next(flow)), map$1(noop), catchError(e => {
223
+ this.flowSubj$.next(null);
224
+ return throwError(() => e);
225
+ }));
226
+ }
227
+ cleanup() {
228
+ this.flowSubj$.next(null);
229
+ this.params = undefined;
230
+ this.templates = {};
231
+ }
232
+ initFlowTemplates$(flow) {
233
+ if (isEmpty(flow.properties.templates)) {
234
+ return of(undefined);
235
+ }
236
+ return forkJoin([
237
+ this.templatesApiService.fetchTemplates$(),
238
+ this.customizationService?.getTemplates?.() ?? of([]),
239
+ ]).pipe(map$1(([templates, localTemplates]) => {
240
+ Object.entries({ ...this.defaultTemplates, ...flow.properties.templates }).forEach(([key, name]) => {
241
+ const type = this.remapTemplateName(key);
242
+ if (type) {
243
+ this.templates[type] =
244
+ localTemplates.find(template => template.name === name && template.type === type) ??
245
+ templates.find(template => template.name === name && template.type === type);
246
+ }
247
+ });
248
+ }));
249
+ }
250
+ remapTemplateName(templateType) {
251
+ switch (templateType) {
252
+ case 'flowEngine':
253
+ return UITemplateType.FLOW_ENGINE;
254
+ default:
255
+ break;
256
+ }
257
+ switch (templateType) {
258
+ case 'assets':
259
+ case 'shoppingCart':
260
+ // No separate Assets template at the moment
261
+ return UITemplateType.SHOPPING_CART;
262
+ case 'catalog':
263
+ return UITemplateType.CATALOG;
264
+ case 'docGen':
265
+ return UITemplateType.DOCGEN;
266
+ case 'guidedSelling':
267
+ return UITemplateType.GUIDED_SELLING;
268
+ case 'flowHeader':
269
+ return UITemplateType.FLOW_HEADER;
270
+ default:
271
+ break;
272
+ }
273
+ return undefined;
274
+ }
275
+ }
276
+ FlowInfoService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowInfoService, deps: [{ token: i1.FlowsApiService }, { token: i1.UITemplatesApiService }, { token: FLOW_CUSTOMIZATION, optional: true }], target: i0.ɵɵFactoryTarget.Injectable });
277
+ FlowInfoService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowInfoService });
278
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowInfoService, decorators: [{
279
+ type: Injectable
280
+ }], ctorParameters: function () { return [{ type: i1.FlowsApiService }, { type: i1.UITemplatesApiService }, { type: undefined, decorators: [{
281
+ type: Optional
282
+ }, {
283
+ type: Inject,
284
+ args: [FLOW_CUSTOMIZATION]
285
+ }] }]; } });
286
+
142
287
  class QuoteDraftService {
288
+ get isInitialized$() {
289
+ return this.isInitializedSubj$.asObservable();
290
+ }
143
291
  get isInitialized() {
144
292
  return this.isInitializedSubj$.getValue();
145
293
  }
@@ -161,40 +309,54 @@ class QuoteDraftService {
161
309
  return this.quoteSubj$.pipe(map(() => this.hasProducts));
162
310
  }
163
311
  get hasProducts() {
164
- const quoteDraft = this.quoteSubj$.value;
165
- return Boolean(quoteDraft && quoteDraft.currentState.length > 0);
312
+ return Boolean(this.quoteSubj$.value?.currentState.length);
313
+ }
314
+ get hasAssets$() {
315
+ return this.assetsSubj$.pipe(map(() => this.hasAssets));
316
+ }
317
+ get hasAssets() {
318
+ return Boolean(this.assetsSubj$.value?.currentState.length);
319
+ }
320
+ get assetsState() {
321
+ return this.assetsSubj$.value;
166
322
  }
167
- constructor(context, quoteApiService, priceApiService) {
323
+ constructor(context, accountApiService, quoteApiService) {
168
324
  this.context = context;
325
+ this.accountApiService = accountApiService;
169
326
  this.quoteApiService = quoteApiService;
170
- this.priceApiService = priceApiService;
171
327
  this.quoteSubj$ = new BehaviorSubject(null);
328
+ this.assetsSubj$ = new BehaviorSubject(null);
172
329
  this.resetSubj$ = new BehaviorSubject(true);
173
330
  this.isInitializedSubj$ = new BehaviorSubject(false);
174
331
  this.initialCurrentState = [];
175
332
  this._hasUnsavedChanges = false;
176
- this.allPriceLists = [];
177
- this.assetPriceLists = [];
178
333
  this.reset$ = this.resetSubj$.asObservable();
179
- this.activePriceList$ = this.context.resolve$().pipe(map(ctx => this.allPriceLists.find(priceList => priceList.id === ctx.properties.PriceListId)), map(priceList => priceList ?? null));
180
334
  this.isInitializedSubj$
181
- .pipe(filter(isInitialized => isInitialized), switchMap(() => this.quoteSubj$.asObservable()), skip(1), tap(quote => this.markAsUpdated(quote)))
335
+ .pipe(filter(isInitialized => isInitialized), switchMap$1(() => this.quoteSubj$.asObservable()), skip(1), tap(quote => this.markAsUpdated(quote)))
182
336
  .subscribe();
183
337
  }
184
338
  reset() {
185
339
  this.resetSubj$.next(true);
186
340
  this.quoteSubj$.next(null);
341
+ this.assetsSubj$.next(null);
187
342
  this.isInitialized = false;
188
343
  this.hasUnsavedChanges = false;
189
344
  }
190
- init(quoteId, params) {
191
- return zip(this.quoteApiService.getQuoteDraft(quoteId, params), this.priceApiService.getPriceLists()).pipe(tap(([quote, allPriceLists]) => {
192
- this.allPriceLists = allPriceLists;
345
+ init(headerId, params) {
346
+ const ctx = this.context.resolve();
347
+ const accountId = this.context.mode === ConfigurationContextMode.ACCOUNT ? headerId : ctx.properties.AccountId;
348
+ return zip(accountId ? this.accountApiService.getAssetsState(accountId, params) : of(null), this.quoteApiService.getQuoteState(headerId, params)).pipe(tap(([assets, quote]) => {
349
+ if (assets) {
350
+ this.assetsSubj$.next(assets);
351
+ }
193
352
  this.quoteSubj$.next(quote);
194
353
  this.context.update(quote.context);
195
- this.populateActivePriceLists$();
196
354
  }), map(() => noop()), take(1));
197
355
  }
356
+ finalizeInit() {
357
+ this.isInitialized = true;
358
+ this.hasUnsavedChanges = false;
359
+ }
198
360
  setCurrentLineItemState(lineItems) {
199
361
  const quoteDraft = this.quoteSubj$.value;
200
362
  if (!quoteDraft) {
@@ -234,6 +396,9 @@ class QuoteDraftService {
234
396
  approvalItems: priceSummary.approvalItems,
235
397
  });
236
398
  }
399
+ setAssetsState(assetsState) {
400
+ this.assetsSubj$.next(assetsState);
401
+ }
237
402
  get quoteDraft$() {
238
403
  return combineLatest([this.quoteSubj$, this.context.resolve$()]).pipe(map(() => this.quoteDraft), filter((quote) => Boolean(quote)), shareReplay());
239
404
  }
@@ -247,54 +412,12 @@ class QuoteDraftService {
247
412
  context: this.context.resolve(),
248
413
  };
249
414
  }
250
- get quoteDraftForActivePriceList() {
251
- const quoteDraft = this.quoteDraft;
252
- if (!quoteDraft) {
253
- return null;
254
- }
255
- return {
256
- ...quoteDraft,
257
- initialState: this.filterByActivePriceList(quoteDraft.initialState),
258
- currentState: this.filterByActivePriceList(quoteDraft.currentState),
259
- };
260
- }
261
415
  get currentState$() {
262
416
  return this.quoteDraft$.pipe(map(quote => quote.currentState));
263
417
  }
264
418
  get currentState() {
265
419
  return this.quoteDraft?.currentState ?? [];
266
420
  }
267
- /**
268
- * Stream of activeCurrentState
269
- */
270
- get activeCurrentState$() {
271
- return this.quoteDraft$.pipe(map(() => this.activeCurrentState));
272
- }
273
- /**
274
- * activeCurrentState is currentState passed through additional filters
275
- */
276
- get activeCurrentState() {
277
- let currentState = this.quoteDraft?.currentState ?? [];
278
- currentState = this.filterByActivePriceList(currentState);
279
- return currentState;
280
- }
281
- /**
282
- * Stream of activeInitialState
283
- */
284
- get activeInitialState$() {
285
- return this.quoteDraft$.pipe(map(() => this.activeInitialState));
286
- }
287
- /**
288
- * activeInitialState is initialState passed through additional filters
289
- */
290
- get activeInitialState() {
291
- const ctx = this.context.resolve();
292
- let initialState = this.quoteDraft?.initialState ?? [];
293
- if (ctx.mode === ConfigurationContextMode.ACCOUNT) {
294
- initialState = this.filterByActivePriceList(initialState);
295
- }
296
- return initialState;
297
- }
298
421
  get isStandalone() {
299
422
  return this.context.resolve().properties.standalone === 'true';
300
423
  }
@@ -317,50 +440,514 @@ class QuoteDraftService {
317
440
  }
318
441
  return false;
319
442
  }
320
- updateActivePriceList(priceListId) {
321
- this.context.update({ properties: { PriceListId: priceListId } });
443
+ markAsUpdated(quote) {
444
+ if (quote?.context.properties['#mode'] === ConfigurationContextMode.ACCOUNT) {
445
+ this.hasUnsavedChanges = !!quote && !quote.currentState.every(li => li.actionCode === 'EXIST');
446
+ }
447
+ else {
448
+ this.hasUnsavedChanges = !isEqual(this.initialCurrentState, quote?.currentState);
449
+ }
322
450
  }
323
- populateActivePriceLists$() {
324
- const ctx = this.context.resolve();
325
- const quoteDraft = this.quoteDraft;
326
- if (!quoteDraft) {
327
- return;
451
+ }
452
+ QuoteDraftService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: QuoteDraftService, deps: [{ token: ContextService }, { token: i1.AccountApiService }, { token: i1.QuoteApiService }], target: i0.ɵɵFactoryTarget.Injectable });
453
+ QuoteDraftService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: QuoteDraftService });
454
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: QuoteDraftService, decorators: [{
455
+ type: Injectable
456
+ }], ctorParameters: function () { return [{ type: ContextService }, { type: i1.AccountApiService }, { type: i1.QuoteApiService }]; } });
457
+
458
+ class FlowStateService {
459
+ constructor(contextService, quoteDraftService, flowInfoService, flowConfiguration, processorsApiService, flowStateApiService, quoteApiService, toastService, customizationService) {
460
+ this.contextService = contextService;
461
+ this.quoteDraftService = quoteDraftService;
462
+ this.flowInfoService = flowInfoService;
463
+ this.flowConfiguration = flowConfiguration;
464
+ this.processorsApiService = processorsApiService;
465
+ this.flowStateApiService = flowStateApiService;
466
+ this.quoteApiService = quoteApiService;
467
+ this.toastService = toastService;
468
+ this.customizationService = customizationService;
469
+ this.NOT_INITIALIZED = Symbol();
470
+ this.EXECUTION_BUFFER_TIME = 100;
471
+ this.executedFunctions = {};
472
+ this.stateId$ = new BehaviorSubject(null);
473
+ this._hasStatefulUnsavedChanges = true;
474
+ this.processors = {};
475
+ this.subscriptions = {};
476
+ this.flowStore = {};
477
+ this.statefulExecutionInProgress$ = new BehaviorSubject(false);
478
+ this.statefulRequestStream$ = new Subject();
479
+ this.cleanup$ = new Subject();
480
+ this.statefulExecutionRequest$ = this.initBufferedRequest$();
481
+ /*
482
+ In stateless mode watch QuoteDraft changes and call executeRequest so that
483
+ all subscriptions get their updates according to updated QuoteDraft
484
+ */
485
+ this.isInitialized$()
486
+ .pipe(filter$1(Boolean), filter$1(() => !this.getFlowSafe().properties.stateful), switchMap(() => this.flowConfiguration.updated$), switchMap(() => this.executeRequest$({}, true)))
487
+ .subscribe();
488
+ this.charges$ = this.flowInfoService.flow$.pipe(filter$1(isDefined), switchMap(() => {
489
+ if (this.flowInfoService.isLegacy) {
490
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(quoteDraft => quoteDraft.charges));
491
+ }
492
+ else {
493
+ return this.subscribe$(UITemplateType.FLOW_ENGINE, 'CHARGES', null, {
494
+ cold: true,
495
+ }).pipe(map$1(response => (response.success ? response.result : {})));
496
+ }
497
+ }), shareReplay$1(1));
498
+ this.charges$.subscribe();
499
+ this.pricePlans$ = this.flowInfoService.flow$.pipe(filter$1(isDefined), switchMap(() => {
500
+ if (this.flowInfoService.isLegacy) {
501
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(quoteDraft => quoteDraft.pricePlans));
502
+ }
503
+ else {
504
+ return this.subscribe$(UITemplateType.FLOW_ENGINE, 'PRICE_PLANS', null, {
505
+ cold: true,
506
+ }).pipe(map$1(response => (response.success ? response.result : {})));
507
+ }
508
+ }), shareReplay$1(1));
509
+ this.pricePlans$.subscribe();
510
+ this.activeMetrics$ = this.flowInfoService.flow$.pipe(filter$1(isDefined), switchMap(() => {
511
+ if (this.flowInfoService.isLegacy) {
512
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(quoteDraft => quoteDraft.activeMetrics));
513
+ }
514
+ else {
515
+ return this.subscribe$(UITemplateType.FLOW_ENGINE, 'ACTIVE_METRICS', null, {
516
+ cold: true,
517
+ }).pipe(map$1(response => (response.success ? response.result : [])));
518
+ }
519
+ }), shareReplay$1(1));
520
+ this.activeMetrics$.subscribe();
521
+ this.isPriceListLocked$ = this.flowInfoService.flow$.pipe(filter$1(isDefined), switchMap(() => {
522
+ if (this.flowInfoService.isLegacy) {
523
+ return of(false);
524
+ }
525
+ else {
526
+ return this.subscribe$(UITemplateType.FLOW_ENGINE, 'IS_PRICE_LIST_LOCKED', null, {
527
+ cold: true,
528
+ }).pipe(map$1(response => (response.success ? response.result : false)));
529
+ }
530
+ }), shareReplay$1(1));
531
+ this.isPriceListLocked$.subscribe();
532
+ }
533
+ init$() {
534
+ return this.initProcessors$().pipe(switchMap(() => {
535
+ if (this.getFlowSafe().properties.stateful) {
536
+ return this.initStateful$();
537
+ }
538
+ else {
539
+ return this.initStateless$();
540
+ }
541
+ }));
542
+ }
543
+ cleanup() {
544
+ Object.values(this.subscriptions).forEach(({ data$ }) => data$.complete());
545
+ this.subscriptions = {};
546
+ if (this.stateId$.value) {
547
+ this.flowStateApiService.cancel(this.stateId$.value).subscribe();
548
+ this.stateId$.next(null);
328
549
  }
329
- // In ACCOUNT mode populate price lists from related assets
330
- if (ctx.mode === ConfigurationContextMode.ACCOUNT) {
331
- // Populate list of price lists
332
- this.assetPriceLists = quoteDraft.currentState
333
- .map(({ priceListId }) => priceListId)
334
- .reduce((trunk, priceListId) => {
335
- if (!priceListId || trunk.some(item => item.id === priceListId)) {
336
- return trunk;
550
+ this.processors = {};
551
+ this.flowStore = {};
552
+ this.cleanup$.next();
553
+ }
554
+ get hasUnsavedChanges() {
555
+ return this.getFlowSafe().properties.stateful
556
+ ? this._hasStatefulUnsavedChanges
557
+ : this.quoteDraftService.hasUnsavedChanges;
558
+ }
559
+ get stateId() {
560
+ return this.stateId$.value;
561
+ }
562
+ get isExecutionInProgress$() {
563
+ return this.statefulExecutionInProgress$.asObservable();
564
+ }
565
+ isInitialized$() {
566
+ return combineLatest([this.stateId$, this.quoteDraftService.isInitialized$]).pipe(map$1(values => values.some(Boolean)));
567
+ }
568
+ isInitialized() {
569
+ return Boolean(this.stateId$.value) || this.quoteDraftService.isInitialized;
570
+ }
571
+ execute$(scope, exec) {
572
+ const request = this.execToRequest(scope, exec);
573
+ return this.executeRequest$(request).pipe(map$1(result => {
574
+ // Keep only requested results
575
+ const actualSelectors = Object.entries(result.selectors).reduce((trunk, [requestId, result]) => {
576
+ if (exec.selectors?.[requestId]) {
577
+ trunk[requestId] = result;
337
578
  }
338
- return [
339
- ...trunk,
340
- { id: priceListId, name: this.allPriceLists.find(item => item.id === priceListId)?.name ?? '' },
341
- ];
342
- }, []);
579
+ return trunk;
580
+ }, {});
581
+ return actualSelectors;
582
+ }));
583
+ }
584
+ dispatch$(scope, action, inputData) {
585
+ const exec = {
586
+ actions: [{ name: action, inputData }],
587
+ };
588
+ const request = this.execToRequest(scope, exec);
589
+ return this.executeRequest$(request).pipe(map$1(noop));
590
+ }
591
+ select$(scope, selectorName, inputData) {
592
+ const requestId = this.generateRequestId(scope, selectorName, inputData);
593
+ const request = this.execToRequest(scope, {
594
+ selectors: {
595
+ [requestId]: {
596
+ name: selectorName,
597
+ inputData,
598
+ },
599
+ },
600
+ });
601
+ return this.executeRequest$(request).pipe(map$1(response => response.selectors[requestId]));
602
+ }
603
+ subscribe$(scope, selectorName, inputData, options) {
604
+ const requestId = this.generateRequestId(scope, selectorName, inputData);
605
+ let subscription = this.subscriptions[requestId];
606
+ if (!subscription) {
607
+ const request = this.execToRequest(scope, {
608
+ selectors: {
609
+ [requestId]: {
610
+ name: selectorName,
611
+ inputData,
612
+ },
613
+ },
614
+ });
615
+ subscription = {
616
+ request,
617
+ data$: new BehaviorSubject(this.NOT_INITIALIZED),
618
+ };
619
+ this.subscriptions[requestId] = subscription;
620
+ if (!options?.cold) {
621
+ this.executeRequest$(request).subscribe();
622
+ }
343
623
  }
624
+ return subscription.data$.pipe(filter$1(data => data != this.NOT_INITIALIZED), map$1(data => data), finalize(() => {
625
+ if (!this.subscriptions[requestId]?.data$.observed) {
626
+ delete this.subscriptions[requestId];
627
+ }
628
+ }));
344
629
  }
345
- filterByActivePriceList(lineItems) {
346
- const ctx = this.context.resolve();
347
- return lineItems.filter(li => !li.priceListId || li.priceListId === ctx.properties.PriceListId);
630
+ save$() {
631
+ if (this.getFlowSafe().properties.stateful) {
632
+ if (this.stateId$.value) {
633
+ return this.flowStateApiService.save(this.stateId$.value);
634
+ }
635
+ }
636
+ else {
637
+ const quoteDraft = this.quoteDraftService.quoteDraft;
638
+ if (quoteDraft) {
639
+ return this.quoteApiService.upsertQuote(quoteDraft).pipe(tap$1(({ configurationId }) => {
640
+ this.contextService.update({ properties: { ConfigurationId: configurationId } });
641
+ }));
642
+ }
643
+ }
644
+ return of({ quoteId: '' });
348
645
  }
349
- markAsUpdated(quote) {
350
- if (quote?.context.properties.mode === ConfigurationContextMode.ACCOUNT) {
351
- this.hasUnsavedChanges = !!quote && !quote.currentState.every(li => li.actionCode === 'EXIST');
646
+ submit$() {
647
+ if (this.getFlowSafe().properties.stateful) {
648
+ if (this.stateId$.value) {
649
+ return this.flowStateApiService.submit(this.stateId$.value);
650
+ }
352
651
  }
353
652
  else {
354
- this.hasUnsavedChanges = !isEqual(this.initialCurrentState, quote?.currentState);
653
+ const quoteDraft = this.quoteDraftService.quoteDraft;
654
+ if (quoteDraft) {
655
+ return this.quoteApiService.submitQuote(quoteDraft).pipe(tap$1(({ configurationId }) => {
656
+ this.contextService.update({ properties: { ConfigurationId: configurationId } });
657
+ }));
658
+ }
355
659
  }
660
+ return of({ quoteId: '' });
661
+ }
662
+ getFlowStore() {
663
+ return this.flowStore;
664
+ }
665
+ getOwnerIdByScope(scope) {
666
+ const ownerId = this.flowInfoService.templates[scope]?.id;
667
+ if (!ownerId) {
668
+ throw `OwnerId is not found for scope ${scope}`;
669
+ }
670
+ return ownerId;
671
+ }
672
+ getScopeByOwnerId(id) {
673
+ for (const template of Object.values(this.flowInfoService.templates)) {
674
+ if (template.id === id) {
675
+ return template.type;
676
+ }
677
+ }
678
+ return;
679
+ }
680
+ execToRequest(scope, exec) {
681
+ const ownerId = this.getOwnerIdByScope(scope);
682
+ return {
683
+ actions: exec.actions?.map(action => ({ apiName: action.name, ownerId, inputData: action.inputData ?? {} })),
684
+ selectors: exec.selectors &&
685
+ Object.entries(exec.selectors).reduce((trunk, [key, selector]) => ({
686
+ ...trunk,
687
+ [key]: { apiName: selector.name, ownerId, inputData: selector.inputData ?? {} },
688
+ }), {}),
689
+ };
690
+ }
691
+ executeRequest$(request, forceSubscriptions = false) {
692
+ const fullRequest = cloneDeep(request);
693
+ if (fullRequest.actions?.length || forceSubscriptions) {
694
+ for (const subscription of Object.values(this.subscriptions)) {
695
+ fullRequest.selectors = assign(fullRequest.selectors, subscription.request.selectors);
696
+ }
697
+ }
698
+ const execution$ = this.getFlowSafe().properties.stateful
699
+ ? this.executeStateful$(fullRequest)
700
+ : this.executeStateless$(fullRequest);
701
+ return execution$.pipe(tap$1(result => this.handleSelectorsResponse(result.selectors)));
702
+ }
703
+ handleSelectorsResponse(selectors) {
704
+ Object.entries(selectors).forEach(([requestId, selectorResult]) => {
705
+ if (!selectorResult.success) {
706
+ this.toastService.add({ severity: ToastType.error, summary: selectorResult.errorMessage });
707
+ }
708
+ const subscription$ = this.subscriptions[requestId]?.data$;
709
+ if (subscription$ && subscription$.value !== selectorResult) {
710
+ subscription$.next(selectorResult);
711
+ }
712
+ });
713
+ }
714
+ initStateful$() {
715
+ // Subscriptions
716
+ this.subscribe$(UITemplateType.FLOW_ENGINE, 'CONTEXT', null, { cold: true })
717
+ .pipe(tap$1(response => {
718
+ if (response.success) {
719
+ this.contextService.update(response.result);
720
+ }
721
+ }), takeUntil(this.cleanup$))
722
+ .subscribe();
723
+ const processorsList = flatten(Object.values(this.processors).map(ownerMap => Object.values(ownerMap ?? {})));
724
+ const processors = processorsList.length ? processorsList : undefined;
725
+ const selectors = Object.values(this.subscriptions)
726
+ .map(({ request }) => request.selectors)
727
+ .filter(isDefined)
728
+ .reduce((trunk, selectors) => ({ ...trunk, ...selectors }), {});
729
+ const request = this.getDefaultExecutionRequestDTO();
730
+ return this.flowStateApiService
731
+ .init({
732
+ quoteId: this.contextService.resolve().headerId,
733
+ params: this.flowInfoService.params ?? {},
734
+ actionsOverride: processors?.filter(processor => processor.type === ConfigurationProcessorTypes.ACTION),
735
+ selectorsOverride: processors?.filter(processor => processor.type === ConfigurationProcessorTypes.SELECTOR),
736
+ selectors: { ...selectors, ...request.selectors },
737
+ actions: request.actions,
738
+ })
739
+ .pipe(map$1(({ stateId, selectors }) => {
740
+ this.handleSelectorsResponse(selectors);
741
+ this.stateId$.next(stateId);
742
+ }));
743
+ }
744
+ initBufferedRequest$() {
745
+ return this.statefulRequestStream$.pipe(buffer(this.statefulRequestStream$.pipe(debounceTime(this.EXECUTION_BUFFER_TIME))), switchMap(requests => {
746
+ if (!this.stateId$.value) {
747
+ throw 'Stateful session is not initialized';
748
+ }
749
+ // merge buffered requests
750
+ const request = {
751
+ actions: requests.flatMap(({ actions }) => actions).filter(isDefined),
752
+ selectors: requests
753
+ .map(({ selectors }) => selectors)
754
+ .filter(isDefined)
755
+ .reduce((acc, selectorsMap) => Object.assign(acc, selectorsMap), {}),
756
+ };
757
+ this.statefulExecutionInProgress$.next(true);
758
+ return this.flowStateApiService.execute(this.stateId$.value, request);
759
+ }), tap$1(({ stateId }) => this.stateId$.next(stateId)), share(), tap$1(() => this.statefulExecutionInProgress$.next(false)), catchError(e => {
760
+ this.statefulExecutionInProgress$.next(false);
761
+ return throwError(() => e);
762
+ }));
763
+ }
764
+ executeStateful$(request) {
765
+ return this.statefulExecutionInProgress$.pipe(filter$1(inProgress => !inProgress), take$1(1), switchMap(() =>
766
+ // make sure stream switches to statefulExecutionRequest$ before pushing an execution request
767
+ combineLatest([
768
+ this.statefulExecutionRequest$,
769
+ of(undefined).pipe(tap$1(() => this.statefulRequestStream$.next(request))),
770
+ ])), map$1(([response]) => response), take$1(1));
771
+ }
772
+ initStateless$() {
773
+ const { headerId } = this.contextService.resolve();
774
+ return this.quoteDraftService.init(headerId, this.flowInfoService.params ?? {}).pipe(tap$1(() => {
775
+ const assets = this.quoteDraftService.assetsState;
776
+ if (assets) {
777
+ this.flowStore = { ...this.flowStore, assets };
778
+ }
779
+ }), switchMap(() => this.executeRequest$(this.getDefaultExecutionRequestDTO())), switchMap(() => this.calculate$()), tap$1(() => this.quoteDraftService.finalizeInit()), map$1(noop));
780
+ }
781
+ calculate$() {
782
+ const flowState = this.quoteDraftService.quoteDraft;
783
+ if (!flowState) {
784
+ return of(undefined);
785
+ }
786
+ /*
787
+ Don't execute procedures when:
788
+ * Initializing a standalone product configuration UI, as procedure is execute in /price call
789
+ * Initializing an empty account (account with no assets)
790
+ */
791
+ const isEmptyAccountMode = this.contextService.mode === ConfigurationContextMode.ACCOUNT &&
792
+ !this.quoteDraftService.hasProducts &&
793
+ !this.quoteDraftService.hasAssets &&
794
+ !this.quoteDraftService.quoteDraft?.initialState.length;
795
+ if (this.quoteDraftService.isStandalone || isEmptyAccountMode) {
796
+ return of(undefined);
797
+ }
798
+ return this.flowConfiguration.calculate$(flowState);
799
+ }
800
+ executeStateless$(request) {
801
+ return of(undefined).pipe(tap$1(() => this.executeStatelessActions(request)), switchMap(() => {
802
+ /*
803
+ Skip price calculation in case
804
+ 1. No actions in the request
805
+ 2. Initialization process execution (state not initialized yet)
806
+ */
807
+ if (!request.actions?.length || !this.isInitialized()) {
808
+ return of(undefined);
809
+ }
810
+ else {
811
+ return this.calculate$();
812
+ }
813
+ }), map$1(() => this.executeStatelessSelectors(request)));
814
+ }
815
+ executeStatelessActions(request) {
816
+ if (!this.quoteDraftService.quoteDraft || !request.actions?.length) {
817
+ return;
818
+ }
819
+ let flowState = this.quoteDraftService.quoteDraft;
820
+ request.actions.forEach(action => {
821
+ try {
822
+ flowState = this.executeActionScript(flowState, action) ?? flowState;
823
+ }
824
+ catch (e) {
825
+ console.error(e);
826
+ this.toastService.add({ severity: ToastType.error, summary: String(e) });
827
+ throw e;
828
+ }
829
+ });
830
+ this.quoteDraftService.updateQuoteDraft(flowState);
831
+ }
832
+ executeStatelessSelectors(request) {
833
+ if (!this.quoteDraftService.quoteDraft) {
834
+ throw 'QuoteDraft is not initialized';
835
+ }
836
+ const flowState = this.quoteDraftService.quoteDraft;
837
+ return EntityUtil.entries(request.selectors ?? {}).reduce((result, [key, selector]) => {
838
+ try {
839
+ result.selectors[key] = {
840
+ success: true,
841
+ result: this.executeSelectorScript(flowState, selector),
842
+ };
843
+ }
844
+ catch (e) {
845
+ console.error(e);
846
+ result.selectors[key] = {
847
+ success: false,
848
+ errorMessage: String(e),
849
+ };
850
+ }
851
+ return result;
852
+ }, { stateId: '', selectors: {} });
853
+ }
854
+ getFlowSafe() {
855
+ if (!this.flowInfoService.flow) {
856
+ throw 'Flow is not defined';
857
+ }
858
+ return this.flowInfoService.flow;
859
+ }
860
+ initProcessors$() {
861
+ const hasOverrides = Boolean(this.customizationService?.getTemplateConfigurationProcessors);
862
+ const flow = this.getFlowSafe();
863
+ if (flow.properties.stateful && !hasOverrides) {
864
+ // Skip initialization as backend will take processors from SF
865
+ return of(undefined);
866
+ }
867
+ const owners$ = Object.values(this.flowInfoService.templates)
868
+ .map(template => {
869
+ if (!template) {
870
+ return;
871
+ }
872
+ const localProcessors$ = this.customizationService?.getTemplateConfigurationProcessors?.(template.name) ?? of(null);
873
+ return localProcessors$.pipe(switchMap(processors => processors ? of(processors) : this.processorsApiService.fetchConfigurationProcessors$(template.id)), tap$1(processors => {
874
+ const processorsMap = processors.reduce((acc, p) => {
875
+ acc[p.apiName] = p;
876
+ return acc;
877
+ }, {});
878
+ this.processors[template.id] = processorsMap;
879
+ }));
880
+ })
881
+ .filter(isDefined);
882
+ if (!owners$.length) {
883
+ return of(undefined);
884
+ }
885
+ return forkJoin(owners$).pipe(map$1(noop));
886
+ }
887
+ executeActionScript(request, executable) {
888
+ const configurationProcessor = this.processors[executable.ownerId]?.[executable.apiName];
889
+ if (!configurationProcessor?.script) {
890
+ const scope = this.getScopeByOwnerId(executable.ownerId);
891
+ const scopeText = scope ? ` in ${scope}` : '';
892
+ throw `ConfigurationProcessor ${executable.apiName}${scopeText} not found`;
893
+ }
894
+ return this.executeProcessorScript(request, configurationProcessor, executable.inputData);
895
+ }
896
+ executeSelectorScript(request, executable) {
897
+ const configurationProcessor = this.processors[executable.ownerId]?.[executable.apiName];
898
+ if (!configurationProcessor?.script) {
899
+ const scope = this.getScopeByOwnerId(executable.ownerId);
900
+ const scopeText = scope ? ` in ${scope}` : '';
901
+ throw `ConfigurationProcessor ${executable.apiName}${scopeText} not found`;
902
+ }
903
+ return this.executeProcessorScript(request, configurationProcessor, executable.inputData);
904
+ }
905
+ executeProcessorScript(request, configurationProcessor, inputData) {
906
+ const scope = this.getScopeByOwnerId(configurationProcessor.ownerId ?? '');
907
+ let functionToExecute = this.executedFunctions[scope + configurationProcessor.apiName];
908
+ if (!functionToExecute) {
909
+ const script = `${configurationProcessor.script}\nreturn transform;`;
910
+ const sourceMap = `\n//# sourceURL=${scope ? scope + '/' : ''}${configurationProcessor.apiName}.js`;
911
+ functionToExecute = new Function(script + sourceMap)();
912
+ this.executedFunctions[scope + configurationProcessor.apiName] = functionToExecute;
913
+ }
914
+ return functionToExecute({
915
+ request,
916
+ inputData,
917
+ flowStore: this.flowStore,
918
+ });
919
+ }
920
+ generateRequestId(scope, selectorName, inputData) {
921
+ const inputDataHash = UUID.hex(JSON.stringify(inputData) || '').slice(0, 8);
922
+ return `${scope}/${selectorName}/${inputDataHash}`;
923
+ }
924
+ getDefaultExecutionRequestDTO() {
925
+ const request = {
926
+ actions: [],
927
+ selectors: {},
928
+ };
929
+ if (this.getFlowSafe().properties.standalone) {
930
+ return request;
931
+ }
932
+ const flowEngineTemplateId = this.getOwnerIdByScope(UITemplateType.FLOW_ENGINE);
933
+ request.actions?.push({
934
+ apiName: 'UPDATE_CONTEXT_PROPERTIES',
935
+ ownerId: flowEngineTemplateId,
936
+ inputData: this.contextService.resolve().properties,
937
+ });
938
+ return request;
356
939
  }
357
940
  }
358
- QuoteDraftService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: QuoteDraftService, deps: [{ token: ContextService }, { token: i1.QuoteApiService }, { token: i1.PriceApiService }], target: i0.ɵɵFactoryTarget.Injectable });
359
- QuoteDraftService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: QuoteDraftService, providedIn: 'root' });
360
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: QuoteDraftService, decorators: [{
361
- type: Injectable,
362
- args: [{ providedIn: 'root' }]
363
- }], ctorParameters: function () { return [{ type: ContextService }, { type: i1.QuoteApiService }, { type: i1.PriceApiService }]; } });
941
+ FlowStateService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowStateService, deps: [{ token: ContextService }, { token: QuoteDraftService }, { token: FlowInfoService }, { token: FlowConfigurationService }, { token: i1.ConfigurationProcessorsApiService }, { token: i1.FlowStateApiService }, { token: i1.QuoteApiService }, { token: i6.ToastService }, { token: FLOW_CUSTOMIZATION, optional: true }], target: i0.ɵɵFactoryTarget.Injectable });
942
+ FlowStateService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowStateService });
943
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowStateService, decorators: [{
944
+ type: Injectable
945
+ }], ctorParameters: function () { return [{ type: ContextService }, { type: QuoteDraftService }, { type: FlowInfoService }, { type: FlowConfigurationService }, { type: i1.ConfigurationProcessorsApiService }, { type: i1.FlowStateApiService }, { type: i1.QuoteApiService }, { type: i6.ToastService }, { type: undefined, decorators: [{
946
+ type: Optional
947
+ }, {
948
+ type: Inject,
949
+ args: [FLOW_CUSTOMIZATION]
950
+ }] }]; } });
364
951
 
365
952
  const findLineItem = (id, lineItems) => {
366
953
  return findLineItemWithComparator(lineItems, (li) => li.id === id);
@@ -418,27 +1005,42 @@ const replaceLineItem = (lineItem, replaceTo, skipCardinalityCalculation = false
418
1005
  lineItems: lineItem.lineItems.map(li => replaceLineItem(li, replaceTo, skipCardinalityCalculation)),
419
1006
  };
420
1007
  };
421
- const calculateCardinalityVariables = (lineItems) => {
1008
+ const collectCardinalityComputations = (portDomains) => {
1009
+ const cardinalityComputations = new Map();
1010
+ entries(portDomains).forEach(([key, portDomain]) => {
1011
+ cardinalityComputations.set(key, portDomain.properties['cardinalityComputation'] === 'true');
1012
+ });
1013
+ return cardinalityComputations;
1014
+ };
1015
+ const calculateCardinalityVariables = (lineItems, cardinalityComputations) => {
422
1016
  const cardVars = new Map();
423
1017
  lineItems
424
1018
  .filter(({ port, type }) => !!port && !!type)
425
1019
  .forEach(li => {
426
- const cardinalityVariableName = `#CV-${li.type}@${li.port}`;
427
- cardVars.set(cardinalityVariableName, (cardVars.get(cardinalityVariableName) ?? 0) + li.qty);
1020
+ if (cardinalityComputations.get(`${li.port}`)) {
1021
+ const cardinalityVariableName = `#CV-${li.type}@${li.port}`;
1022
+ cardVars.set(cardinalityVariableName, (cardVars.get(cardinalityVariableName) ?? 0) + li.qty);
1023
+ }
428
1024
  });
429
1025
  return cardVars;
430
1026
  };
1027
+ const cardinalityRegexp = new RegExp('#CV-[a-zA-Z0-9_]+@(?<portName>[a-zA-Z0-9_]+)');
431
1028
  const recalculateCardinalityVariables = (original, updated) => {
432
- const cardinalityVariables = calculateCardinalityVariables(updated.lineItems);
433
- const originalCardinalityVariables = calculateCardinalityVariables(original.lineItems);
1029
+ const cardinalityComputations = collectCardinalityComputations(updated.portDomains ?? original.portDomains ?? {});
1030
+ const cardinalityVariables = calculateCardinalityVariables(updated.lineItems, cardinalityComputations);
1031
+ const originalCardinalityVariables = calculateCardinalityVariables(original.lineItems, cardinalityComputations);
434
1032
  originalCardinalityVariables.forEach((value, key) => {
435
- if (cardinalityVariables.get(key) === value) {
436
- // no need to update cardinality if no changes
437
- cardinalityVariables.delete(key);
438
- }
439
- else if (!cardinalityVariables.has(key)) {
440
- // remove last item from port
441
- cardinalityVariables.set(key, 0);
1033
+ const execArray = cardinalityRegexp.exec(key);
1034
+ const portName = execArray?.groups?.['portName'];
1035
+ if (!portName || cardinalityComputations.get(portName)) {
1036
+ if (cardinalityVariables.get(key) === value) {
1037
+ // no need to update cardinality if no changes
1038
+ cardinalityVariables.delete(key);
1039
+ }
1040
+ else if (!cardinalityVariables.has(key)) {
1041
+ // remove last item from port
1042
+ cardinalityVariables.set(key, 0);
1043
+ }
442
1044
  }
443
1045
  });
444
1046
  return {
@@ -458,7 +1060,7 @@ const upsertAttributes = (originalAttributes, attributesToUpsert) => {
458
1060
  const [origAttr] = getAttributes(acc, [name]);
459
1061
  return [
460
1062
  ...acc.filter(attr => attr.name !== name),
461
- { ...(origAttr ?? { name }), cfgStatus: origAttr ? 'Changed' : 'User', value },
1063
+ { ...(origAttr ?? { name, type: '' }), cfgStatus: origAttr ? 'Changed' : 'User', value },
462
1064
  ];
463
1065
  }, originalAttributes);
464
1066
  };
@@ -494,20 +1096,6 @@ const getRecommendedPrices = (portDomain, type) => {
494
1096
  }, [0, 0]) ?? [0, 0];
495
1097
  return { net, list };
496
1098
  };
497
- const generateModifiedAssetsMap = (lineItems) => {
498
- return lineItems.reduce((acc, li) => {
499
- const isModified = isLineItemModified(li);
500
- if (!isModified) {
501
- return acc;
502
- }
503
- const target = getOriginParent(lineItems, li);
504
- const id = target?.assetId ?? target?.openOrderLineItemId;
505
- if (id) {
506
- acc[id] = true;
507
- }
508
- return acc;
509
- }, {});
510
- };
511
1099
  const getOriginParent = (lineItems, currentLineItem) => {
512
1100
  let target = currentLineItem;
513
1101
  while (target && target.rampInstanceId) {
@@ -515,11 +1103,11 @@ const getOriginParent = (lineItems, currentLineItem) => {
515
1103
  }
516
1104
  return target;
517
1105
  };
518
- const isLineItemModified = (lineItem) => {
519
- if (lineItem.actionCode === 'EXIST' && lineItem.status === 'PENDING') {
1106
+ const assetPredicateFn = (lineItem, assetId) => {
1107
+ if (!assetId) {
520
1108
  return false;
521
1109
  }
522
- return lineItem.actionCode !== 'EXIST';
1110
+ return lineItem.assetId === assetId || lineItem.openOrderLineItemId === assetId;
523
1111
  };
524
1112
  const multiplyLineItems = (lineItem, qty, split) => {
525
1113
  if (split) {
@@ -528,7 +1116,7 @@ const multiplyLineItems = (lineItem, qty, split) => {
528
1116
  id: UUID.UUID(),
529
1117
  lineItems: lineItem.lineItems.map(unifyIds),
530
1118
  });
531
- return map$1(new Array(qty), () => unifyIds(lineItem));
1119
+ return map$2(new Array(qty), () => unifyIds(lineItem));
532
1120
  }
533
1121
  else {
534
1122
  return [
@@ -548,18 +1136,16 @@ const filterOutTechnicalAttributes = (attributes) => {
548
1136
 
549
1137
  var lineItem_utils = /*#__PURE__*/Object.freeze({
550
1138
  __proto__: null,
551
- calculateCardinalityVariables: calculateCardinalityVariables,
1139
+ assetPredicateFn: assetPredicateFn,
552
1140
  filterOutTechnicalAttributes: filterOutTechnicalAttributes,
553
1141
  findLineItem: findLineItem,
554
1142
  findLineItemWithComparator: findLineItemWithComparator,
555
1143
  generateLineItem: generateLineItem,
556
- generateModifiedAssetsMap: generateModifiedAssetsMap,
557
1144
  getAttributeValue: getAttributeValue,
558
1145
  getAttributes: getAttributes,
559
1146
  getOriginParent: getOriginParent,
560
1147
  getRecommendedPrices: getRecommendedPrices,
561
1148
  insertLineItem: insertLineItem,
562
- isLineItemModified: isLineItemModified,
563
1149
  isTechnicalAttribute: isTechnicalAttribute,
564
1150
  mapAttributes: mapAttributes,
565
1151
  multiplyLineItems: multiplyLineItems,
@@ -587,16 +1173,19 @@ class RuntimeSettingsService {
587
1173
  };
588
1174
  }
589
1175
  create() {
590
- return this.configurationSettingsApiService.fetchSettings().pipe(map$2(settings => this.parseConfigurationSettings(settings)), tap$1(configurationSettings => {
1176
+ return this.configurationSettingsApiService.fetchSettings().pipe(map$1(settings => this.parseConfigurationSettings(settings)), tap$1(configurationSettings => {
591
1177
  this.configurationSettings$.next(configurationSettings);
592
1178
  this.addShoppingCartSettings(configurationSettings['shopping-cart'] ?? []);
593
1179
  this.formattingSettings = this.getFormattingSettings();
594
- }), map$2(() => undefined));
1180
+ }), map$1(() => undefined));
595
1181
  }
596
1182
  initCurrency(iso) {
597
1183
  if (iso) {
598
1184
  const symbol = this.getCurrencySymbol('en-US', iso);
599
1185
  this.currencySettings$.next({ iso, symbol });
1186
+ if (this.formattingSettings) {
1187
+ this.formattingSettings.currencySymbol = symbol;
1188
+ }
600
1189
  }
601
1190
  }
602
1191
  getFormattingSettings() {
@@ -667,32 +1256,11 @@ class RuntimeSettingsService {
667
1256
  }
668
1257
  }
669
1258
  RuntimeSettingsService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: RuntimeSettingsService, deps: [{ token: i1.ConfigurationSettingsApiService }], target: i0.ɵɵFactoryTarget.Injectable });
670
- RuntimeSettingsService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: RuntimeSettingsService, providedIn: 'root' });
1259
+ RuntimeSettingsService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: RuntimeSettingsService });
671
1260
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: RuntimeSettingsService, decorators: [{
672
- type: Injectable,
673
- args: [{ providedIn: 'root' }]
1261
+ type: Injectable
674
1262
  }], ctorParameters: function () { return [{ type: i1.ConfigurationSettingsApiService }]; } });
675
1263
 
676
- const FORMATTING_SETTINGS_TOKEN = new InjectionToken('Summary of formatting settings for variant types of data, e.g. numbers, text, dates, etc');
677
-
678
- var RuntimeMode;
679
- (function (RuntimeMode) {
680
- RuntimeMode[RuntimeMode["TEST"] = 0] = "TEST";
681
- RuntimeMode[RuntimeMode["PROD"] = 1] = "PROD";
682
- })(RuntimeMode || (RuntimeMode = {}));
683
- var RuntimeOperation;
684
- (function (RuntimeOperation) {
685
- RuntimeOperation["INIT"] = "INIT";
686
- RuntimeOperation["UPDATE"] = "UPDATE";
687
- })(RuntimeOperation || (RuntimeOperation = {}));
688
- var RuntimeStep;
689
- (function (RuntimeStep) {
690
- RuntimeStep["START"] = "START";
691
- RuntimeStep["UPDATE"] = "UPDATE";
692
- })(RuntimeStep || (RuntimeStep = {}));
693
-
694
- const UI_DEFINITION_VERSION = 3;
695
-
696
1264
  class LineItemWorker {
697
1265
  constructor(src) {
698
1266
  this.li = { ...src };
@@ -711,6 +1279,14 @@ class LineItemWorker {
711
1279
  }
712
1280
  }
713
1281
 
1282
+ function extractMetadata(uiDefinition) {
1283
+ return omit(uiDefinition, [
1284
+ 'children',
1285
+ 'pages',
1286
+ 'components',
1287
+ ]);
1288
+ }
1289
+
714
1290
  class ConfigurationService {
715
1291
  constructor(quoteDraftService, runtimeService, contextService, configurationApiService, messageService, dialogService, runtimeSettings) {
716
1292
  this.quoteDraftService = quoteDraftService;
@@ -721,10 +1297,7 @@ class ConfigurationService {
721
1297
  this.dialogService = dialogService;
722
1298
  this.runtimeSettings = runtimeSettings;
723
1299
  this.mode = ConfigurationMode.SEARCH;
724
- this.lineItem = new BehaviorSubject(undefined);
725
- this.charges = new BehaviorSubject({});
726
- this.pricePlans = new BehaviorSubject({});
727
- this.procedureContext = new BehaviorSubject({});
1300
+ this.configurationState = new BehaviorSubject(null);
728
1301
  this.isLoadingSubj$ = new BehaviorSubject(false);
729
1302
  this.isLoading$ = this.isLoadingSubj$.asObservable();
730
1303
  this.hasUnsavedChanges = false;
@@ -733,23 +1306,23 @@ class ConfigurationService {
733
1306
  this.hasUnsavedChanges = false;
734
1307
  this.runtimeService.reset();
735
1308
  this.configurableRamp = undefined;
736
- this.lineItem.next(undefined);
737
- this.charges.next({});
738
- this.pricePlans.next({});
1309
+ this.configurationState.next(null);
739
1310
  }
740
1311
  patch$(lineItem, options) {
741
- if (!this.lineItem.value) {
1312
+ const source = this.getSnapshot();
1313
+ if (!source) {
742
1314
  return throwError(() => new Error(`Source LineItem not found`));
743
1315
  }
744
1316
  const skipCardinalityCalculation = options?.skipCardinalityCalculation || this.contextSnapshot.properties['#skipCardinalityCalculation'] === 'true';
745
- this.configurableRamp = new LineItemWorker(this.lineItem.value).replace(lineItem, skipCardinalityCalculation).li;
746
- return this.configure().pipe(catchError(error => {
1317
+ this.configurableRamp = new LineItemWorker(source).replace(lineItem, skipCardinalityCalculation).li;
1318
+ return this.configure().pipe(catchError$1(error => {
747
1319
  console.error(error);
748
1320
  if (!this.runtimeService.uiDefinitionProperties.suppressToastMessages) {
749
1321
  this.messageService.add({ severity: 'error', summary: error });
750
1322
  }
751
1323
  // bounce back if configuration call has failed
752
- this.lineItem.next(this.lineItem.value ? { ...this.lineItem.value } : undefined);
1324
+ const prevState = this.configurationState.value;
1325
+ this.configurationState.next(prevState ? { ...prevState } : null);
753
1326
  return throwError(() => error);
754
1327
  }), tap(() => {
755
1328
  if (!this.hasUnsavedChanges) {
@@ -764,10 +1337,10 @@ class ConfigurationService {
764
1337
  this.configurableRamp = lineItem;
765
1338
  }
766
1339
  get() {
767
- return this.lineItem.asObservable().pipe(shareReplay$1());
1340
+ return this.configurationState.pipe(map(state => state?.lineItem), shareReplay$1());
768
1341
  }
769
1342
  getSnapshot() {
770
- return this.lineItem.value ? { ...this.lineItem.value } : undefined;
1343
+ return this.configurationState.value?.lineItem ? { ...this.configurationState.value?.lineItem } : undefined;
771
1344
  }
772
1345
  getRuntimeModel() {
773
1346
  const runtimeModel = this.runtimeService.runtimeModel;
@@ -783,6 +1356,12 @@ class ConfigurationService {
783
1356
  }
784
1357
  return runtimeContext;
785
1358
  }
1359
+ get state$() {
1360
+ return this.configurationState.asObservable();
1361
+ }
1362
+ get stateSnapshot() {
1363
+ return this.configurationState.value;
1364
+ }
786
1365
  get contextSnapshot() {
787
1366
  return this.contextService.resolve();
788
1367
  }
@@ -790,22 +1369,22 @@ class ConfigurationService {
790
1369
  return this.contextService.resolve$();
791
1370
  }
792
1371
  get charges$() {
793
- return this.charges.asObservable();
1372
+ return this.configurationState.pipe(map(state => state?.charges ?? {}));
794
1373
  }
795
1374
  get chargesSnapshot() {
796
- return this.charges.value;
1375
+ return this.configurationState.value?.charges ?? {};
797
1376
  }
798
1377
  get pricePlans$() {
799
- return this.pricePlans.asObservable();
1378
+ return this.configurationState.pipe(map(state => state?.pricePlans ?? {}));
800
1379
  }
801
1380
  get pricePlansSnapshot() {
802
- return this.pricePlans.value;
1381
+ return this.configurationState.value?.pricePlans ?? {};
803
1382
  }
804
1383
  get procedureContext$() {
805
- return this.procedureContext.asObservable();
1384
+ return this.configurationState.pipe(map(state => state?.procedureContext ?? {}));
806
1385
  }
807
1386
  get procedureContextSnapshot() {
808
- return this.procedureContext.value;
1387
+ return this.configurationState.value?.procedureContext ?? {};
809
1388
  }
810
1389
  configure() {
811
1390
  return this.configureRequest$(this.generateRequest());
@@ -825,44 +1404,55 @@ class ConfigurationService {
825
1404
  runtimeModel,
826
1405
  pricingEnabled,
827
1406
  });
828
- return configure$.pipe(tap(({ lineItem, context, charges, pricePlans, deletedLineItems, procedureContext }) => {
829
- this.contextService.update(context ?? {});
830
- this.charges.next(charges ?? {});
831
- this.pricePlans.next(pricePlans ?? {});
832
- this.procedureContext.next(procedureContext ?? {});
833
- if (lineItem) {
834
- this.lineItem.next(lineItem);
835
- }
836
- if (deletedLineItems?.length) {
1407
+ return configure$.pipe(tap(result => {
1408
+ this.contextService.update(result.context);
1409
+ this.configurationState.next(result);
1410
+ if (result.deletedLineItems?.length) {
837
1411
  this.showInactiveProductsConfirmation();
838
1412
  }
839
- this.configurableRamp = lineItem;
840
- }), map(({ lineItem }) => lineItem), catchError(error => throwError(() => new Error(error.error?.message || error.message || JSON.stringify(error)))), finalize(() => this.isLoadingSubj$.next(false)));
1413
+ this.configurableRamp = result.lineItem;
1414
+ }), map(({ lineItem }) => lineItem), catchError$1(error => throwError(() => new Error(error.error?.message || error.message || JSON.stringify(error)))), finalize$1(() => this.isLoadingSubj$.next(false)));
841
1415
  }
842
1416
  configureExternal$(props) {
843
1417
  return this.runtimeService
844
1418
  .init({ productId: props.productId, defaultQty: props.qty, attributesMap: props.attributesMap })
845
- .pipe(switchMap(() => this.configure()), first(), catchError(error => {
1419
+ .pipe(switchMap$1(() => this.configure()), first(), catchError$1(error => {
846
1420
  this.messageService.add({ severity: ToastType.error, summary: error });
847
1421
  throw error;
848
- }), finalize(() => this.reset()));
1422
+ }), finalize$1(() => this.reset()));
849
1423
  }
850
1424
  configureGuidedSelling$(data) {
851
1425
  return this.configurationApiService
852
1426
  .configureLineItem({
853
1427
  configurationRequest: getGuidedSellingConfigurationRequest(data, this.contextService.resolve()),
854
1428
  })
855
- .pipe(catchError(error => {
1429
+ .pipe(catchError$1(error => {
856
1430
  if (error instanceof HttpErrorResponse) {
857
1431
  this.messageService.add({ severity: ToastType.error, summary: error.error.message || error.error });
858
1432
  }
859
1433
  throw error;
860
1434
  }));
861
1435
  }
862
- generateRequest() {
1436
+ generateRequest(lightMode = true) {
1437
+ const lineItem = this.generateLineItem();
1438
+ let request = {
1439
+ lineItem,
1440
+ mode: this.mode,
1441
+ step: !this.configurationState.value?.lineItem ? RuntimeStep.START : RuntimeStep.UPDATE,
1442
+ attributeDomainMode: 'ALL',
1443
+ context: this.contextService.resolve(),
1444
+ lineItems: this.quoteDraftService.quoteDraft?.currentState || [],
1445
+ asset: this.getAsset(),
1446
+ };
1447
+ if (lightMode) {
1448
+ request = ConfigurationTranslatorUtils.lightenConfigurationRequest(request);
1449
+ }
1450
+ return request;
1451
+ }
1452
+ generateLineItem() {
863
1453
  const runtimeContext = this.getRuntimeContext();
864
1454
  const uiDefinitionProperties = this.getUIDefinitionProperties();
865
- let lineItem = this.configurableRamp;
1455
+ let lineItem = cloneDeep(this.configurableRamp);
866
1456
  if (!lineItem) {
867
1457
  const { initializationProps } = this.runtimeService ?? {};
868
1458
  lineItem = getDefaultLineItem(runtimeContext, uiDefinitionProperties, initializationProps?.defaultQty);
@@ -872,17 +1462,15 @@ class ConfigurationService {
872
1462
  lineItem = new LineItemWorker(lineItem).patchAttribute(attributes).li;
873
1463
  }
874
1464
  }
875
- let request = {
876
- lineItem,
877
- mode: this.mode,
878
- step: !this.lineItem.value ? RuntimeStep.START : RuntimeStep.UPDATE,
879
- attributeDomainMode: 'ALL',
880
- context: this.contextService.resolve(),
881
- lineItems: this.quoteDraftService.quoteDraft?.currentState || [],
882
- asset: this.getAsset(),
883
- };
884
- request = ConfigurationTranslatorUtils.lightenConfigurationRequest(request);
885
- return request;
1465
+ return lineItem;
1466
+ }
1467
+ getAsset() {
1468
+ const lineItem = this.configurableRamp;
1469
+ if (!lineItem) {
1470
+ return;
1471
+ }
1472
+ const assetId = lineItem.assetId ?? lineItem.openOrderLineItemId;
1473
+ return this.quoteDraftService.assetsState?.initialState.find(li => assetPredicateFn(li, assetId));
886
1474
  }
887
1475
  getUIDefinitionProperties() {
888
1476
  return {
@@ -914,27 +1502,12 @@ class ConfigurationService {
914
1502
  }
915
1503
  });
916
1504
  }
917
- getAsset() {
918
- const lineItem = this.configurableRamp;
919
- if (!lineItem) {
920
- return;
921
- }
922
- return this.quoteDraftService.quoteDraft?.initialState.find(a => a.id === lineItem.openOrderLineItemId || a.id === lineItem.assetId);
923
- }
924
1505
  }
925
- ConfigurationService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationService, deps: [{ token: QuoteDraftService }, { token: ConfigurationRuntimeService }, { token: ContextService }, { token: i1.ConfigurationApiService }, { token: i5.MessageService }, { token: i6.DialogService }, { token: RuntimeSettingsService }], target: i0.ɵɵFactoryTarget.Injectable });
1506
+ ConfigurationService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationService, deps: [{ token: QuoteDraftService }, { token: ConfigurationRuntimeService }, { token: ContextService }, { token: i1.ConfigurationApiService }, { token: i5.MessageService }, { token: i6$1.DialogService }, { token: RuntimeSettingsService }], target: i0.ɵɵFactoryTarget.Injectable });
926
1507
  ConfigurationService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationService });
927
1508
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationService, decorators: [{
928
1509
  type: Injectable
929
- }], ctorParameters: function () { return [{ type: QuoteDraftService }, { type: ConfigurationRuntimeService }, { type: ContextService }, { type: i1.ConfigurationApiService }, { type: i5.MessageService }, { type: i6.DialogService }, { type: RuntimeSettingsService }]; } });
930
-
931
- function extractMetadata(uiDefinition) {
932
- return omit(uiDefinition, [
933
- 'children',
934
- 'pages',
935
- 'components',
936
- ]);
937
- }
1510
+ }], ctorParameters: function () { return [{ type: QuoteDraftService }, { type: ConfigurationRuntimeService }, { type: ContextService }, { type: i1.ConfigurationApiService }, { type: i5.MessageService }, { type: i6$1.DialogService }, { type: RuntimeSettingsService }]; } });
938
1511
 
939
1512
  class FlowUpdateService {
940
1513
  update(rootLineItems, updates, charges) {
@@ -1075,6 +1648,8 @@ class FlowConfigurationService {
1075
1648
  this.quoteDraftService = quoteDraftService;
1076
1649
  this.updateService = updateService;
1077
1650
  this.configurationService = configurationService;
1651
+ this.updatedSubj$ = new Subject();
1652
+ this.updated$ = this.updatedSubj$.asObservable();
1078
1653
  }
1079
1654
  calculate$(quoteDraft) {
1080
1655
  return this.proceduresApiService.apply$(quoteDraft).pipe(tap$1(result => {
@@ -1084,7 +1659,7 @@ class FlowConfigurationService {
1084
1659
  .slice()
1085
1660
  .sort((a, b) => initialStateIds.indexOf(a.integrationId) - initialStateIds.indexOf(b.integrationId));
1086
1661
  this.quoteDraftService.updateQuoteDraft(result);
1087
- }), map$2(noop));
1662
+ }), map$1(noop));
1088
1663
  }
1089
1664
  calculate(quoteDraft) {
1090
1665
  this.calculate$(quoteDraft).subscribe();
@@ -1094,11 +1669,11 @@ class FlowConfigurationService {
1094
1669
  if (!quoteDraft) {
1095
1670
  return of(null);
1096
1671
  }
1097
- return of([]).pipe(map$2(() => {
1672
+ return of([]).pipe(map$1(() => {
1098
1673
  const updatedState = cloneDeep(quoteDraft.currentState);
1099
1674
  this.updateService.update(updatedState, updates, quoteDraft.charges);
1100
1675
  return updatedState;
1101
- }), switchMap$1(updatedState => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$2(() => this.quoteDraftService.quoteDraft), this.handleErrorAndBounceBack());
1676
+ }), switchMap(updatedState => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$1(() => this.quoteDraftService.quoteDraft), tap$1(() => this.updatedSubj$.next()), this.handleErrorAndBounceBack());
1102
1677
  }
1103
1678
  update(updates) {
1104
1679
  this.update$(updates).subscribe();
@@ -1106,7 +1681,7 @@ class FlowConfigurationService {
1106
1681
  revert$(lineItemId) {
1107
1682
  const quoteDraft = this.quoteDraftService.quoteDraft;
1108
1683
  const initialCurrentState = this.quoteDraftService.getInitialCurrentState();
1109
- const currentState = this.quoteDraftService.activeCurrentState;
1684
+ const currentState = this.quoteDraftService.currentState;
1110
1685
  const currentLineItemIndex = currentState.findIndex(({ id }) => id === lineItemId);
1111
1686
  const currentLineItem = currentState[currentLineItemIndex];
1112
1687
  const initialLineItem = initialCurrentState.find(({ integrationId }) => integrationId === currentLineItem?.integrationId);
@@ -1117,7 +1692,7 @@ class FlowConfigurationService {
1117
1692
  updatedState.splice(currentLineItemIndex, 1, initialLineItem);
1118
1693
  return of([]).pipe(tap$1(() => {
1119
1694
  this.quoteDraftService.setCurrentLineItemState(updatedState);
1120
- }), switchMap$1(() => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$2(() => this.quoteDraftService.quoteDraft), this.handleErrorAndBounceBack());
1695
+ }), switchMap(() => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$1(() => this.quoteDraftService.quoteDraft), tap$1(() => this.updatedSubj$.next()), this.handleErrorAndBounceBack());
1121
1696
  }
1122
1697
  revert(lineItemId) {
1123
1698
  this.revert$(lineItemId).subscribe();
@@ -1128,7 +1703,7 @@ class FlowConfigurationService {
1128
1703
  if (!quoteDraft) {
1129
1704
  return of(null);
1130
1705
  }
1131
- return of([]).pipe(map$2(() => ids.reduce((result, id) => this.updateService.delete(result, id), currentState)), switchMap$1(updatedState => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$2(() => this.quoteDraftService.quoteDraft), this.handleErrorAndBounceBack());
1706
+ return of([]).pipe(map$1(() => ids.reduce((result, id) => this.updateService.delete(result, id), currentState)), switchMap(updatedState => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$1(() => this.quoteDraftService.quoteDraft), tap$1(() => this.updatedSubj$.next()), this.handleErrorAndBounceBack());
1132
1707
  }
1133
1708
  delete(ids) {
1134
1709
  this.delete$(ids).subscribe();
@@ -1139,34 +1714,34 @@ class FlowConfigurationService {
1139
1714
  return of(null);
1140
1715
  }
1141
1716
  const updatedState = [...quoteDraft.currentState, term];
1142
- return of([]).pipe(switchMap$1(() => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$2(() => this.quoteDraftService.quoteDraft), this.handleErrorAndBounceBack());
1717
+ return of([]).pipe(switchMap(() => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$1(() => this.quoteDraftService.quoteDraft), tap$1(() => this.updatedSubj$.next()), this.handleErrorAndBounceBack());
1143
1718
  }
1144
1719
  addToCart$(props) {
1145
1720
  const quoteDraft = this.quoteDraftService.quoteDraft;
1146
1721
  if (!quoteDraft) {
1147
1722
  return of(null);
1148
1723
  }
1149
- return this.configurationService.configureExternal$(props).pipe(map$2(lineItem => {
1724
+ return this.configurationService.configureExternal$(props).pipe(map$1(lineItem => {
1150
1725
  const model = this.configurationService.getRuntimeModel();
1151
1726
  const split = model?.types.find(type => type.name === lineItem.type)?.split ?? false;
1152
1727
  const lineItems = multiplyLineItems(lineItem, props.qty ?? 1, split);
1153
1728
  return [...quoteDraft.currentState, ...lineItems];
1154
- }), switchMap$1(updatedState => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$2(() => this.quoteDraftService.quoteDraft), this.handleErrorAndBounceBack());
1729
+ }), switchMap(updatedState => this.calculate$({ ...quoteDraft, currentState: updatedState })), map$1(() => this.quoteDraftService.quoteDraft), tap$1(() => this.updatedSubj$.next()), this.handleErrorAndBounceBack());
1155
1730
  }
1156
1731
  get() {
1157
- return this.quoteDraftService.quoteDraft$.pipe(map$2(() => this.quoteDraftService.activeCurrentState), shareReplay$1());
1732
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(() => this.quoteDraftService.currentState), shareReplay$1());
1158
1733
  }
1159
1734
  getSnapshot() {
1160
1735
  return this.quoteDraftService?.currentState.slice() ?? [];
1161
1736
  }
1162
1737
  get charges$() {
1163
- return this.quoteDraftService.quoteDraft$.pipe(map$2(({ charges }) => charges));
1738
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(({ charges }) => charges));
1164
1739
  }
1165
1740
  get pricePlans$() {
1166
- return this.quoteDraftService.quoteDraft$.pipe(map$2(({ pricePlans }) => pricePlans));
1741
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(({ pricePlans }) => pricePlans));
1167
1742
  }
1168
1743
  get activeMetrics$() {
1169
- return this.quoteDraftService.quoteDraft$.pipe(map$2(({ activeMetrics }) => activeMetrics));
1744
+ return this.quoteDraftService.quoteDraft$.pipe(map$1(({ activeMetrics }) => activeMetrics));
1170
1745
  }
1171
1746
  get chargesSnapshot() {
1172
1747
  return this.quoteDraftService.quoteDraft?.charges ?? {};
@@ -1185,12 +1760,13 @@ class FlowConfigurationService {
1185
1760
  }
1186
1761
  handleErrorAndBounceBack() {
1187
1762
  return (source$) => {
1188
- return source$.pipe(catchError$1(error => {
1763
+ return source$.pipe(catchError(error => {
1189
1764
  console.error(error);
1190
1765
  // bounce back if configuration call has failed
1191
1766
  const quoteDraft = this.quoteDraftService.quoteDraft;
1192
1767
  if (quoteDraft) {
1193
1768
  this.quoteDraftService.updateQuoteDraft(quoteDraft);
1769
+ this.updatedSubj$.next();
1194
1770
  }
1195
1771
  return throwError(() => error);
1196
1772
  }));
@@ -1203,121 +1779,92 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImpor
1203
1779
  type: Injectable
1204
1780
  }], ctorParameters: function () { return [{ type: i1.ProceduresApiService }, { type: ContextService }, { type: QuoteDraftService }, { type: FlowUpdateService }, { type: ConfigurationService }]; } });
1205
1781
 
1206
- function calculateMetricByMethod(lineItems, metric, method) {
1207
- const items = getLineItemsByMethod(lineItems, method);
1208
- return items.reduce((acc, li) => {
1209
- let value = li.reduce((accProduct, item) => accProduct + ((item.totalMetrics && item.totalMetrics[metric]) || 0), 0);
1210
- if (method === 'avg' && li.length > 0) {
1211
- value /= li.length;
1212
- }
1213
- return acc + value;
1214
- }, 0);
1782
+ class FlowConfigurationModule {
1215
1783
  }
1216
- function getLineItemsByMethod(lineItems, method) {
1217
- switch (method) {
1218
- case 'first': {
1219
- return lineItems.filter(li => !li.rampInstanceId).map(item => [item]);
1220
- }
1221
- case 'last': {
1222
- const rootTermItems = lineItems.filter(li => !li.rampInstanceId);
1223
- const products = rootTermItems.map(lineItem => [
1224
- lineItem,
1225
- ...lineItems.filter(li => li.rampInstanceId === lineItem.id),
1226
- ]);
1227
- return products
1228
- .map(items => [...items].sort((a, b) => getDateValue(a.endDate || '') - getDateValue(b.endDate || '')).pop())
1229
- .filter((li) => Boolean(li))
1230
- .map(item => [item]);
1231
- }
1232
- case 'avg': {
1233
- const rootTermItems = lineItems.filter(li => !li.rampInstanceId);
1234
- return rootTermItems.map(lineItem => [lineItem, ...lineItems.filter(li => li.rampInstanceId === lineItem.id)]);
1235
- }
1236
- case 'sum': {
1237
- return lineItems.map(item => [item]);
1784
+ FlowConfigurationModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
1785
+ FlowConfigurationModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, imports: [ApiModule] });
1786
+ FlowConfigurationModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, providers: [FlowConfigurationService, FlowUpdateService], imports: [ApiModule] });
1787
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, decorators: [{
1788
+ type: NgModule,
1789
+ args: [{
1790
+ imports: [ApiModule],
1791
+ providers: [FlowConfigurationService, FlowUpdateService],
1792
+ }]
1793
+ }] });
1794
+
1795
+ class FlowStateConfigurationService {
1796
+ constructor(flowInfoService, flowConfigurationService, flowStateApiService, flowStateService) {
1797
+ this.flowInfoService = flowInfoService;
1798
+ this.flowConfigurationService = flowConfigurationService;
1799
+ this.flowStateApiService = flowStateApiService;
1800
+ this.flowStateService = flowStateService;
1801
+ this.configurationStateId$ = new BehaviorSubject(null);
1802
+ }
1803
+ get configurationStateId() {
1804
+ return this.configurationStateId$.value;
1805
+ }
1806
+ addToCart$(props) {
1807
+ let request$;
1808
+ const stateful = this.flowInfoService.flow?.properties.stateful;
1809
+ if (stateful) {
1810
+ const stateId = this.flowStateService.stateId;
1811
+ if (!stateId) {
1812
+ request$ = of();
1813
+ }
1814
+ else {
1815
+ const lineItem = generateConfigurationLineItem(props, props.qty);
1816
+ request$ = this.flowStateApiService.newConfiguration(stateId, { lineItem }).pipe(tap$1(r => this.configurationStateId$.next(r.stateId)), switchMap(() => {
1817
+ if (!this.configurationStateId) {
1818
+ return of();
1819
+ }
1820
+ return this.flowStateApiService.saveConfiguration(stateId, this.configurationStateId).pipe(tap$1(() => this.configurationStateId$.next(null)), map$1(noop));
1821
+ }));
1822
+ }
1238
1823
  }
1239
- default: {
1240
- return lineItems.map(item => [item]);
1824
+ else {
1825
+ request$ = this.flowConfigurationService.addToCart$(props).pipe(map$1(noop));
1241
1826
  }
1827
+ return request$.pipe(switchMap(() => this.flowStateService.executeRequest$({}, true)), map$1(noop));
1242
1828
  }
1243
1829
  }
1244
- function getDateValue(date) {
1245
- return date ? new Date(date).getTime() : 0;
1246
- }
1830
+ FlowStateConfigurationService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowStateConfigurationService, deps: [{ token: FlowInfoService }, { token: FlowConfigurationService }, { token: i1.FlowStateApiService }, { token: FlowStateService }], target: i0.ɵɵFactoryTarget.Injectable });
1831
+ FlowStateConfigurationService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowStateConfigurationService });
1832
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowStateConfigurationService, decorators: [{
1833
+ type: Injectable
1834
+ }], ctorParameters: function () { return [{ type: FlowInfoService }, { type: FlowConfigurationService }, { type: i1.FlowStateApiService }, { type: FlowStateService }]; } });
1247
1835
 
1248
- class MetricsCalculationService {
1249
- get onMetricsUpdate$() {
1250
- return this.metricsUpdated$.asObservable();
1836
+ class IntegrationState {
1837
+ constructor() {
1838
+ this.stateSubj$ = new BehaviorSubject({});
1839
+ this.action$ = new Subject();
1251
1840
  }
1252
- constructor(quoteDraftService, flowConfiguration, settingsService) {
1253
- this.quoteDraftService = quoteDraftService;
1254
- this.flowConfiguration = flowConfiguration;
1255
- this.settingsService = settingsService;
1256
- this.metricsUpdated$ = new Subject();
1257
- this.quoteMetricsSettings = {};
1258
- this.metricsCalculationMethodMap = {};
1259
- this.metricsData = {};
1260
- this.activeMetricRules = [];
1261
- this.activeMetricRules = this.flowConfiguration.activeMetricsSnapshot.filter(metricRule => metricRule.metrics.some(metric => !!metric.totalName));
1262
- combineLatest([
1263
- this.quoteDraftService.currentState$,
1264
- this.settingsService.fetchSetting('QUOTE_LEVEL_METRIC_CALCULATION_METHOD').pipe(take$1(1)),
1265
- ]).subscribe(([lineItems, setting]) => {
1266
- let settingsData = {};
1267
- try {
1268
- settingsData = JSON.parse(setting?.value || '{}');
1269
- }
1270
- catch (error) {
1271
- settingsData = {};
1272
- }
1273
- this.quoteMetricsSettings = settingsData;
1274
- this.updateMetrics(lineItems);
1275
- });
1841
+ get state$() {
1842
+ return this.stateSubj$.asObservable();
1276
1843
  }
1277
- getMetricValue(metric) {
1278
- return this.metricsData[metric] || 0;
1844
+ get state() {
1845
+ return this.stateSubj$.getValue();
1279
1846
  }
1280
- updateMetrics(lineItems) {
1281
- const metricKeys = this.collectMetricKeys(lineItems).filter(key => !key.includes('Effective_'));
1282
- this.metricsCalculationMethodMap = this.buildMetricsCalculationMethods(metricKeys, this.metricsCalculationMethodMap);
1283
- this.metricsData = metricKeys.reduce((acc, key) => ({ ...acc, [key]: this.calculateMetric(lineItems, key) }), {});
1284
- this.metricsUpdated$.next();
1847
+ patchState(update) {
1848
+ this.stateSubj$.next({ ...this.stateSubj$.getValue(), ...update });
1285
1849
  }
1286
- calculateMetric(lineItems, metric) {
1287
- return calculateMetricByMethod(lineItems, metric, this.metricsCalculationMethodMap[metric] || 'sum');
1850
+ dispatch(action) {
1851
+ this.action$.next(action);
1288
1852
  }
1289
- buildMetricsCalculationMethods(metricKeys, initial) {
1290
- return metricKeys.reduce((acc, name) => {
1291
- if (acc[name]) {
1292
- return acc;
1293
- }
1294
- acc = { ...acc, [name]: 'sum' };
1295
- const metricRule = this.getMetricRuleByTotalMetricName(name);
1296
- const settingKey = metricRule?.metrics?.find(metric => metric.totalName === name)?.name || name;
1297
- if (this.quoteMetricsSettings[settingKey]) {
1298
- acc = { ...acc, [name]: this.quoteMetricsSettings[settingKey] };
1299
- }
1300
- return acc;
1301
- }, initial);
1853
+ listen$(actionType) {
1854
+ return this.action$.pipe(filter$1(action => action.type === actionType), map$1(action => action.payload));
1302
1855
  }
1303
- collectMetricKeys(lineItems) {
1304
- const keys = [];
1305
- lineItems.forEach(lineItem => {
1306
- keys.push(...Object.keys(lineItem.totalMetrics || {}));
1307
- keys.push(...this.collectMetricKeys(lineItem.lineItems));
1308
- });
1309
- return uniq(keys);
1856
+ listenAll$() {
1857
+ return this.action$.asObservable();
1310
1858
  }
1311
- getMetricRuleByTotalMetricName(name) {
1312
- return this.activeMetricRules.find(metricRule => metricRule.metrics.find(metric => metric.totalName === name));
1859
+ clear() {
1860
+ this.stateSubj$.next({});
1313
1861
  }
1314
1862
  }
1315
- MetricsCalculationService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: MetricsCalculationService, deps: [{ token: QuoteDraftService }, { token: FlowConfigurationService }, { token: i1.ConfigurationSettingsApiService }], target: i0.ɵɵFactoryTarget.Injectable });
1316
- MetricsCalculationService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: MetricsCalculationService, providedIn: 'root' });
1317
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: MetricsCalculationService, decorators: [{
1318
- type: Injectable,
1319
- args: [{ providedIn: 'root' }]
1320
- }], ctorParameters: function () { return [{ type: QuoteDraftService }, { type: FlowConfigurationService }, { type: i1.ConfigurationSettingsApiService }]; } });
1863
+ IntegrationState.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: IntegrationState, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
1864
+ IntegrationState.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: IntegrationState });
1865
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: IntegrationState, decorators: [{
1866
+ type: Injectable
1867
+ }] });
1321
1868
 
1322
1869
  class ProductImagesService {
1323
1870
  constructor(productApiService) {
@@ -1329,20 +1876,19 @@ class ProductImagesService {
1329
1876
  this.imagesMap$.next({ ...this.imagesMap$.value, [productId]: '' });
1330
1877
  this.fetchProductImage(productId);
1331
1878
  }
1332
- return this.imagesMap$.pipe(map$2(imagesMap => imagesMap[productId]), distinctUntilChanged());
1879
+ return this.imagesMap$.pipe(map$1(imagesMap => imagesMap[productId] ?? null), distinctUntilChanged());
1333
1880
  }
1334
1881
  fetchProductImage(productId) {
1335
1882
  this.productApiService
1336
1883
  .fetchImage$(productId)
1337
- .pipe(map$2(file => URL.createObjectURL(file)), catchError$1(() => of('')), tap$1(url => this.imagesMap$.next({ ...this.imagesMap$.value, [productId]: url })))
1884
+ .pipe(map$1(file => URL.createObjectURL(file)), catchError(() => of('')), tap$1(url => this.imagesMap$.next({ ...this.imagesMap$.value, [productId]: url })))
1338
1885
  .subscribe();
1339
1886
  }
1340
1887
  }
1341
1888
  ProductImagesService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ProductImagesService, deps: [{ token: i1.ProductApiService }], target: i0.ɵɵFactoryTarget.Injectable });
1342
- ProductImagesService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ProductImagesService, providedIn: 'root' });
1889
+ ProductImagesService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ProductImagesService });
1343
1890
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ProductImagesService, decorators: [{
1344
- type: Injectable,
1345
- args: [{ providedIn: 'root' }]
1891
+ type: Injectable
1346
1892
  }], ctorParameters: function () { return [{ type: i1.ProductApiService }]; } });
1347
1893
 
1348
1894
  class RuntimeContextService {
@@ -1481,61 +2027,218 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImpor
1481
2027
  type: Injectable
1482
2028
  }], ctorParameters: function () { return [{ type: i1.ConfigurationApiService }, { type: ContextService }, { type: RuntimeContextService }]; } });
1483
2029
 
1484
- class ConfigurationState {
1485
- constructor(statefulConfigurationApiService, runtimeService, configurationService, toastService) {
1486
- this.statefulConfigurationApiService = statefulConfigurationApiService;
1487
- this.runtimeService = runtimeService;
2030
+ class ConfigurationStateService {
2031
+ constructor(configurationRuntimeService, configurationService, quoteDraftService, toastService, flowStateService, flowInfoService, flowConfigurationService, flowStateApiService, quoteApiService) {
2032
+ this.configurationRuntimeService = configurationRuntimeService;
1488
2033
  this.configurationService = configurationService;
2034
+ this.quoteDraftService = quoteDraftService;
1489
2035
  this.toastService = toastService;
1490
- this.stateSubj$ = new BehaviorSubject({});
1491
- this.state$ = this.stateSubj$.asObservable();
2036
+ this.flowStateService = flowStateService;
2037
+ this.flowInfoService = flowInfoService;
2038
+ this.flowConfigurationService = flowConfigurationService;
2039
+ this.flowStateApiService = flowStateApiService;
2040
+ this.quoteApiService = quoteApiService;
2041
+ this.isInitialized$ = new BehaviorSubject(false);
2042
+ this.canceledConfiguration$ = new Subject();
2043
+ this.NOT_INITIALIZED = Symbol();
2044
+ this.EXECUTION_BUFFER_TIME = 100;
2045
+ this.executedFunctions = {};
1492
2046
  this.stateId = null;
2047
+ this.ownerId = '';
2048
+ this.subscriptions = {};
2049
+ this.configurationStore = {};
2050
+ this.statefulExecutionInProgress$ = new BehaviorSubject(false);
2051
+ this.statefulRequestStream$ = new Subject();
2052
+ this.statefulExecutionRequest$ = this.initBufferedRequest$();
1493
2053
  }
1494
2054
  init$() {
1495
- return this.configurationService.configure().pipe(switchMap$1(() => {
1496
- if (!this.isStatefulConfiguration) {
1497
- return of(undefined);
1498
- }
1499
- const { actions, selectors } = this.runtimeService.runtimeContext?.uiDefinitionContainer ?? {};
1500
- return this.statefulConfigurationApiService.init({
1501
- item: this.configurationService.generateRequest(),
1502
- actions: actions?.map(action => ({ name: action.apiName, script: action.script })),
1503
- selectors: selectors?.map(selector => ({ name: selector.apiName, script: selector.script })),
1504
- });
1505
- }), tap$1(stateId => (this.stateId = stateId || null)), map$2(() => undefined));
2055
+ let request$;
2056
+ if (this.flowStateService.stateId && this.isStatefulConfiguration) {
2057
+ request$ = this.initStateful$();
2058
+ }
2059
+ else {
2060
+ request$ = this.initStateless$();
2061
+ }
2062
+ return request$.pipe(finalize(() => {
2063
+ this.isInitialized$.next(true);
2064
+ this.canceledConfiguration$ = new Subject();
2065
+ }));
1506
2066
  }
1507
2067
  cleanup() {
1508
- this.stateId = null;
2068
+ Object.values(this.subscriptions).forEach(({ data$ }) => data$.complete());
2069
+ this.subscriptions = {};
2070
+ if (this.stateId) {
2071
+ this.cancelConfiguration();
2072
+ }
2073
+ this.configurationStore = {};
2074
+ this.executedFunctions = {};
1509
2075
  this.configurationService.reset();
1510
- this.stateSubj$.next({});
1511
2076
  }
1512
- execute$(req) {
2077
+ execute$(req, forceSubscriptions) {
2078
+ const fullRequest = cloneDeep(req);
2079
+ if (fullRequest.actions?.length || forceSubscriptions) {
2080
+ for (const subscription of Object.values(this.subscriptions)) {
2081
+ fullRequest.selectors = assign(fullRequest.selectors, subscription.request.selectors);
2082
+ }
2083
+ }
2084
+ let execution$;
1513
2085
  if (this.isStatefulConfiguration) {
1514
- return this.executeStateful$(req);
2086
+ execution$ = this.executeStateful$(fullRequest);
1515
2087
  }
1516
2088
  else {
1517
- return this.executeStateless$(req);
2089
+ execution$ = this.executeStateless$(fullRequest);
1518
2090
  }
2091
+ return execution$.pipe(tap$1(result => this.handleSelectorsResponse(result.selectors)));
2092
+ }
2093
+ handleSelectorsResponse(selectors) {
2094
+ Object.entries(selectors).forEach(([requestId, selectorResult]) => {
2095
+ if (!selectorResult.success) {
2096
+ this.toastService.add({ severity: ToastType.error, summary: selectorResult.errorMessage });
2097
+ }
2098
+ const subscription$ = this.subscriptions[requestId]?.data$;
2099
+ if (subscription$) {
2100
+ subscription$.next(selectorResult);
2101
+ }
2102
+ });
1519
2103
  }
1520
- dispatch$(actionName, inputData) {
1521
- return this.execute$({ actions: [{ name: actionName, inputData }] });
2104
+ dispatch$(actionName, inputData = {}) {
2105
+ return this.execute$({ actions: [{ apiName: actionName, inputData, ownerId: this.ownerId }] });
1522
2106
  }
1523
- select$(selectorName, inputData) {
2107
+ select$(selectorName, inputData = {}) {
1524
2108
  const requestId = UUID.UUID();
1525
2109
  return this.execute$({
1526
2110
  selectors: {
1527
2111
  [requestId]: {
1528
- name: selectorName,
2112
+ apiName: selectorName,
1529
2113
  inputData,
2114
+ ownerId: this.ownerId,
1530
2115
  },
1531
2116
  },
1532
- }).pipe(map$2(() => this.stateSubj$.value[requestId]), tap$1(() => this.stateSubj$.next(omit(this.stateSubj$.value, requestId))));
2117
+ }).pipe(map$1(response => response.selectors[requestId]));
2118
+ }
2119
+ subscribe$(selectorName, inputData = {}, options) {
2120
+ const requestId = UUID.UUID();
2121
+ let subscription = this.subscriptions[requestId];
2122
+ if (!subscription) {
2123
+ const request = {
2124
+ selectors: {
2125
+ [requestId]: {
2126
+ apiName: selectorName,
2127
+ inputData,
2128
+ ownerId: this.ownerId,
2129
+ },
2130
+ },
2131
+ };
2132
+ subscription = {
2133
+ request,
2134
+ data$: new BehaviorSubject(this.NOT_INITIALIZED),
2135
+ };
2136
+ this.subscriptions[requestId] = subscription;
2137
+ if (!options?.cold) {
2138
+ this.execute$(request).subscribe();
2139
+ }
2140
+ }
2141
+ return subscription.data$.pipe(filter$1(data => data != this.NOT_INITIALIZED), map$1(data => data), distinctUntilChanged(), finalize(() => {
2142
+ if (!this.subscriptions[requestId]?.data$.observed) {
2143
+ delete this.subscriptions[requestId];
2144
+ }
2145
+ }), takeUntil(this.canceledConfiguration$));
2146
+ }
2147
+ saveConfiguration(quoteId, flow) {
2148
+ if (this.isStatefulConfiguration) {
2149
+ return this.flowStateApiService
2150
+ .saveConfiguration(this.flowStateService.stateId ?? '', this.stateId ?? '')
2151
+ .pipe(switchMap(r => this.flowStateService.executeRequest$({}, true).pipe(map$1(() => r))));
2152
+ }
2153
+ else {
2154
+ if (!flow) {
2155
+ if (!quoteId) {
2156
+ return of({ quoteId: '' });
2157
+ }
2158
+ const rootLineItem = this.configurationService.getSnapshot();
2159
+ const asset = this.configurationService.getAsset();
2160
+ const currentState = rootLineItem ? [rootLineItem] : [];
2161
+ const initialState = asset ? [asset] : [];
2162
+ return this.quoteApiService
2163
+ .getQuoteState(quoteId)
2164
+ .pipe(switchMap(quoteDraft => this.quoteApiService.upsertQuote({ ...quoteDraft, currentState, initialState })));
2165
+ }
2166
+ else {
2167
+ const quoteDraft = this.quoteDraftService.quoteDraft;
2168
+ const lineItem = this.configurationService.getSnapshot();
2169
+ if (!quoteDraft || !lineItem) {
2170
+ return of({ quoteId: '' });
2171
+ }
2172
+ const isNewLineItem = quoteDraft.currentState.every(li => li.id !== lineItem.id);
2173
+ let currentState;
2174
+ if (isNewLineItem) {
2175
+ currentState = [...quoteDraft.currentState, lineItem];
2176
+ }
2177
+ else {
2178
+ currentState = quoteDraft.currentState.map(li => (li.id === lineItem.id ? lineItem : li));
2179
+ }
2180
+ const asset = this.configurationService.getAsset();
2181
+ const initialState = [...(this.quoteDraftService.quoteDraft?.initialState ?? [])];
2182
+ if (asset) {
2183
+ if (!initialState.some(li => li.id === asset.id)) {
2184
+ initialState.push(asset);
2185
+ }
2186
+ }
2187
+ return this.flowConfigurationService
2188
+ .calculate$({ ...quoteDraft, currentState, initialState })
2189
+ .pipe(map$1(() => ({ quoteId: '' })));
2190
+ }
2191
+ }
2192
+ }
2193
+ cancelConfiguration() {
2194
+ if (!this.isInitialized$.value) {
2195
+ return of(undefined);
2196
+ }
2197
+ this.canceledConfiguration$.next();
2198
+ this.canceledConfiguration$.complete();
2199
+ this.subscriptions = {};
2200
+ this.isInitialized$.next(false);
2201
+ if (!this.isInitialized$.value || !this.isStatefulConfiguration) {
2202
+ return of(undefined);
2203
+ }
2204
+ return this.flowStateApiService.cancelConfiguration(this.flowStateService.stateId ?? '', this.stateId ?? '');
1533
2205
  }
1534
2206
  get isStatefulConfiguration() {
1535
- return this.runtimeService.uiDefinitionProperties.statefulConfigurationEnabled ?? false;
2207
+ return this.flowInfoService.flow?.properties.stateful ?? false;
2208
+ }
2209
+ initStateful$() {
2210
+ this.ownerId = this.configurationRuntimeService.runtimeContext?.uiDefinitionContainer?.id ?? '';
2211
+ const lineItemId = this.configurationRuntimeService.runtimeContext?.properties?.lineItemId;
2212
+ if (!this.flowStateService.stateId) {
2213
+ return of(undefined);
2214
+ }
2215
+ const container = this.configurationRuntimeService.runtimeContext?.uiDefinitionContainer;
2216
+ const lineItem = this.configurationService.generateLineItem();
2217
+ let request$;
2218
+ if (!lineItemId) {
2219
+ request$ = this.flowStateApiService.newConfiguration(this.flowStateService.stateId, {
2220
+ lineItem,
2221
+ actionsOverride: container?.actions?.map(processor => ({ ...processor, ownerId: this.ownerId })),
2222
+ selectorsOverride: container?.selectors?.map(processor => ({ ...processor, ownerId: this.ownerId })),
2223
+ });
2224
+ }
2225
+ else {
2226
+ request$ = this.flowStateApiService.startConfiguration(this.flowStateService.stateId, {
2227
+ lineItemId,
2228
+ actionsOverride: container?.actions?.map(processor => ({ ...processor, ownerId: this.ownerId })),
2229
+ selectorsOverride: container?.selectors?.map(processor => ({ ...processor, ownerId: this.ownerId })),
2230
+ });
2231
+ }
2232
+ return request$.pipe(map$1(r => {
2233
+ this.stateId = r.stateId;
2234
+ return undefined;
2235
+ }));
2236
+ }
2237
+ initStateless$() {
2238
+ return this.configurationService.configure().pipe(map$1(() => undefined));
1536
2239
  }
1537
2240
  executeStateless$(request) {
1538
- return of(undefined).pipe(switchMap$1(() => {
2241
+ return of(undefined).pipe(switchMap(() => {
1539
2242
  // Apply actions and execute configuration/price call
1540
2243
  // No need to run configuration if no actions in the request
1541
2244
  if (!request.actions?.length) {
@@ -1546,109 +2249,112 @@ class ConfigurationState {
1546
2249
  configurationRequest = this.executeActionScript(configurationRequest, action) ?? configurationRequest;
1547
2250
  });
1548
2251
  return this.configurationService.configureRequest$(configurationRequest);
1549
- }), tap$1(() => {
1550
- if (!request.selectors) {
1551
- return;
1552
- }
2252
+ }), map$1(() => {
1553
2253
  // Run selectors and apply them to the state
1554
- const finalConfigurationRequest = this.configurationService.generateRequest();
1555
- const selectorsResult = EntityUtil.entries(request.selectors).reduce((trunk, [key, selector]) => {
1556
- trunk[key] = this.executeSelectorScript(finalConfigurationRequest, selector);
1557
- return trunk;
1558
- }, {});
1559
- this.stateSubj$.next({
1560
- ...this.stateSubj$.value,
1561
- ...selectorsResult,
1562
- });
1563
- }), map$2(() => undefined));
2254
+ const configurationState = cloneDeep(this.configurationService.stateSnapshot);
2255
+ if (!configurationState) {
2256
+ return { stateId: '', selectors: {} };
2257
+ }
2258
+ const selectorsResult = EntityUtil.entries(request.selectors ?? {}).reduce((result, [key, selector]) => {
2259
+ try {
2260
+ result.selectors[key] = {
2261
+ success: true,
2262
+ result: this.executeSelectorScript(configurationState, selector),
2263
+ };
2264
+ }
2265
+ catch (e) {
2266
+ console.error(e);
2267
+ result.selectors[key] = {
2268
+ success: false,
2269
+ errorMessage: String(e),
2270
+ };
2271
+ }
2272
+ return result;
2273
+ }, { stateId: '', selectors: {} });
2274
+ return selectorsResult;
2275
+ }), catchError(error => {
2276
+ if (!this.configurationRuntimeService.uiDefinitionProperties.suppressToastMessages) {
2277
+ this.toastService.add({ severity: ToastType.error, summary: String(error) });
2278
+ }
2279
+ return throwError(() => error);
2280
+ }));
2281
+ }
2282
+ initBufferedRequest$() {
2283
+ return this.statefulRequestStream$.pipe(buffer(this.statefulRequestStream$.pipe(debounceTime(this.EXECUTION_BUFFER_TIME))), switchMap(requests => {
2284
+ if (!this.flowStateService.stateId || !this.stateId) {
2285
+ throw 'Stateful session is not initialized';
2286
+ }
2287
+ // merge buffered requests
2288
+ const request = {
2289
+ actions: requests.flatMap(({ actions }) => actions).filter(isDefined),
2290
+ selectors: requests
2291
+ .map(({ selectors }) => selectors)
2292
+ .filter(isDefined)
2293
+ .reduce((acc, selectorsMap) => Object.assign(acc, selectorsMap), {}),
2294
+ };
2295
+ this.statefulExecutionInProgress$.next(true);
2296
+ return this.flowStateApiService.executeConfiguration(this.flowStateService.stateId, this.stateId, request);
2297
+ }), tap$1(({ stateId }) => (this.stateId = stateId)), share(), tap$1(() => this.statefulExecutionInProgress$.next(false)), catchError(e => {
2298
+ this.statefulExecutionInProgress$.next(false);
2299
+ return throwError(() => e);
2300
+ }));
1564
2301
  }
1565
2302
  executeStateful$(request) {
1566
- if (!this.stateId) {
1567
- return of(undefined);
1568
- }
1569
- return this.statefulConfigurationApiService.execute(this.stateId, request).pipe(tap$1(response => {
1570
- this.stateId = response.stateId;
1571
- const updatedState = this.stateSubj$.value;
1572
- EntityUtil.entries(response.selectors).forEach(([key, value]) => {
1573
- if (!value.success) {
1574
- if (!this.runtimeService.uiDefinitionProperties.suppressToastMessages) {
1575
- this.toastService.add({ summary: value.errorMessage, severity: ToastType.error });
1576
- }
1577
- return;
1578
- }
1579
- updatedState[key] = value.result;
1580
- });
1581
- this.stateSubj$.next(updatedState);
1582
- }), map$2(() => undefined));
2303
+ return this.statefulExecutionInProgress$.pipe(filter$1(inProgress => !inProgress), take$1(1), switchMap(() =>
2304
+ // make sure stream switches to statefulExecutionRequest$ before pushing an execution request
2305
+ combineLatest([
2306
+ this.statefulExecutionRequest$,
2307
+ of(undefined).pipe(tap$1(() => this.statefulRequestStream$.next(request))),
2308
+ ])), map$1(([response]) => response), take$1(1));
1583
2309
  }
1584
2310
  executeActionScript(request, processor) {
1585
- const { actions } = this.runtimeService.runtimeContext?.uiDefinitionContainer ?? {};
1586
- const script = actions?.find(action => action.apiName === processor.name)?.script;
1587
- if (!script) {
1588
- return null;
2311
+ const { actions } = this.configurationRuntimeService.runtimeContext?.uiDefinitionContainer ?? {};
2312
+ const configurationProcessor = actions?.find(action => action.apiName === processor.apiName);
2313
+ if (!configurationProcessor?.script) {
2314
+ throw `ConfigurationProcessor ${processor.apiName} not found`;
1589
2315
  }
1590
- return this.executeProcessorScript(request, script, processor.inputData);
2316
+ return this.executeProcessorScript(request, configurationProcessor, processor.inputData);
1591
2317
  }
1592
2318
  executeSelectorScript(request, processor) {
1593
- const { selectors } = this.runtimeService.runtimeContext?.uiDefinitionContainer ?? {};
1594
- const script = selectors?.find(selector => selector.apiName === processor.name)?.script;
1595
- if (!script) {
1596
- return null;
1597
- }
1598
- return this.executeProcessorScript(request, script, processor.inputData);
1599
- }
1600
- executeProcessorScript(request, script, inputData) {
1601
- return new Function(`${script}\nreturn transform;`)()({
2319
+ const { selectors } = this.configurationRuntimeService.runtimeContext?.uiDefinitionContainer ?? {};
2320
+ const configurationProcessor = selectors?.find(selector => selector.apiName === processor.apiName);
2321
+ if (!configurationProcessor?.script) {
2322
+ throw `ConfigurationProcessor ${processor.apiName} not found`;
2323
+ }
2324
+ return this.executeProcessorScript(request, configurationProcessor, processor.inputData);
2325
+ }
2326
+ executeProcessorScript(request, configurationProcessor, inputData) {
2327
+ let functionToExecute = this.executedFunctions[configurationProcessor.apiName];
2328
+ if (!functionToExecute) {
2329
+ const script = `${configurationProcessor.script}\nreturn transform;`;
2330
+ const sourceMap = `\n//# sourceURL=${configurationProcessor.apiName}.js`;
2331
+ functionToExecute = new Function(script + sourceMap)();
2332
+ this.executedFunctions[configurationProcessor.apiName] = functionToExecute;
2333
+ }
2334
+ return functionToExecute({
1602
2335
  request,
1603
- inputData: inputData,
2336
+ inputData,
2337
+ flowStore: this.flowStateService.getFlowStore(),
2338
+ configurationStore: this.configurationStore,
1604
2339
  });
1605
2340
  }
1606
2341
  }
1607
- ConfigurationState.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationState, deps: [{ token: i1.StatefulConfigurationApiService }, { token: ConfigurationRuntimeService }, { token: ConfigurationService }, { token: i4.ToastService }], target: i0.ɵɵFactoryTarget.Injectable });
1608
- ConfigurationState.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationState });
1609
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationState, decorators: [{
2342
+ ConfigurationStateService.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationStateService, deps: [{ token: ConfigurationRuntimeService }, { token: ConfigurationService }, { token: QuoteDraftService }, { token: i6.ToastService }, { token: FlowStateService }, { token: FlowInfoService }, { token: FlowConfigurationService }, { token: i1.FlowStateApiService }, { token: i1.QuoteApiService }], target: i0.ɵɵFactoryTarget.Injectable });
2343
+ ConfigurationStateService.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationStateService });
2344
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationStateService, decorators: [{
1610
2345
  type: Injectable
1611
- }], ctorParameters: function () { return [{ type: i1.StatefulConfigurationApiService }, { type: ConfigurationRuntimeService }, { type: ConfigurationService }, { type: i4.ToastService }]; } });
1612
-
1613
- class FlowConfigurationModule {
1614
- }
1615
- FlowConfigurationModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
1616
- FlowConfigurationModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule });
1617
- FlowConfigurationModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, providers: [FlowConfigurationService, FlowUpdateService, PriceApiService] });
1618
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: FlowConfigurationModule, decorators: [{
1619
- type: NgModule,
1620
- args: [{
1621
- imports: [],
1622
- providers: [FlowConfigurationService, FlowUpdateService, PriceApiService],
1623
- }]
1624
- }] });
2346
+ }], ctorParameters: function () { return [{ type: ConfigurationRuntimeService }, { type: ConfigurationService }, { type: QuoteDraftService }, { type: i6.ToastService }, { type: FlowStateService }, { type: FlowInfoService }, { type: FlowConfigurationService }, { type: i1.FlowStateApiService }, { type: i1.QuoteApiService }]; } });
1625
2347
 
1626
2348
  class ConfigurationModule {
1627
2349
  }
1628
2350
  ConfigurationModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
1629
- ConfigurationModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationModule, imports: [ConfirmationDialogModule] });
1630
- ConfigurationModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationModule, providers: [
1631
- ContextApiService,
1632
- ProductModelApiService,
1633
- ConfigurationApiService,
1634
- ConfigurationRuntimeService,
1635
- RuntimeContextService,
1636
- ConfigurationService,
1637
- ConfigurationState,
1638
- ], imports: [ConfirmationDialogModule] });
2351
+ ConfigurationModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationModule, imports: [ConfirmationDialogModule, ApiModule] });
2352
+ ConfigurationModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationModule, providers: [ConfigurationRuntimeService, RuntimeContextService, ConfigurationService, ConfigurationStateService], imports: [ConfirmationDialogModule, ApiModule] });
1639
2353
  i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: ConfigurationModule, decorators: [{
1640
2354
  type: NgModule,
1641
2355
  args: [{
1642
- imports: [ConfirmationDialogModule],
1643
- providers: [
1644
- ContextApiService,
1645
- ProductModelApiService,
1646
- ConfigurationApiService,
1647
- ConfigurationRuntimeService,
1648
- RuntimeContextService,
1649
- ConfigurationService,
1650
- ConfigurationState,
1651
- ],
2356
+ imports: [ConfirmationDialogModule, ApiModule],
2357
+ providers: [ConfigurationRuntimeService, RuntimeContextService, ConfigurationService, ConfigurationStateService],
1652
2358
  }]
1653
2359
  }] });
1654
2360
 
@@ -1665,6 +2371,14 @@ class SdkCoreModule {
1665
2371
  SdkCoreModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: SdkCoreModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
1666
2372
  SdkCoreModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "14.0.0", version: "15.2.9", ngImport: i0, type: SdkCoreModule, imports: [ConfigurationModule, FlowConfigurationModule] });
1667
2373
  SdkCoreModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "15.2.9", ngImport: i0, type: SdkCoreModule, providers: [
2374
+ ContextService,
2375
+ FlowInfoService,
2376
+ QuoteDraftService,
2377
+ ProductImagesService,
2378
+ IntegrationState,
2379
+ FlowStateService,
2380
+ FlowStateConfigurationService,
2381
+ RuntimeSettingsService,
1668
2382
  {
1669
2383
  provide: FORMATTING_SETTINGS_TOKEN,
1670
2384
  useExisting: RuntimeSettingsService,
@@ -1675,6 +2389,14 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImpor
1675
2389
  args: [{
1676
2390
  imports: [ConfigurationModule, FlowConfigurationModule],
1677
2391
  providers: [
2392
+ ContextService,
2393
+ FlowInfoService,
2394
+ QuoteDraftService,
2395
+ ProductImagesService,
2396
+ IntegrationState,
2397
+ FlowStateService,
2398
+ FlowStateConfigurationService,
2399
+ RuntimeSettingsService,
1678
2400
  {
1679
2401
  provide: FORMATTING_SETTINGS_TOKEN,
1680
2402
  useExisting: RuntimeSettingsService,
@@ -1849,5 +2571,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "15.2.9", ngImpor
1849
2571
  * Generated bundle index. Do not edit.
1850
2572
  */
1851
2573
 
1852
- export { ActionCodePipe, CalendarDirective, ConfigurationRuntimeService, ConfigurationService, ConfigurationState, ContextService, DEFAULT_FORMATTING_SETTINGS, DatePipe, FORMATTING_SETTINGS_TOKEN, FlowConfigurationModule, FlowConfigurationService, FlowUpdateService, LineItemWorker, MetricsCalculationService, NumberPipe, PricePipe, ProductImagesService, QuoteDraftService, RuntimeMode, RuntimeOperation, RuntimeSettingsService, RuntimeStep, SdkCoreModule, SdkDirectivesModule, SdkPipesModule, UI_DEFINITION_VERSION, calculateCardinalityVariables, extractMetadata, filterOutTechnicalAttributes, findLineItem, findLineItemWithComparator, generateLineItem, generateModifiedAssetsMap, getAttributeValue, getAttributes, getDefaultLineItem, getGuidedSellingConfigurationRequest, getOriginParent, getRecommendedPrices, insertLineItem, isLineItemModified, isTechnicalAttribute, lineItem_utils as lineItemUtils, mapAttributes, multiplyLineItems, patchAttributes, recalculateCardinalityVariables, removeLineItem, replaceLineItem, upsertAttributes };
2574
+ export { ActionCodePipe, CalendarDirective, ConfigurationRuntimeService, ConfigurationService, ConfigurationStateService, ContextService, DEFAULT_FORMATTING_SETTINGS, DatePipe, FLOW_CUSTOMIZATION, FORMATTING_SETTINGS_TOKEN, FlowConfigurationModule, FlowConfigurationService, FlowInfoService, FlowStateConfigurationService, FlowStateService, FlowUpdateService, IntegrationState, LineItemWorker, NumberPipe, PricePipe, ProductImagesService, QuoteDraftService, RuntimeMode, RuntimeOperation, RuntimeSettingsService, RuntimeStep, SdkCoreModule, SdkDirectivesModule, SdkPipesModule, UI_DEFINITION_VERSION, assetPredicateFn, extractMetadata, filterOutTechnicalAttributes, findLineItem, findLineItemWithComparator, generateConfigurationLineItem, generateLineItem, getAttributeValue, getAttributes, getDefaultLineItem, getGuidedSellingConfigurationRequest, getOriginParent, getRecommendedPrices, insertLineItem, isTechnicalAttribute, lineItem_utils as lineItemUtils, mapAttributes, multiplyLineItems, patchAttributes, recalculateCardinalityVariables, removeLineItem, replaceLineItem, upsertAttributes };
1853
2575
  //# sourceMappingURL=veloceapps-sdk-core.mjs.map