@nocobase/plugin-flow-engine 2.2.0-beta.1 → 2.2.0-beta.11

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.
Files changed (72) hide show
  1. package/dist/client/index.js +1 -1
  2. package/dist/externalVersion.js +9 -9
  3. package/dist/locale/en-US.json +1 -0
  4. package/dist/locale/index.d.ts +2 -0
  5. package/dist/locale/zh-CN.json +1 -0
  6. package/dist/node_modules/@ant-design/icons-svg/package.json +1 -1
  7. package/dist/node_modules/acorn/package.json +1 -1
  8. package/dist/node_modules/acorn-jsx/package.json +1 -1
  9. package/dist/node_modules/acorn-walk/package.json +1 -1
  10. package/dist/node_modules/ses/package.json +1 -1
  11. package/dist/node_modules/zod/package.json +1 -1
  12. package/dist/server/flow-surfaces/{runjs-authoring/blocked-global-stop/index.d.ts → approval/authoring-validation.d.ts} +1 -2
  13. package/dist/server/flow-surfaces/approval/authoring-validation.js +1151 -0
  14. package/dist/server/flow-surfaces/approval/blueprint-service.js +2 -0
  15. package/dist/server/flow-surfaces/authoring-validation.d.ts +2 -1
  16. package/dist/server/flow-surfaces/authoring-validation.js +639 -59
  17. package/dist/server/flow-surfaces/blueprint/compile-blocks.js +7 -3
  18. package/dist/server/flow-surfaces/blueprint/compile-plan.js +19 -15
  19. package/dist/server/flow-surfaces/blueprint/export-document.d.ts +50 -0
  20. package/dist/server/flow-surfaces/blueprint/export-document.js +2510 -0
  21. package/dist/server/flow-surfaces/blueprint/normalize-document.js +2 -1
  22. package/dist/server/flow-surfaces/blueprint/public-types.d.ts +1 -0
  23. package/dist/server/flow-surfaces/builder.js +43 -5
  24. package/dist/server/flow-surfaces/catalog.js +13 -2
  25. package/dist/server/flow-surfaces/configure-options.js +5 -3
  26. package/dist/server/flow-surfaces/constants.d.ts +9 -2
  27. package/dist/server/flow-surfaces/constants.js +1 -0
  28. package/dist/server/flow-surfaces/contract-guard.js +37 -5
  29. package/dist/server/flow-surfaces/default-action-popup.d.ts +2 -0
  30. package/dist/server/flow-surfaces/default-action-popup.js +27 -13
  31. package/dist/server/flow-surfaces/filter-group.d.ts +19 -2
  32. package/dist/server/flow-surfaces/filter-group.js +232 -3
  33. package/dist/server/flow-surfaces/planning/compiler.d.ts +1 -0
  34. package/dist/server/flow-surfaces/planning/compiler.js +205 -82
  35. package/dist/server/flow-surfaces/planning/key-registry.d.ts +1 -1
  36. package/dist/server/flow-surfaces/planning/runtime.js +1 -0
  37. package/dist/server/flow-surfaces/planning/step-link.d.ts +1 -1
  38. package/dist/server/flow-surfaces/planning/step-link.js +22 -3
  39. package/dist/server/flow-surfaces/public-data-surface-default-filter.js +0 -9
  40. package/dist/server/flow-surfaces/reaction/field-value.d.ts +9 -0
  41. package/dist/server/flow-surfaces/reaction/field-value.js +51 -2
  42. package/dist/server/flow-surfaces/reaction/linkage.d.ts +6 -1
  43. package/dist/server/flow-surfaces/reaction/linkage.js +18 -3
  44. package/dist/server/flow-surfaces/reaction/meta.js +19 -1
  45. package/dist/server/flow-surfaces/reaction/types.d.ts +19 -0
  46. package/dist/server/flow-surfaces/relation-backing-foreign-key.d.ts +10 -0
  47. package/dist/server/flow-surfaces/relation-backing-foreign-key.js +79 -0
  48. package/dist/server/flow-surfaces/runjs-authoring/ast/source.d.ts +1 -0
  49. package/dist/server/flow-surfaces/runjs-authoring/ast/source.js +20 -0
  50. package/dist/server/flow-surfaces/runjs-authoring/rules.js +0 -2
  51. package/dist/server/flow-surfaces/runjs-authoring/runtime/constants.d.ts +0 -1
  52. package/dist/server/flow-surfaces/runjs-authoring/runtime/constants.js +11 -19
  53. package/dist/server/flow-surfaces/runjs-authoring/runtime/types.d.ts +0 -12
  54. package/dist/server/flow-surfaces/runjs-authoring/scan/filter.js +12 -2
  55. package/dist/server/flow-surfaces/runjs-authoring/scan/index.d.ts +0 -14
  56. package/dist/server/flow-surfaces/runjs-authoring/scan/index.js +10 -8
  57. package/dist/server/flow-surfaces/runjs-authoring/scan/source-patterns.d.ts +0 -14
  58. package/dist/server/flow-surfaces/runjs-authoring/scan/source-patterns.js +18 -73
  59. package/dist/server/flow-surfaces/runjs-authoring/types.d.ts +1 -1
  60. package/dist/server/flow-surfaces/runjs-authoring/validators/index.js +9 -53
  61. package/dist/server/flow-surfaces/service.d.ts +53 -0
  62. package/dist/server/flow-surfaces/service.js +997 -127
  63. package/dist/server/flow-surfaces/types.d.ts +2 -1
  64. package/dist/server/variables/records.js +7 -2
  65. package/dist/server/variables/registry.js +3 -0
  66. package/dist/swagger/flow-surfaces.d.ts +193 -0
  67. package/dist/swagger/flow-surfaces.examples.d.ts +11 -0
  68. package/dist/swagger/flow-surfaces.examples.js +11 -0
  69. package/dist/swagger/flow-surfaces.js +179 -10
  70. package/dist/swagger/index.d.ts +193 -0
  71. package/package.json +2 -2
  72. package/dist/server/flow-surfaces/runjs-authoring/blocked-global-stop/index.js +0 -40
