snow-flow 10.0.1-dev.467 → 10.0.1-dev.468

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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "$schema": "https://json.schemastore.org/package.json",
3
- "version": "10.0.1-dev.467",
3
+ "version": "10.0.1-dev.468",
4
4
  "name": "snow-flow",
5
5
  "description": "Snow-Flow - ServiceNow Multi-Agent Development Framework powered by AI",
6
6
  "license": "Elastic-2.0",
@@ -1009,12 +1009,30 @@ async function addActionViaGraphQL(
1009
1009
  inputResult.actionParams, uuid
1010
1010
  );
1011
1011
  steps.record_action = recordActionResult.steps;
1012
+ var hasRecordPills = recordActionResult.labelCacheEntries.length > 0;
1013
+
1014
+ // For record actions: clear data pill values from INSERT — they'll be set via separate UPDATE
1015
+ // (Flow Designer's GraphQL API ignores labelCache during INSERT, it only works with UPDATE)
1016
+ var insertInputs = recordActionResult.inputs;
1017
+ if (hasRecordPills) {
1018
+ // Clone inputs and clear data pill values for INSERT
1019
+ insertInputs = recordActionResult.inputs.map(function (inp: any) {
1020
+ if (inp.name === 'record' && inp.value?.value?.startsWith('{{')) {
1021
+ return { ...inp, value: { schemaless: false, schemalessValue: '', value: '' } };
1022
+ }
1023
+ if (inp.name === 'values' && inp.value?.value?.includes('{{')) {
1024
+ return { ...inp, value: { schemaless: false, schemalessValue: '', value: '' } };
1025
+ }
1026
+ return inp;
1027
+ });
1028
+ steps.record_action_strategy = 'two_step';
1029
+ }
1012
1030
 
1013
1031
  const actionResponseFields = 'actions { inserts { sysId uiUniqueIdentifier __typename } updates deletes __typename }' +
1014
1032
  ' flowLogics { inserts { sysId uiUniqueIdentifier __typename } updates deletes __typename }' +
1015
1033
  ' subflows { inserts { sysId uiUniqueIdentifier __typename } updates deletes __typename }';
1016
1034
 
1017
- // Build mutation payload — single INSERT with full inputs (matching UI behavior)
1035
+ // Build mutation payload — INSERT with inputs (data pill values cleared for record actions)
1018
1036
  const flowPatch: any = {
1019
1037
  flowId: flowId,
1020
1038
  actions: {
@@ -1028,25 +1046,62 @@ async function addActionViaGraphQL(
1028
1046
  uiUniqueIdentifier: uuid,
1029
1047
  type: 'action',
1030
1048
  parentUiId: parentUiId || '',
1031
- inputs: recordActionResult.inputs
1049
+ inputs: insertInputs
1032
1050
  }]
1033
1051
  }
1034
1052
  };
1035
1053
 
1036
- // Add labelCache entries for data pill references in record actions
1037
- if (recordActionResult.labelCacheEntries.length > 0) {
1038
- flowPatch.labelCache = { insert: recordActionResult.labelCacheEntries };
1039
- }
1040
-
1041
1054
  // Add parent flow logic update signal (tells GraphQL the parent was modified)
1042
1055
  if (parentUiId) {
1043
1056
  flowPatch.flowLogics = { update: [{ uiUniqueIdentifier: parentUiId, type: 'flowlogic' }] };
1044
1057
  }
1045
1058
 
1046
1059
  try {
1060
+ // Step 1: INSERT the action element
1047
1061
  const result = await executeFlowPatchMutation(client, flowPatch, actionResponseFields);
1048
1062
  const actionId = result?.actions?.inserts?.[0]?.sysId;
1049
1063
  steps.insert = { success: !!actionId, actionId, uuid };
1064
+ if (!actionId) return { success: false, steps, error: 'GraphQL action INSERT returned no ID' };
1065
+
1066
+ // Step 2: UPDATE with data pill values + labelCache (separate mutation, matching UI behavior)
1067
+ // The Flow Designer UI always sets data pill references via a separate UPDATE.
1068
+ if (hasRecordPills) {
1069
+ var updateInputs: any[] = [];
1070
+ // Collect all inputs that have data pill values
1071
+ for (var ri = 0; ri < recordActionResult.inputs.length; ri++) {
1072
+ var inp = recordActionResult.inputs[ri];
1073
+ var val = inp.value?.value || '';
1074
+ if (inp.name === 'record' && val.startsWith('{{')) {
1075
+ updateInputs.push({ name: 'record', value: { schemaless: false, schemalessValue: '', value: val } });
1076
+ } else if (inp.name === 'table_name') {
1077
+ updateInputs.push({ name: 'table_name', displayValue: inp.displayValue || { value: '' }, value: inp.value || { value: '' } });
1078
+ } else if (inp.name === 'values' && val) {
1079
+ updateInputs.push({ name: 'values', value: { schemaless: false, schemalessValue: '', value: val } });
1080
+ }
1081
+ }
1082
+
1083
+ if (updateInputs.length > 0) {
1084
+ try {
1085
+ var updatePatch: any = {
1086
+ flowId: flowId,
1087
+ labelCache: { insert: recordActionResult.labelCacheEntries },
1088
+ actions: {
1089
+ update: [{
1090
+ uiUniqueIdentifier: uuid,
1091
+ type: 'action',
1092
+ inputs: updateInputs
1093
+ }]
1094
+ }
1095
+ };
1096
+ await executeFlowPatchMutation(client, updatePatch, actionResponseFields);
1097
+ steps.record_update = { success: true, inputCount: updateInputs.length };
1098
+ } catch (ue: any) {
1099
+ steps.record_update = { success: false, error: ue.message };
1100
+ // Action was created — update failure is non-fatal
1101
+ }
1102
+ }
1103
+ }
1104
+
1050
1105
  return { success: true, actionId: actionId || undefined, steps };
1051
1106
  } catch (e: any) {
1052
1107
  steps.insert = { success: false, error: e.message };