@ukiahinsure/a2ui-react-adapter 0.1.7 → 0.1.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -29,6 +29,7 @@ var A2UIClientAdapter = class {
29
29
  #surfaceOrder = [];
30
30
  #structureBySurface = /* @__PURE__ */ new Map();
31
31
  #persistedListRowsByPath = /* @__PURE__ */ new Map();
32
+ #deletedListItemIdsByPath = /* @__PURE__ */ new Map();
32
33
  #version = 0;
33
34
  #lastSeq = 0;
34
35
  #disposed = false;
@@ -157,6 +158,7 @@ var A2UIClientAdapter = class {
157
158
  this.#surfaceOrder = [];
158
159
  this.#structureBySurface.clear();
159
160
  this.#persistedListRowsByPath.clear();
161
+ this.#deletedListItemIdsByPath.clear();
160
162
  previous.model.dispose();
161
163
  this.#notify();
162
164
  }
@@ -213,12 +215,17 @@ var A2UIClientAdapter = class {
213
215
  const rawMessages = envelope.kind === "snapshot" ? validated.data : mergePersistedListRowsIntoMessages(
214
216
  validated.data,
215
217
  envelope.surfaceId,
216
- this.#persistedListRowsByPath
218
+ this.#persistedListRowsByPath,
219
+ this.#deletedListItemIdsByPath
217
220
  );
218
- const actionCompleteMessages = ensureOptionalCoverageSkipActionMessages(
221
+ const listAddFreeMessages = removeListAddActionMessages(
219
222
  rawMessages,
220
223
  envelope.surfaceId
221
224
  );
225
+ const actionCompleteMessages = ensureOptionalCoverageSkipActionMessages(
226
+ listAddFreeMessages,
227
+ envelope.surfaceId
228
+ );
222
229
  const nextStructure = updateSurfaceStructures(
223
230
  actionCompleteMessages,
224
231
  envelope.kind === "snapshot" ? /* @__PURE__ */ new Map() : cloneSurfaceStructures(this.#structureBySurface)
@@ -264,9 +271,11 @@ var A2UIClientAdapter = class {
264
271
  this.#structureBySurface = nextStructure;
265
272
  if (envelope.kind === "snapshot") {
266
273
  this.#persistedListRowsByPath.clear();
274
+ this.#deletedListItemIdsByPath.clear();
267
275
  }
268
276
  rememberPersistedListRows(
269
277
  this.#persistedListRowsByPath,
278
+ this.#deletedListItemIdsByPath,
270
279
  candidate.model.getSurface(envelope.surfaceId)?.dataModel.get("/")
271
280
  );
272
281
  previous.model.dispose();
@@ -302,6 +311,9 @@ var A2UIClientAdapter = class {
302
311
  event.context
303
312
  );
304
313
  }
314
+ if (event.actionName === "flow.list.delete") {
315
+ this.#removeDeletedListRow(event.surfaceId, event.context);
316
+ }
305
317
  this.#options.onAction?.(event);
306
318
  for (const listener of this.#actionListeners) {
307
319
  listener(event);
@@ -327,6 +339,27 @@ var A2UIClientAdapter = class {
327
339
  );
328
340
  this.#notify();
329
341
  }
342
+ #removeDeletedListRow(surfaceId, context) {
343
+ const listPath = context.listPath;
344
+ const itemId = context.itemId;
345
+ if (typeof listPath !== "string" || listPath.length === 0 || typeof itemId !== "string" || itemId.length === 0) {
346
+ return;
347
+ }
348
+ const cachedRows = this.#persistedListRowsByPath.get(listPath) ?? [];
349
+ const nextRows = removeListRowByItemId(cachedRows, itemId);
350
+ this.#persistedListRowsByPath.set(listPath, nextRows);
351
+ rememberDeletedListItemId(this.#deletedListItemIdsByPath, listPath, itemId);
352
+ const surface = this.#processor.model.getSurface(surfaceId);
353
+ if (surface === void 0) {
354
+ return;
355
+ }
356
+ surface.dataModel.set(`/${listPath}`, cloneJsonArray(nextRows));
357
+ surface.dataModel.set(
358
+ `/${listPath.replaceAll(".", "/")}`,
359
+ cloneJsonArray(nextRows)
360
+ );
361
+ this.#notify();
362
+ }
330
363
  #snapshotMessages() {
331
364
  const messages = [];
332
365
  for (const surface of this.#processor.model.surfacesMap.values()) {
@@ -458,7 +491,7 @@ function ensureOptionalCoverageSkipActionMessages(messages, surfaceId) {
458
491
  const nextParent = {
459
492
  ...parent,
460
493
  children: parent.children.flatMap(
461
- (child) => child === submit.id ? [buttonId, child] : [child]
494
+ (child) => child === submit.id ? [child, buttonId] : [child]
462
495
  )
463
496
  };
464
497
  const nextComponents = update.components.map(
@@ -494,6 +527,59 @@ function ensureOptionalCoverageSkipActionMessages(messages, surfaceId) {
494
527
  }
495
528
  return messages;
496
529
  }
530
+ function removeListAddActionMessages(messages, surfaceId) {
531
+ for (let index = 0; index < messages.length; index += 1) {
532
+ const message = messages[index];
533
+ if (!isRecord(message) || !isRecord(message.updateComponents)) {
534
+ continue;
535
+ }
536
+ const update = message.updateComponents;
537
+ if (update.surfaceId !== surfaceId || !Array.isArray(update.components)) {
538
+ continue;
539
+ }
540
+ const addIds = listAddComponentIds(update.components);
541
+ if (addIds.size === 0) {
542
+ continue;
543
+ }
544
+ const nextMessages = [...messages];
545
+ nextMessages[index] = {
546
+ ...message,
547
+ updateComponents: {
548
+ ...update,
549
+ components: update.components.filter(
550
+ (component) => !(isRecord(component) && isNonEmptyString(component.id) && addIds.has(component.id))
551
+ ).map(
552
+ (component) => removeComponentChildren(component, addIds)
553
+ )
554
+ }
555
+ };
556
+ return nextMessages;
557
+ }
558
+ return messages;
559
+ }
560
+ function listAddComponentIds(components) {
561
+ const ids = /* @__PURE__ */ new Set();
562
+ for (const component of components) {
563
+ if (!isRecord(component) || !isNonEmptyString(component.id) || !hasActionName(component, "flow.list.add")) {
564
+ continue;
565
+ }
566
+ ids.add(component.id);
567
+ const child = component.child;
568
+ if (typeof child === "string" && child.length > 0) {
569
+ ids.add(child);
570
+ }
571
+ }
572
+ return ids;
573
+ }
574
+ function removeComponentChildren(component, removedIds) {
575
+ if (!isRecord(component) || !Array.isArray(component.children)) {
576
+ return component;
577
+ }
578
+ const children = component.children.filter(
579
+ (child) => typeof child !== "string" || !removedIds.has(child)
580
+ );
581
+ return children.length === component.children.length ? component : { ...component, children };
582
+ }
497
583
  function submitActionWithDefaultUnknown(submit, field) {
498
584
  if (!isRecord(submit.action) || !isRecord(submit.action.event)) {
499
585
  return submit;
@@ -562,6 +648,9 @@ function optionalCoverageFieldFromFieldBindings(components) {
562
648
  if (normalized.includes("employerunioncoverage") || normalized.includes("coverageemployerunioncoverage")) {
563
649
  return "employer_union_coverage";
564
650
  }
651
+ if (normalized.includes("currentcoveragetype") || normalized.includes("coveragecurrentcoveragetype")) {
652
+ return "current_coverage_type";
653
+ }
565
654
  return void 0;
566
655
  }
567
656
  function componentFieldSearchText(component) {
@@ -770,8 +859,8 @@ function fieldFromPointer(path) {
770
859
  function fieldPointer(field) {
771
860
  return `/${field.replaceAll("~", "~0").replaceAll("/", "~1")}`;
772
861
  }
773
- function mergePersistedListRowsIntoMessages(messages, surfaceId, persistedRowsByPath) {
774
- if (persistedRowsByPath.size === 0) {
862
+ function mergePersistedListRowsIntoMessages(messages, surfaceId, persistedRowsByPath, deletedItemIdsByPath) {
863
+ if (persistedRowsByPath.size === 0 && deletedItemIdsByPath.size === 0) {
775
864
  return [...messages];
776
865
  }
777
866
  let mergedRoot = false;
@@ -786,7 +875,8 @@ function mergePersistedListRowsIntoMessages(messages, surfaceId, persistedRowsBy
786
875
  ...message.updateDataModel,
787
876
  value: mergePersistedListRowsIntoRoot(
788
877
  message.updateDataModel.value,
789
- persistedRowsByPath
878
+ persistedRowsByPath,
879
+ deletedItemIdsByPath
790
880
  )
791
881
  }
792
882
  };
@@ -801,25 +891,34 @@ function mergePersistedListRowsIntoMessages(messages, surfaceId, persistedRowsBy
801
891
  updateDataModel: {
802
892
  surfaceId,
803
893
  path: "/",
804
- value: mergePersistedListRowsIntoRoot({}, persistedRowsByPath)
894
+ value: mergePersistedListRowsIntoRoot(
895
+ {},
896
+ persistedRowsByPath,
897
+ deletedItemIdsByPath
898
+ )
805
899
  }
806
900
  }
807
901
  ];
808
902
  }
809
- function mergePersistedListRowsIntoRoot(root, persistedRowsByPath) {
903
+ function mergePersistedListRowsIntoRoot(root, persistedRowsByPath, deletedItemIdsByPath) {
810
904
  const merged = cloneJsonRecord(root);
811
- for (const [listPath, rows] of persistedRowsByPath) {
905
+ for (const listPath of /* @__PURE__ */ new Set([
906
+ ...persistedRowsByPath.keys(),
907
+ ...deletedItemIdsByPath.keys()
908
+ ])) {
909
+ const rows = persistedRowsByPath.get(listPath) ?? [];
812
910
  const dottedRows = merged[listPath];
813
911
  const nestedRows = getNestedValue(merged, listPath);
814
912
  const incomingRows = Array.isArray(dottedRows) ? dottedRows : Array.isArray(nestedRows) ? nestedRows : void 0;
815
913
  const shouldPreserveCachedRows = rows.length > 0 && (incomingRows === void 0 || incomingRows.length === 0 && (!hasListDraft(merged, listPath) || hasBlankListDraft(merged, listPath)));
816
914
  const effectiveRows = shouldPreserveCachedRows ? rows : incomingRows ?? rows;
817
- if (!Array.isArray(dottedRows) || shouldPreserveCachedRows) {
818
- merged[listPath] = cloneJsonArray(effectiveRows);
819
- }
820
- if (!Array.isArray(nestedRows) || shouldPreserveCachedRows) {
821
- setNestedValue(merged, listPath, cloneJsonArray(effectiveRows));
822
- }
915
+ const visibleRows = filterDeletedListRows(
916
+ effectiveRows,
917
+ deletedItemIdsByPath.get(listPath)
918
+ );
919
+ const normalizedRows = normalizeListRows(listPath, visibleRows, merged);
920
+ merged[listPath] = cloneJsonArray(normalizedRows);
921
+ setNestedValue(merged, listPath, cloneJsonArray(normalizedRows));
823
922
  }
824
923
  return merged;
825
924
  }
@@ -850,14 +949,66 @@ function isBlankDraftValue(value) {
850
949
  }
851
950
  return false;
852
951
  }
853
- function rememberPersistedListRows(persistedRowsByPath, root) {
952
+ function rememberPersistedListRows(persistedRowsByPath, deletedItemIdsByPath, root) {
854
953
  if (!isRecord(root)) {
855
954
  return;
856
955
  }
857
956
  for (const [listPath, rows] of listRowsFromRoot(root)) {
858
- persistedRowsByPath.set(listPath, cloneJsonArray(rows));
957
+ const visibleRows = filterDeletedListRows(
958
+ rows,
959
+ deletedItemIdsByPath.get(listPath)
960
+ );
961
+ persistedRowsByPath.set(
962
+ listPath,
963
+ normalizeListRows(listPath, visibleRows, root)
964
+ );
859
965
  }
860
966
  }
967
+ function normalizeListRows(listPath, rows, root) {
968
+ const clonedRows = cloneJsonArray(rows);
969
+ if (listPath !== "needs.providers") {
970
+ return clonedRows;
971
+ }
972
+ const rootProvider = root === void 0 ? void 0 : providerRowFromAliases(root);
973
+ if (clonedRows.length === 0 && rootProvider !== void 0) {
974
+ return [normalizeProviderRow(rootProvider)];
975
+ }
976
+ return clonedRows.map(
977
+ (row) => isRecord(row) ? normalizeProviderRow(row, rootProvider) : row
978
+ );
979
+ }
980
+ function normalizeProviderRow(row, fallback) {
981
+ const normalized = cloneJsonRecord(row);
982
+ const name = firstProviderName(normalized) ?? (fallback === void 0 ? void 0 : firstProviderName(fallback));
983
+ const location = firstProviderLocation(normalized) ?? (fallback === void 0 ? void 0 : firstProviderLocation(fallback));
984
+ if (normalized.primary_care_provider === void 0 && name !== void 0) {
985
+ normalized.primary_care_provider = name;
986
+ }
987
+ if (normalized.primary_care_provider_location === void 0 && location !== void 0) {
988
+ normalized.primary_care_provider_location = location;
989
+ }
990
+ if (name !== void 0 && location !== void 0 && typeof normalized.__displayText === "string" && !normalized.__displayText.includes(location)) {
991
+ normalized.__displayText = `${normalized.__displayText} | Provider Location: ${location}`;
992
+ } else if (normalized.__displayText === void 0 && (name !== void 0 || location !== void 0)) {
993
+ normalized.__displayText = [
994
+ name === void 0 ? void 0 : `Provider Name: ${name}`,
995
+ location === void 0 ? void 0 : `Provider Location: ${location}`
996
+ ].filter((part) => part !== void 0).join(" | ");
997
+ }
998
+ return normalized;
999
+ }
1000
+ function providerRowFromAliases(source) {
1001
+ const name = firstProviderName(source);
1002
+ const location = firstProviderLocation(source);
1003
+ if (name === void 0 && location === void 0) {
1004
+ return void 0;
1005
+ }
1006
+ return {
1007
+ itemId: "voice-primary-care-provider",
1008
+ ...name === void 0 ? {} : { primary_care_provider: name },
1009
+ ...location === void 0 ? {} : { primary_care_provider_location: location }
1010
+ };
1011
+ }
861
1012
  function submittedProviderRowFromEvent(event) {
862
1013
  if (event.actionName !== "flow.submit") {
863
1014
  return void 0;
@@ -866,37 +1017,8 @@ function submittedProviderRowFromEvent(event) {
866
1017
  if (listPath !== "needs.providers" && !hasProviderSubmitFields(event.context)) {
867
1018
  return void 0;
868
1019
  }
869
- const name = firstTextField(event.context, [
870
- "primary_care_provider",
871
- "primaryCareProvider",
872
- "primary_provider",
873
- "primaryProvider",
874
- "primary_care_doctor",
875
- "primaryCareDoctor",
876
- "pcp",
877
- "providerName",
878
- "provider_name",
879
- "displayName",
880
- "display_name",
881
- "doctorName",
882
- "doctorname",
883
- "doctor_name",
884
- "name"
885
- ]);
886
- const location = firstTextField(event.context, [
887
- "primary_care_provider_location",
888
- "primaryCareProviderLocation",
889
- "provider_location",
890
- "providerLocation",
891
- "location_details",
892
- "locationDetails",
893
- "office_location",
894
- "officeLocation",
895
- "practice_location",
896
- "practiceLocation",
897
- "location",
898
- "address"
899
- ]);
1020
+ const name = firstProviderName(event.context);
1021
+ const location = firstProviderLocation(event.context);
900
1022
  if (name === void 0 && location === void 0) {
901
1023
  return void 0;
902
1024
  }
@@ -1088,6 +1210,122 @@ function upsertListRow(rows, row) {
1088
1210
  }
1089
1211
  return [...next, row];
1090
1212
  }
1213
+ function removeListRowByItemId(rows, itemId) {
1214
+ return rows.filter(
1215
+ (row) => !isRecord(row) || row.itemId !== itemId
1216
+ );
1217
+ }
1218
+ function rememberDeletedListItemId(deletedItemIdsByPath, listPath, itemId) {
1219
+ const deleted = deletedItemIdsByPath.get(listPath) ?? /* @__PURE__ */ new Set();
1220
+ deleted.add(itemId);
1221
+ deletedItemIdsByPath.set(listPath, deleted);
1222
+ }
1223
+ function filterDeletedListRows(rows, deletedItemIds) {
1224
+ const clonedRows = cloneJsonArray(rows);
1225
+ if (deletedItemIds === void 0 || deletedItemIds.size === 0) {
1226
+ return clonedRows;
1227
+ }
1228
+ return clonedRows.filter(
1229
+ (row) => !isRecord(row) || !deletedItemIds.has(stringRowItemId(row))
1230
+ );
1231
+ }
1232
+ function stringRowItemId(row) {
1233
+ const itemId = row.itemId;
1234
+ return typeof itemId === "string" ? itemId : "";
1235
+ }
1236
+ var PROVIDER_NAME_FIELDS = /* @__PURE__ */ new Set([
1237
+ "primary_care_provider",
1238
+ "primarycareprovider",
1239
+ "primary_care_provider_name",
1240
+ "primarycareprovidername",
1241
+ "primary_provider",
1242
+ "primaryprovider",
1243
+ "primary_provider_name",
1244
+ "primaryprovidername",
1245
+ "primary_care_doctor",
1246
+ "primarycaredoctor",
1247
+ "primary_care_doctor_name",
1248
+ "primarycaredoctorname",
1249
+ "pcp",
1250
+ "pcp_name",
1251
+ "pcpname",
1252
+ "provider",
1253
+ "provider_name",
1254
+ "providername",
1255
+ "display_name",
1256
+ "displayname",
1257
+ "doctor",
1258
+ "doctor_name",
1259
+ "doctorname",
1260
+ "name"
1261
+ ]);
1262
+ var PROVIDER_LOCATION_FIELDS = /* @__PURE__ */ new Set([
1263
+ "primary_care_provider_location",
1264
+ "primarycareproviderlocation",
1265
+ "primary_provider_location",
1266
+ "primaryproviderlocation",
1267
+ "primary_care_location",
1268
+ "primarycarelocation",
1269
+ "primary_care_doctor_location",
1270
+ "primarycaredoctorlocation",
1271
+ "pcp_location",
1272
+ "pcplocation",
1273
+ "provider_location",
1274
+ "providerlocation",
1275
+ "provider_location_details",
1276
+ "providerlocationdetails",
1277
+ "doctor_location",
1278
+ "doctorlocation",
1279
+ "location",
1280
+ "location_details",
1281
+ "locationdetails",
1282
+ "office_location",
1283
+ "officelocation",
1284
+ "practice_location",
1285
+ "practicelocation",
1286
+ "provider_address",
1287
+ "provideraddress",
1288
+ "doctor_address",
1289
+ "doctoraddress",
1290
+ "address",
1291
+ "city_state",
1292
+ "citystate"
1293
+ ]);
1294
+ function firstProviderName(source) {
1295
+ return firstTextByNormalizedField(source, PROVIDER_NAME_FIELDS);
1296
+ }
1297
+ function firstProviderLocation(source) {
1298
+ return firstTextByNormalizedField(source, PROVIDER_LOCATION_FIELDS);
1299
+ }
1300
+ function firstTextByNormalizedField(source, fields) {
1301
+ for (const [key, value] of Object.entries(source)) {
1302
+ if (!fields.has(normalizeFieldKey(key))) {
1303
+ continue;
1304
+ }
1305
+ const text = scalarText(value);
1306
+ if (text !== void 0) {
1307
+ return text;
1308
+ }
1309
+ }
1310
+ return void 0;
1311
+ }
1312
+ function scalarText(value) {
1313
+ if (typeof value === "string") {
1314
+ const text = value.trim();
1315
+ return text.length > 0 ? text : void 0;
1316
+ }
1317
+ if (!isRecord(value)) {
1318
+ return void 0;
1319
+ }
1320
+ return firstTextField(value, [
1321
+ "value",
1322
+ "displayValue",
1323
+ "display_value",
1324
+ "text",
1325
+ "answer",
1326
+ "label"
1327
+ ]);
1328
+ }
1091
1329
  function firstTextField(source, keys) {
1092
1330
  for (const key of keys) {
1093
1331
  const value = source[key];
@@ -1754,8 +1992,22 @@ function applyControlValidationAttributes(control, field) {
1754
1992
  }
1755
1993
  function attachControlValidationBehavior(control, field) {
1756
1994
  const maxLength = numericMaxLengthForField(field);
1995
+ const customValidation = customValidationForField(field);
1757
1996
  if (maxLength === void 0 || !isTextInput(control)) {
1758
- return void 0;
1997
+ if (customValidation === void 0 || !isTextInput(control)) {
1998
+ return void 0;
1999
+ }
2000
+ const validate = () => {
2001
+ applyCustomValidationMessage(control, customValidation);
2002
+ };
2003
+ control.addEventListener("input", validate);
2004
+ control.addEventListener("change", validate);
2005
+ validate();
2006
+ return () => {
2007
+ control.setCustomValidity("");
2008
+ control.removeEventListener("input", validate);
2009
+ control.removeEventListener("change", validate);
2010
+ };
1759
2011
  }
1760
2012
  const sanitize = () => {
1761
2013
  const next = control.value.replace(/\D/g, "").slice(0, maxLength);
@@ -1763,15 +2015,50 @@ function attachControlValidationBehavior(control, field) {
1763
2015
  control.value = next;
1764
2016
  control.dispatchEvent(new Event("input", { bubbles: true }));
1765
2017
  }
2018
+ if (customValidation !== void 0) {
2019
+ applyCustomValidationMessage(control, customValidation);
2020
+ }
1766
2021
  };
1767
2022
  control.addEventListener("input", sanitize);
1768
2023
  control.addEventListener("change", sanitize);
1769
2024
  sanitize();
1770
2025
  return () => {
2026
+ control.setCustomValidity("");
1771
2027
  control.removeEventListener("input", sanitize);
1772
2028
  control.removeEventListener("change", sanitize);
1773
2029
  };
1774
2030
  }
2031
+ function customValidationForField(field) {
2032
+ if (isZipValidationRegexp(field.validationRegexp)) {
2033
+ return {
2034
+ message: "Enter a valid 5-digit ZIP code.",
2035
+ pattern: regexpFromPattern(field.validationRegexp)
2036
+ };
2037
+ }
2038
+ if (isPhoneValidationRegexp(field.validationRegexp)) {
2039
+ return {
2040
+ message: "Enter a valid 10-digit US phone number.",
2041
+ pattern: regexpFromPattern(field.validationRegexp)
2042
+ };
2043
+ }
2044
+ return void 0;
2045
+ }
2046
+ function applyCustomValidationMessage(control, validation) {
2047
+ control.setCustomValidity("");
2048
+ if (control.value.length > 0 && (validation.pattern?.test(control.value) === false || !control.checkValidity())) {
2049
+ control.setCustomValidity(validation.message);
2050
+ }
2051
+ }
2052
+ function regexpFromPattern(pattern) {
2053
+ if (pattern === void 0) {
2054
+ return void 0;
2055
+ }
2056
+ try {
2057
+ return new RegExp(pattern);
2058
+ } catch {
2059
+ return void 0;
2060
+ }
2061
+ }
1775
2062
  function numericMaxLengthForField(field) {
1776
2063
  if (isPhoneValidationRegexp(field.validationRegexp)) {
1777
2064
  return 10;
@@ -2537,6 +2824,7 @@ function decodeRendererAction(event) {
2537
2824
  ([key]) => key !== "listPath" && key !== "itemId"
2538
2825
  );
2539
2826
  const fields2 = scalarFields(fieldEntries2, listPath);
2827
+ const targetStateId2 = listActionTargetStateId(event.sourceComponentId);
2540
2828
  if (action !== "flow.list.delete" && (fields2 === null || Object.keys(fields2).length === 0)) {
2541
2829
  return null;
2542
2830
  }
@@ -2544,6 +2832,7 @@ function decodeRendererAction(event) {
2544
2832
  action,
2545
2833
  payload: {
2546
2834
  listPath,
2835
+ ...targetStateId2 === void 0 ? {} : { targetStateId: targetStateId2 },
2547
2836
  ...typeof itemId === "string" ? { itemId } : {},
2548
2837
  ...fields2 !== null && Object.keys(fields2).length > 0 ? { fields: fields2 } : {}
2549
2838
  }
@@ -2566,6 +2855,14 @@ function decodeRendererAction(event) {
2566
2855
  }
2567
2856
  };
2568
2857
  }
2858
+ function listActionTargetStateId(sourceComponentId) {
2859
+ const markerIndex = sourceComponentId.indexOf(":list");
2860
+ if (markerIndex <= 0) {
2861
+ return void 0;
2862
+ }
2863
+ const stateId = sourceComponentId.slice(0, markerIndex);
2864
+ return stateId.length > 0 ? stateId : void 0;
2865
+ }
2569
2866
  function scalarFields(entries, listPath) {
2570
2867
  const fields = {};
2571
2868
  for (const [key, value] of entries) {