@@ -132,8 +132,9 @@ function normalizeNavigation(input) {
132
132
  return void 0;
133
133
  }
134
134
  (0, import_private_utils.assertPlainObject)(input, "flowSurfaces applyBlueprint navigation");
135
- (0, import_private_utils.assertOnlyAllowedKeys)(input, "flowSurfaces applyBlueprint navigation", ["group", "item"]);
135
+ (0, import_private_utils.assertOnlyAllowedKeys)(input, "flowSurfaces applyBlueprint navigation", ["layoutUid", "group", "item"]);
136
136
  const normalized = (0, import_service_utils.buildDefinedPayload)({
137
+ layoutUid: (0, import_private_utils.readOptionalString)(input.layoutUid),
137
138
  group: import_lodash.default.isUndefined(input.group) ? void 0 : (() => {
138
139
  (0, import_private_utils.assertPlainObject)(input.group, "flowSurfaces applyBlueprint navigation.group");
139
140
  (0, import_private_utils.assertOnlyAllowedKeys)(input.group, "flowSurfaces applyBlueprint navigation.group", [
@@ -20,6 +20,7 @@ export type FlowSurfaceApplyBlueprintNavigationGroup = {
20
20
  hideInMenu?: boolean;
21
21
  };
22
22
  export type FlowSurfaceApplyBlueprintNavigation = {
23
+ layoutUid?: string;
23
24
  group?: FlowSurfaceApplyBlueprintNavigationGroup;
24
25
  item?: {
25
26
  title?: string;
@@ -731,10 +731,19 @@ function buildActionTree(options) {
731
731
  containerUse: options.containerUse,
732
732
  resourceInit: options.resourceInit
733
733
  });
734
+ const requestedProps = options.props;
735
+ const requestedButtonGeneral = import_lodash.default.get(options.stepParams, ["buttonSettings", "general"]);
736
+ const stripImplicitTitle = shouldStripImplicitIconOnlyActionTitle(requestedProps, requestedButtonGeneral);
734
737
  const props = import_lodash.default.merge({}, import_lodash.default.cloneDeep(defaults.props || {}), import_lodash.default.cloneDeep(options.props || {}));
738
+ if (stripImplicitTitle) {
739
+ delete props.title;
740
+ }
735
741
  const stepParams = import_lodash.default.merge({}, import_lodash.default.cloneDeep(defaults.stepParams || {}), import_lodash.default.cloneDeep(options.stepParams || {}));
736
742
  if (import_lodash.default.isPlainObject((_a = stepParams == null ? void 0 : stepParams.buttonSettings) == null ? void 0 : _a.general)) {
737
743
  stepParams.buttonSettings.general = import_lodash.default.merge({}, stepParams.buttonSettings.general, pickButtonGeneralProps(props));
744
+ if (stripImplicitTitle) {
745
+ delete stepParams.buttonSettings.general.title;
746
+ }
738
747
  }
739
748
  return {
740
749
  use,
@@ -767,10 +776,15 @@ function buildCanonicalTableActionsColumnNode(options = {}) {
767
776
  }
768
777
  function pickButtonGeneralProps(props) {
769
778
  return import_lodash.default.pickBy(
770
- import_lodash.default.pick(props || {}, ["title", "tooltip", "icon", "type", "danger", "color"]),
779
+ import_lodash.default.pick(props || {}, ["title", "tooltip", "icon", "iconOnly", "type", "danger", "color"]),
771
780
  (value) => !import_lodash.default.isUndefined(value)
772
781
  );
773
782
  }
783
+ function shouldStripImplicitIconOnlyActionTitle(props, buttonGeneral) {
784
+ const hasRequestedOnlyIcon = import_lodash.default.isPlainObject(props) && Object.prototype.hasOwnProperty.call(props, "iconOnly") && props.iconOnly === true || import_lodash.default.isPlainObject(buttonGeneral) && Object.prototype.hasOwnProperty.call(buttonGeneral, "iconOnly") && buttonGeneral.iconOnly === true;
785
+ const hasRequestedTitle = import_lodash.default.isPlainObject(props) && Object.prototype.hasOwnProperty.call(props, "title") || import_lodash.default.isPlainObject(buttonGeneral) && Object.prototype.hasOwnProperty.call(buttonGeneral, "title");
786
+ return hasRequestedOnlyIcon && !hasRequestedTitle;
787
+ }
774
788
  function assignClientKeysToUids(spec, clientKeyToUid) {
775
789
  const next = import_lodash.default.cloneDeep(spec);
776
790
  const walk = (node) => {
@@ -805,12 +819,16 @@ function buildActionDefaults(options) {
805
819
  (approvalDefaults == null ? void 0 : approvalDefaults.props) || {}
806
820
  );
807
821
  const normalizedProps = applyContainerActionStyle(props, options.containerUse);
822
+ const buttonGeneralProps = applyCompactRecordActionButtonDefaults(
823
+ pickButtonGeneralProps(normalizedProps),
824
+ options.containerUse
825
+ );
808
826
  const stepParams = import_lodash.default.merge(
809
827
  {},
810
828
  import_lodash.default.cloneDeep((approvalDefaults == null ? void 0 : approvalDefaults.stepParams) || {}),
811
829
  readonlyCalendarAction ? {} : {
812
830
  buttonSettings: {
813
- general: pickButtonGeneralProps(normalizedProps)
831
+ general: buttonGeneralProps
814
832
  }
815
833
  }
816
834
  );
@@ -919,6 +937,9 @@ function inferPopupActionSourceId(resourceInit) {
919
937
  if (!(resourceInit == null ? void 0 : resourceInit.associationName)) {
920
938
  return void 0;
921
939
  }
940
+ if (!Object.prototype.hasOwnProperty.call(resourceInit, "sourceId")) {
941
+ return "{{ctx.view.inputArgs.sourceId}}";
942
+ }
922
943
  const sourceId = typeof (resourceInit == null ? void 0 : resourceInit.sourceId) === "string" ? resourceInit.sourceId.trim() : resourceInit == null ? void 0 : resourceInit.sourceId;
923
944
  if (!sourceId) {
924
945
  return void 0;
@@ -997,6 +1018,7 @@ function inferActionDefaultProps(use, scope) {
997
1018
  title: "",
998
1019
  tooltip: '{{t("Delete")}}',
999
1020
  icon: "DeleteOutlined",
1021
+ iconOnly: true,
1000
1022
  position: "right"
1001
1023
  },
1002
1024
  BulkEditActionModel: {
@@ -1120,10 +1142,26 @@ function inferActionDefaultProps(use, scope) {
1120
1142
  }
1121
1143
  );
1122
1144
  }
1145
+ const COMPACT_RECORD_ACTION_CONTAINER_USES = /* @__PURE__ */ new Set([
1146
+ "TableActionsColumnModel",
1147
+ "ListItemModel",
1148
+ "GridCardItemModel",
1149
+ "CommentItemModel"
1150
+ ]);
1151
+ function isCompactRecordActionContainerUse(containerUse) {
1152
+ return COMPACT_RECORD_ACTION_CONTAINER_USES.has(String(containerUse || "").trim());
1153
+ }
1154
+ function applyCompactRecordActionButtonDefaults(props, containerUse) {
1155
+ if (isCompactRecordActionContainerUse(containerUse) && props.icon === null && !Object.prototype.hasOwnProperty.call(props, "iconOnly")) {
1156
+ return {
1157
+ ...props,
1158
+ iconOnly: false
1159
+ };
1160
+ }
1161
+ return props;
1162
+ }
1123
1163
  function applyContainerActionStyle(props, containerUse) {
1124
- if (["TableActionsColumnModel", "ListItemModel", "GridCardItemModel", "CommentItemModel"].includes(
1125
- String(containerUse || "").trim()
1126
- )) {
1164
+ if (isCompactRecordActionContainerUse(containerUse)) {
1127
1165
  return {
1128
1166
  ...props,
1129
1167
  type: "link",
@@ -182,7 +182,7 @@ const FILTER_FORM_ITEM_ALLOWED_PATHS = [
182
182
  "init.filterField.type",
183
183
  "initialValue.defaultValue"
184
184
  ];
185
- const ACTION_PROP_KEYS = ["title", "tooltip", "icon", "type", "htmlType", "position", "danger", "color"];
185
+ const ACTION_PROP_KEYS = ["title", "tooltip", "icon", "iconOnly", "type", "htmlType", "position", "danger", "color"];
186
186
  const FILTER_ACTION_PROP_KEYS = [...ACTION_PROP_KEYS, "filterableFieldNames", "defaultFilterValue", "filterValue"];
187
187
  const FILTER_ACTION_PROP_PATH_SCHEMAS = {
188
188
  filterableFieldNames: {
@@ -197,6 +197,7 @@ const ACTION_BUTTON_SETTINGS_GROUP = {
197
197
  "general.title",
198
198
  "general.tooltip",
199
199
  "general.icon",
200
+ "general.iconOnly",
200
201
  "general.type",
201
202
  "general.danger",
202
203
  "general.color",
@@ -208,6 +209,7 @@ const ACTION_BUTTON_SETTINGS_GROUP = {
208
209
  "general.title": STRING_SCHEMA,
209
210
  "general.tooltip": STRING_SCHEMA,
210
211
  "general.icon": NULLABLE_STRING_SCHEMA,
212
+ "general.iconOnly": BOOLEAN_SCHEMA,
211
213
  "general.type": STRING_SCHEMA,
212
214
  "general.danger": BOOLEAN_SCHEMA,
213
215
  "general.color": STRING_SCHEMA,
@@ -244,6 +246,15 @@ const RUN_JS_SETTINGS_GROUP = {
244
246
  "runJs.version": STRING_SCHEMA
245
247
  }
246
248
  };
249
+ const JS_BLOCK_SETTINGS_GROUP = {
250
+ allowedPaths: [...RUN_JS_ALLOWED_PATHS, "showBlockCard.showBlockCard"],
251
+ mergeStrategy: "deep",
252
+ eventBindingSteps: ["runJs"],
253
+ pathSchemas: {
254
+ ...RUN_JS_SETTINGS_GROUP.pathSchemas,
255
+ "showBlockCard.showBlockCard": BOOLEAN_SCHEMA
256
+ }
257
+ };
247
258
  const FIELD_SETTINGS_INIT_GROUP = {
248
259
  allowedPaths: [
249
260
  "init.dataSourceKey",
@@ -1378,7 +1389,7 @@ const JS_BLOCK_CONTRACT = createContract({
1378
1389
  }
1379
1390
  });
1380
1391
  JS_BLOCK_CONTRACT.domains.stepParams = groupedDomain({
1381
- jsSettings: RUN_JS_SETTINGS_GROUP
1392
+ jsSettings: JS_BLOCK_SETTINGS_GROUP
1382
1393
  });
1383
1394
  const MAP_BLOCK_CONTRACT = createContract({
1384
1395
  editableDomains: ["props", "decoratorProps", "stepParams", "flowRegistry"],
@@ -201,7 +201,7 @@ const DETAILS_OPTIONS = {
201
201
  sorting: SORTING,
202
202
  dataScope: FILTER_GROUP,
203
203
  linkageRules: arrayOption(
204
- "Raw linkage-rules payload. For AI/CLI authoring, prefer `getReactionMeta` + `setFieldLinkageRules` instead of guessing this configure key directly.",
204
+ "Raw canonical linkage-rules payload. The API normalizes condition-only rules to include `actions: []`; for AI/CLI authoring, prefer `getReactionMeta` + `setFieldLinkageRules` instead of guessing this configure key directly.",
205
205
  { example: [] }
206
206
  )
207
207
  };
@@ -237,7 +237,7 @@ const CALENDAR_OPTIONS = {
237
237
  weekStart: numberOption("Week start day. Use 1 for Monday or 0 for Sunday.", { example: 1 }),
238
238
  dataScope: FILTER_GROUP,
239
239
  linkageRules: arrayOption(
240
- "Raw linkage-rules payload. For AI/CLI authoring, prefer `getReactionMeta` + `setBlockLinkageRules` instead of guessing this configure key directly.",
240
+ "Raw canonical linkage-rules payload. The API normalizes condition-only rules to include `actions: []`; for AI/CLI authoring, prefer `getReactionMeta` + `setBlockLinkageRules` instead of guessing this configure key directly.",
241
241
  { example: [] }
242
242
  ),
243
243
  quickCreatePopup: OPEN_VIEW,
@@ -413,6 +413,7 @@ const JS_BLOCK_OPTIONS = {
413
413
  title: stringOption("Title", { example: "Runtime Banner" }),
414
414
  description: stringOption("Description", { example: "Custom JS block" }),
415
415
  className: stringOption("className", { example: "users-banner" }),
416
+ showBlockCard: booleanOption("Whether to show the outer block card", { default: true, example: true }),
416
417
  code: JS_CODE,
417
418
  version: JS_VERSION
418
419
  };
@@ -560,6 +561,7 @@ const ACTION_COMMON_OPTIONS = {
560
561
  title: stringOption("Button title", { example: "Run" }),
561
562
  tooltip: stringOption("Tooltip"),
562
563
  icon: stringOption("Icon", { example: "PlusOutlined" }),
564
+ iconOnly: booleanOption("Whether to render only the icon without visible button text", { example: true }),
563
565
  type: stringOption("Button type", { example: "primary" }),
564
566
  color: stringOption("Color"),
565
567
  htmlType: stringOption("HTML button type", { example: "submit" }),
@@ -588,7 +590,7 @@ const APPROVAL_ASSIGN_ACTION_OPTIONS = {
588
590
  };
589
591
  const ACTION_LINKAGE_OPTIONS = {
590
592
  linkageRules: arrayOption(
591
- "Raw linkage-rules payload. For AI/CLI authoring, prefer `getReactionMeta` + `setActionLinkageRules` instead of guessing this configure key directly.",
593
+ "Raw canonical linkage-rules payload. The API normalizes condition-only rules to include `actions: []`; for AI/CLI authoring, prefer `getReactionMeta` + `setActionLinkageRules` instead of guessing this configure key directly.",
592
594
  { example: [] }
593
595
  )
594
596
  };
@@ -45,6 +45,13 @@ export declare const FLOW_SURFACE_ACTION_DEFINITIONS: {
45
45
  readonly mutate: false;
46
46
  readonly valueSource: "default";
47
47
  };
48
+ readonly exportBlueprint: {
49
+ readonly method: "post";
50
+ readonly read: true;
51
+ readonly transaction: false;
52
+ readonly mutate: false;
53
+ readonly valueSource: "default";
54
+ };
48
55
  readonly getReactionMeta: {
49
56
  readonly method: "post";
50
57
  readonly read: true;
@@ -373,7 +380,7 @@ type SelectFlowSurfaceActionNames<TFlag extends keyof FlowSurfaceActionDefinitio
373
380
  [K in FlowSurfacesActionName]: (typeof FLOW_SURFACE_ACTION_DEFINITIONS)[K][TFlag] extends true ? K : never;
374
381
  }[FlowSurfacesActionName];
375
382
  type FlowSurfaceMutateActionName = SelectFlowSurfaceActionNames<'mutate'>;
376
- export declare const FLOW_SURFACES_ACTION_NAMES: ("setFieldValueRules" | "setBlockLinkageRules" | "setFieldLinkageRules" | "setActionLinkageRules" | "context" | "get" | "configure" | "createPage" | "addTab" | "addPopupTab" | "addBlock" | "addField" | "addAction" | "addRecordAction" | "compose" | "createMenu" | "catalog" | "describeSurface" | "getReactionMeta" | "applyBlueprint" | "applyApprovalBlueprint" | "listTemplates" | "getTemplate" | "saveTemplate" | "updateTemplate" | "destroyTemplate" | "convertTemplateToCopy" | "updateMenu" | "destroyPage" | "updateTab" | "moveTab" | "removeTab" | "updatePopupTab" | "movePopupTab" | "removePopupTab" | "addBlocks" | "addFields" | "addActions" | "addRecordActions" | "updateSettings" | "getEventFlowMeta" | "addEventFlow" | "setEventFlow" | "removeEventFlow" | "setEventFlows" | "setLayout" | "moveNode" | "removeNode" | "mutate" | "apply")[];
383
+ export declare const FLOW_SURFACES_ACTION_NAMES: ("setFieldValueRules" | "setBlockLinkageRules" | "setFieldLinkageRules" | "setActionLinkageRules" | "context" | "get" | "configure" | "apply" | "createPage" | "addTab" | "addPopupTab" | "addBlock" | "addField" | "addAction" | "addRecordAction" | "compose" | "createMenu" | "catalog" | "describeSurface" | "exportBlueprint" | "getReactionMeta" | "applyBlueprint" | "applyApprovalBlueprint" | "listTemplates" | "getTemplate" | "saveTemplate" | "updateTemplate" | "destroyTemplate" | "convertTemplateToCopy" | "updateMenu" | "destroyPage" | "updateTab" | "moveTab" | "removeTab" | "updatePopupTab" | "movePopupTab" | "removePopupTab" | "addBlocks" | "addFields" | "addActions" | "addRecordActions" | "updateSettings" | "getEventFlowMeta" | "addEventFlow" | "setEventFlow" | "removeEventFlow" | "setEventFlows" | "setLayout" | "moveNode" | "removeNode" | "mutate")[];
377
384
  export declare const FLOW_SURFACES_READ_ACTION_NAMES: SelectFlowSurfaceActionNames<"read">[];
378
385
  export declare const FLOW_SURFACE_MUTATE_OP_TYPES: FlowSurfaceMutateActionName[];
379
- export declare const FLOW_SURFACES_ACTION_METHODS: Record<"setFieldValueRules" | "setBlockLinkageRules" | "setFieldLinkageRules" | "setActionLinkageRules" | "context" | "get" | "configure" | "createPage" | "addTab" | "addPopupTab" | "addBlock" | "addField" | "addAction" | "addRecordAction" | "compose" | "createMenu" | "catalog" | "describeSurface" | "getReactionMeta" | "applyBlueprint" | "applyApprovalBlueprint" | "listTemplates" | "getTemplate" | "saveTemplate" | "updateTemplate" | "destroyTemplate" | "convertTemplateToCopy" | "updateMenu" | "destroyPage" | "updateTab" | "moveTab" | "removeTab" | "updatePopupTab" | "movePopupTab" | "removePopupTab" | "addBlocks" | "addFields" | "addActions" | "addRecordActions" | "updateSettings" | "getEventFlowMeta" | "addEventFlow" | "setEventFlow" | "removeEventFlow" | "setEventFlows" | "setLayout" | "moveNode" | "removeNode" | "mutate" | "apply", FlowSurfaceActionMethod>;
386
+ export declare const FLOW_SURFACES_ACTION_METHODS: Record<"setFieldValueRules" | "setBlockLinkageRules" | "setFieldLinkageRules" | "setActionLinkageRules" | "context" | "get" | "configure" | "apply" | "createPage" | "addTab" | "addPopupTab" | "addBlock" | "addField" | "addAction" | "addRecordAction" | "compose" | "createMenu" | "catalog" | "describeSurface" | "exportBlueprint" | "getReactionMeta" | "applyBlueprint" | "applyApprovalBlueprint" | "listTemplates" | "getTemplate" | "saveTemplate" | "updateTemplate" | "destroyTemplate" | "convertTemplateToCopy" | "updateMenu" | "destroyPage" | "updateTab" | "moveTab" | "removeTab" | "updatePopupTab" | "movePopupTab" | "removePopupTab" | "addBlocks" | "addFields" | "addActions" | "addRecordActions" | "updateSettings" | "getEventFlowMeta" | "addEventFlow" | "setEventFlow" | "removeEventFlow" | "setEventFlows" | "setLayout" | "moveNode" | "removeNode" | "mutate", FlowSurfaceActionMethod>;
@@ -40,6 +40,7 @@ const FLOW_SURFACE_ACTION_DEFINITIONS = {
40
40
  context: { method: "post", read: true, transaction: false, mutate: false, valueSource: "default" },
41
41
  get: { method: "get", read: true, transaction: false, mutate: false, valueSource: "read" },
42
42
  describeSurface: { method: "post", read: true, transaction: false, mutate: false, valueSource: "default" },
43
+ exportBlueprint: { method: "post", read: true, transaction: false, mutate: false, valueSource: "default" },
43
44
  getReactionMeta: { method: "post", read: true, transaction: false, mutate: false, valueSource: "default" },
44
45
  setFieldValueRules: { method: "post", read: false, transaction: true, mutate: false, valueSource: "default" },
45
46
  setBlockLinkageRules: { method: "post", read: false, transaction: true, mutate: false, valueSource: "default" },
@@ -393,23 +393,55 @@ function normalizeLinkageRulesValue(value, context, path) {
393
393
  return value;
394
394
  }
395
395
  return value.map((rule, index) => {
396
- if (!import_lodash.default.isPlainObject(rule) || !import_lodash.default.has(rule, "condition")) {
397
- return rule;
396
+ if (!import_lodash.default.isPlainObject(rule)) {
397
+ (0, import_errors.throwBadRequest)(
398
+ `flowSurfaces updateSettings domain '${getLinkageRuleDomainPath(context, path, index)}' on '${context.use}' expects each linkage rule to be an object`
399
+ );
398
400
  }
399
401
  const normalizedRule = import_lodash.default.cloneDeep(rule);
400
- const domainPath = context.groupKey ? `${context.domain}.${context.groupKey}.${path}[${index}].condition` : `${context.domain}.${path}[${index}].condition`;
402
+ const hasCondition = import_lodash.default.has(normalizedRule, "condition");
403
+ const hasWhen = import_lodash.default.has(normalizedRule, "when");
404
+ const conditionLeaf = hasCondition ? "condition" : hasWhen ? "when" : "condition";
405
+ const conditionInput = hasCondition ? import_lodash.default.get(normalizedRule, "condition") : hasWhen ? import_lodash.default.get(normalizedRule, "when") : import_filter_group.FLOW_SURFACE_EMPTY_FILTER_GROUP;
401
406
  import_lodash.default.set(
402
407
  normalizedRule,
403
408
  "condition",
404
409
  (0, import_filter_group.normalizeFlowSurfaceCompatibleFilterGroupValue)(
405
- import_lodash.default.get(normalizedRule, "condition"),
406
- `flowSurfaces updateSettings domain '${domainPath}' on '${context.use}' expects FilterGroup or backend query filter like ${import_filter_group.FLOW_SURFACE_FILTER_GROUP_EXAMPLE}`,
410
+ conditionInput,
411
+ `flowSurfaces updateSettings domain '${getLinkageRuleDomainPath(context, path, index, conditionLeaf)}' on '${context.use}' expects FilterGroup or backend query filter like ${import_filter_group.FLOW_SURFACE_FILTER_GROUP_EXAMPLE}`,
407
412
  { strictDateValues: true }
408
413
  )
409
414
  );
415
+ const hasActions = import_lodash.default.has(normalizedRule, "actions");
416
+ const hasThen = import_lodash.default.has(normalizedRule, "then");
417
+ const actionsLeaf = hasActions ? "actions" : hasThen ? "then" : "actions";
418
+ const actionsInput = hasActions ? import_lodash.default.get(normalizedRule, "actions") : hasThen ? import_lodash.default.get(normalizedRule, "then") : [];
419
+ if (!Array.isArray(actionsInput)) {
420
+ (0, import_errors.throwBadRequest)(
421
+ `flowSurfaces updateSettings domain '${getLinkageRuleDomainPath(context, path, index, actionsLeaf)}' on '${context.use}' expects actions/then to be an array`
422
+ );
423
+ }
424
+ import_lodash.default.set(normalizedRule, "actions", actionsInput);
425
+ if (!import_lodash.default.has(normalizedRule, "key")) {
426
+ import_lodash.default.set(normalizedRule, "key", `linkage-rule-${index + 1}`);
427
+ }
428
+ if (!import_lodash.default.has(normalizedRule, "title")) {
429
+ import_lodash.default.set(normalizedRule, "title", `Linkage rule ${index + 1}`);
430
+ }
431
+ if (!import_lodash.default.has(normalizedRule, "enable")) {
432
+ const enabled = import_lodash.default.get(normalizedRule, "enabled");
433
+ import_lodash.default.set(normalizedRule, "enable", typeof enabled === "boolean" ? enabled : true);
434
+ }
435
+ import_lodash.default.unset(normalizedRule, "enabled");
436
+ import_lodash.default.unset(normalizedRule, "when");
437
+ import_lodash.default.unset(normalizedRule, "then");
410
438
  return normalizedRule;
411
439
  });
412
440
  }
441
+ function getLinkageRuleDomainPath(context, path, index, leaf) {
442
+ const basePath = context.groupKey ? `${context.domain}.${context.groupKey}.${path}[${index}]` : `${context.domain}.${path}[${index}]`;
443
+ return leaf ? `${basePath}.${leaf}` : basePath;
444
+ }
413
445
  function isContractDefinedFlowGroup(groupContract) {
414
446
  if (!groupContract) {
415
447
  return false;
@@ -47,6 +47,7 @@ export type FlowSurfaceDefaultActionPopupFieldGroupCandidate = {
47
47
  type FlowSurfaceDefaultActionPopupFieldFilterOptions = {
48
48
  excludeAuditTimestampFields?: boolean;
49
49
  excludeAssociationFields?: boolean;
50
+ excludeRelationBackingForeignKeyFields?: boolean;
50
51
  };
51
52
  type FlowSurfaceDefaultActionPopupFieldsInput = any[] | {
52
53
  fieldPaths?: any[];
@@ -60,6 +61,7 @@ export declare function getFlowSurfaceDefaultActionPopupConfigByUse(use?: string
60
61
  export declare function resolveFlowSurfaceDefaultActionPopupTabTitle(use?: string, currentTitle?: string | null): string;
61
62
  export declare function isFlowSurfaceDefaultActionPopupBusinessField(field: any): boolean;
62
63
  export declare function pickFlowSurfaceDefaultActionPopupFieldPaths(candidates: FlowSurfaceDefaultActionPopupFieldCandidate[], options?: FlowSurfaceDefaultActionPopupFieldFilterOptions): string[];
64
+ export declare function collectFlowSurfaceDefaultActionPopupFieldGroupFieldPaths(fieldGroups: FlowSurfaceDefaultActionPopupFieldGroupCandidate[] | undefined): Set<string>;
63
65
  export declare function pickFlowSurfaceDefaultActionPopupFieldGroups(candidates: FlowSurfaceDefaultActionPopupFieldCandidate[], fieldGroups: FlowSurfaceDefaultActionPopupFieldGroupCandidate[] | undefined, options?: FlowSurfaceDefaultActionPopupFieldFilterOptions): FlowSurfaceDefaultActionPopupFieldGroupCandidate[];
64
66
  export declare function buildFlowSurfaceDefaultActionPopupBlocks(use: string | undefined, fieldsInput: FlowSurfaceDefaultActionPopupFieldsInput): _.Dictionary<string | any[] | Record<string, any> | FlowSurfaceDefaultActionPopupFieldGroupCandidate[] | FlowSurfaceDefaultActionPopupSubmitAction[] | {
65
67
  binding: "currentCollection" | "currentRecord";
@@ -39,6 +39,7 @@ __export(default_action_popup_exports, {
39
39
  FLOW_SURFACE_DEFAULT_ACTION_POPUP_TYPES: () => FLOW_SURFACE_DEFAULT_ACTION_POPUP_TYPES,
40
40
  FLOW_SURFACE_DEFAULT_ACTION_POPUP_USES: () => FLOW_SURFACE_DEFAULT_ACTION_POPUP_USES,
41
41
  buildFlowSurfaceDefaultActionPopupBlocks: () => buildFlowSurfaceDefaultActionPopupBlocks,
42
+ collectFlowSurfaceDefaultActionPopupFieldGroupFieldPaths: () => collectFlowSurfaceDefaultActionPopupFieldGroupFieldPaths,
42
43
  getFlowSurfaceDefaultActionPopupConfigByUse: () => getFlowSurfaceDefaultActionPopupConfigByUse,
43
44
  hasFlowSurfaceInlinePopupBlocks: () => hasFlowSurfaceInlinePopupBlocks,
44
45
  hasFlowSurfaceInlinePopupTemplate: () => hasFlowSurfaceInlinePopupTemplate,
@@ -52,6 +53,7 @@ __export(default_action_popup_exports, {
52
53
  module.exports = __toCommonJS(default_action_popup_exports);
53
54
  var import_lodash = __toESM(require("lodash"));
54
55
  var import_association_interfaces = require("./association-interfaces");
56
+ var import_relation_backing_foreign_key = require("./relation-backing-foreign-key");
55
57
  var import_service_helpers = require("./service-helpers");
56
58
  const DEFAULT_ACTION_POPUP_SYSTEM_FIELD_NAMES = /* @__PURE__ */ new Set(["id", "createdBy", "createdById", "updatedBy", "updatedById"]);
57
59
  const DEFAULT_ACTION_POPUP_SYSTEM_FIELD_INTERFACES = /* @__PURE__ */ new Set([
@@ -214,13 +216,10 @@ function isFlowSurfaceDefaultActionPopupAssociationField(field) {
214
216
  const fieldType = String((0, import_service_helpers.getFieldType)(field) || "").trim();
215
217
  return fieldType === "belongsTo" || fieldType === "hasOne" || fieldType === "hasMany" || fieldType === "belongsToMany";
216
218
  }
217
- function collectFlowSurfaceDefaultActionPopupAssociationForeignKeys(candidates) {
218
- return new Set(
219
- candidates.map((candidate) => candidate == null ? void 0 : candidate.field).filter((field) => (0, import_service_helpers.getFieldType)(field) === "belongsTo").map((field) => {
220
- var _a;
221
- return String((field == null ? void 0 : field.foreignKey) || ((_a = field == null ? void 0 : field.options) == null ? void 0 : _a.foreignKey) || "").trim();
222
- }).filter(Boolean)
223
- );
219
+ function collectFlowSurfaceDefaultActionPopupRelationBackingForeignKeys(candidates) {
220
+ return (0, import_relation_backing_foreign_key.collectRelationBackingForeignKeyNames)({
221
+ getFields: () => candidates.map((candidate) => candidate == null ? void 0 : candidate.field).filter(Boolean)
222
+ });
224
223
  }
225
224
  function isFlowSurfaceDefaultActionPopupAssociationForeignKeyField(field, associationForeignKeys) {
226
225
  const fieldName = String((0, import_service_helpers.getFieldName)(field) || "").trim();
@@ -229,13 +228,26 @@ function isFlowSurfaceDefaultActionPopupAssociationForeignKeyField(field, associ
229
228
  function pickFlowSurfaceDefaultActionPopupFieldPaths(candidates, options = {}) {
230
229
  return filterFlowSurfaceDefaultActionPopupFieldCandidates(candidates, options).map((candidate) => String((candidate == null ? void 0 : candidate.fieldPath) || "").trim()).filter(Boolean);
231
230
  }
231
+ function collectFlowSurfaceDefaultActionPopupFieldGroupFieldPaths(fieldGroups) {
232
+ const fieldPaths = /* @__PURE__ */ new Set();
233
+ import_lodash.default.castArray(fieldGroups || []).forEach((group) => {
234
+ import_lodash.default.castArray((group == null ? void 0 : group.fields) || []).forEach((field) => {
235
+ const fieldPath = getFlowSurfaceDefaultActionPopupFieldGroupFieldPath(field);
236
+ if (fieldPath) {
237
+ fieldPaths.add(fieldPath);
238
+ }
239
+ });
240
+ });
241
+ return fieldPaths;
242
+ }
232
243
  function filterFlowSurfaceDefaultActionPopupFieldCandidates(candidates, options = {}) {
233
- const associationForeignKeys = collectFlowSurfaceDefaultActionPopupAssociationForeignKeys(candidates);
244
+ const associationForeignKeys = collectFlowSurfaceDefaultActionPopupRelationBackingForeignKeys(candidates);
245
+ const excludeRelationBackingForeignKeyFields = options.excludeRelationBackingForeignKeyFields !== false;
234
246
  const preferredCandidates = candidates.filter(
235
- (candidate) => !isFlowSurfaceDefaultActionPopupSystemField(candidate.field) && (!options.excludeAuditTimestampFields || !isFlowSurfaceDefaultActionPopupAuditTimestampField(candidate.field)) && (!options.excludeAssociationFields || !isFlowSurfaceDefaultActionPopupAssociationField(candidate.field)) && !isFlowSurfaceDefaultActionPopupMultiValueAssociationField(candidate.field) && !isFlowSurfaceDefaultActionPopupAssociationForeignKeyField(candidate.field, associationForeignKeys)
247
+ (candidate) => !isFlowSurfaceDefaultActionPopupSystemField(candidate.field) && (!options.excludeAuditTimestampFields || !isFlowSurfaceDefaultActionPopupAuditTimestampField(candidate.field)) && (!options.excludeAssociationFields || !isFlowSurfaceDefaultActionPopupAssociationField(candidate.field)) && !isFlowSurfaceDefaultActionPopupMultiValueAssociationField(candidate.field) && (!excludeRelationBackingForeignKeyFields || !isFlowSurfaceDefaultActionPopupAssociationForeignKeyField(candidate.field, associationForeignKeys))
236
248
  );
237
249
  const fallbackCandidates = candidates.filter(
238
- (candidate) => !isFlowSurfaceDefaultActionPopupTechnicalIdField(candidate.field) && (!options.excludeAuditTimestampFields || !isFlowSurfaceDefaultActionPopupAuditTimestampField(candidate.field)) && (!options.excludeAssociationFields || !isFlowSurfaceDefaultActionPopupAssociationField(candidate.field)) && !isFlowSurfaceDefaultActionPopupMultiValueAssociationField(candidate.field) && !isFlowSurfaceDefaultActionPopupAssociationForeignKeyField(candidate.field, associationForeignKeys)
250
+ (candidate) => !isFlowSurfaceDefaultActionPopupTechnicalIdField(candidate.field) && (!options.excludeAuditTimestampFields || !isFlowSurfaceDefaultActionPopupAuditTimestampField(candidate.field)) && (!options.excludeAssociationFields || !isFlowSurfaceDefaultActionPopupAssociationField(candidate.field)) && !isFlowSurfaceDefaultActionPopupMultiValueAssociationField(candidate.field) && (!excludeRelationBackingForeignKeyFields || !isFlowSurfaceDefaultActionPopupAssociationForeignKeyField(candidate.field, associationForeignKeys))
239
251
  );
240
252
  const baseCandidates = preferredCandidates.length ? preferredCandidates : fallbackCandidates;
241
253
  return baseCandidates.filter((candidate) => String((candidate == null ? void 0 : candidate.fieldPath) || "").trim());
@@ -266,9 +278,10 @@ function normalizeFlowSurfaceDefaultActionPopupFieldGroupField(field, fieldPath)
266
278
  }
267
279
  function pickFlowSurfaceDefaultActionPopupFieldGroups(candidates, fieldGroups, options = {}) {
268
280
  const allowedFieldPaths = new Set(
269
- filterFlowSurfaceDefaultActionPopupFieldCandidates(candidates, options).map(
270
- (candidate) => String((candidate == null ? void 0 : candidate.fieldPath) || "").trim()
271
- )
281
+ filterFlowSurfaceDefaultActionPopupFieldCandidates(candidates, {
282
+ ...options,
283
+ excludeRelationBackingForeignKeyFields: false
284
+ }).map((candidate) => String((candidate == null ? void 0 : candidate.fieldPath) || "").trim())
272
285
  );
273
286
  const usedFieldPaths = /* @__PURE__ */ new Set();
274
287
  return import_lodash.default.castArray(fieldGroups || []).flatMap((group) => {
@@ -351,6 +364,7 @@ function hasFlowSurfaceInlinePopupBlocks(popup) {
351
364
  FLOW_SURFACE_DEFAULT_ACTION_POPUP_TYPES,
352
365
  FLOW_SURFACE_DEFAULT_ACTION_POPUP_USES,
353
366
  buildFlowSurfaceDefaultActionPopupBlocks,
367
+ collectFlowSurfaceDefaultActionPopupFieldGroupFieldPaths,
354
368
  getFlowSurfaceDefaultActionPopupConfigByUse,
355
369
  hasFlowSurfaceInlinePopupBlocks,
356
370
  hasFlowSurfaceInlinePopupTemplate,
@@ -11,13 +11,30 @@ export declare const FLOW_SURFACE_EMPTY_FILTER_GROUP: {
11
11
  items: any[];
12
12
  };
13
13
  export declare const FLOW_SURFACE_FILTER_GROUP_EXAMPLE: string;
14
+ export declare const FLOW_SURFACE_DATE_FILTER_OPERATORS: Set<string>;
14
15
  export declare function assertFlowSurfaceFilterOperator(operator: unknown, path: string): void;
15
- export declare function normalizeFlowSurfaceFilterDateValue(operator: unknown, value: unknown, path: string): unknown;
16
- export declare function normalizeFlowSurfaceStrictFilterDateValue(operator: unknown, value: unknown, path: string): unknown;
16
+ export declare function normalizeFlowSurfaceFilterDateValue(operator: unknown, value: unknown, path: string, options?: {
17
+ allowContextPathValue?: boolean;
18
+ }): unknown;
19
+ export declare function normalizeFlowSurfaceStrictFilterDateValue(operator: unknown, value: unknown, path: string, options?: {
20
+ allowContextPathValue?: boolean;
21
+ }): unknown;
22
+ export declare function isFlowSurfaceDateLikeFieldMeta(value: {
23
+ type?: unknown;
24
+ interface?: unknown;
25
+ } | undefined | null): boolean;
26
+ export declare function normalizeFlowSurfaceDateConditionValue(operator: unknown, value: unknown, path: string, options?: {
27
+ fieldPath?: string;
28
+ fieldType?: unknown;
29
+ fieldInterface?: unknown;
30
+ allowContextPathValue?: boolean;
31
+ }): unknown;
17
32
  export declare function normalizeFlowSurfaceFilterGroupValue(value: any, errorPrefix: string, options?: {
18
33
  strictDateValues?: boolean;
34
+ allowContextPathValue?: boolean;
19
35
  }): any;
20
36
  export declare function normalizeFlowSurfaceCompatibleFilterGroupValue(value: unknown, errorPrefix: string, options?: {
21
37
  strictDateValues?: boolean;
38
+ allowContextPathValue?: boolean;
22
39
  }): any;
23
40
  export declare function assertFlowSurfaceFilterGroupShape(filter: any): void;