@gadmin2n/schematics 0.0.143 → 0.0.145

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 (279) hide show
  1. package/dist/lib/application/files/gadmin2-game-angle-demo/config/.types.d.ts +10 -0
  2. package/dist/lib/application/files/gadmin2-game-angle-demo/config/prisma/approval.prisma +2 -0
  3. package/dist/lib/application/files/gadmin2-game-angle-demo/config/prisma/workflow.prisma +140 -19
  4. package/dist/lib/application/files/gadmin2-game-angle-demo/server/package.json +2 -2
  5. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/data-mngt.seed.ts +0 -2
  6. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflow-node-types.ts +694 -327
  7. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflow-outbox.ts +57 -0
  8. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflow.seed.ts +35 -5
  9. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflows.ts +224 -59
  10. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/codeRuntime/code-executor.spec.ts +23 -0
  11. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/codeRuntime/code-executor.ts +16 -5
  12. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/codeRuntime/code-runtime.controller.spec.ts +98 -0
  13. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/codeRuntime/code-runtime.controller.ts +26 -6
  14. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/codeRuntime/code-runtime.dto.ts +17 -2
  15. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction-runtime.controller.spec.ts +1 -0
  16. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction-runtime.controller.ts +3 -0
  17. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction-runtime.dto.ts +0 -2
  18. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction-signal-outbox.service.spec.ts +30 -0
  19. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction-signal-outbox.service.ts +28 -6
  20. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction.service.spec.ts +63 -0
  21. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-interaction.service.ts +151 -38
  22. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/external-wait.handler.ts +4 -1
  23. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/human-approval.handler.spec.ts +16 -5
  24. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/externalInteraction/human-approval.handler.ts +23 -6
  25. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/httpRequest/http-request-runtime.controller.spec.ts +130 -0
  26. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/httpRequest/http-request-runtime.controller.ts +62 -62
  27. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/httpRequest/http-request-runtime.dto.ts +15 -1
  28. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/httpRequest/http-request-runtime.util.spec.ts +70 -9
  29. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/httpRequest/http-request-runtime.util.ts +31 -7
  30. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/approval-signal-outbox.service.spec.ts +30 -0
  31. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/approval-signal-outbox.service.ts +28 -6
  32. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/approval-subject-source.util.spec.ts +50 -3
  33. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/approval-subject-source.util.ts +26 -3
  34. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/human-approval.dto.ts +53 -47
  35. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/human-approval.errors.ts +0 -1
  36. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/human-approval.service.spec.ts +541 -0
  37. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/human-approval.service.ts +442 -200
  38. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/outbox-retry.util.ts +1 -0
  39. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/runtime/human-approval-runtime.controller.spec.ts +150 -0
  40. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/runtime/human-approval-runtime.controller.ts +56 -40
  41. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/runtime/human-approval-runtime.dto.ts +16 -60
  42. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/integrationConnection/integration-connection.controller.ts +13 -0
  43. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/integrationConnection/integration-connection.service.spec.ts +44 -0
  44. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/integrationConnection/integration-connection.service.ts +6 -0
  45. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/dsl-validate.util.spec.ts +258 -12
  46. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/dsl-validate.util.ts +127 -14
  47. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/manual-workflow-execution.spec.ts +85 -0
  48. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/manual-workflow-execution.ts +108 -0
  49. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/parameter-binding.ts +5 -5
  50. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/temporal.service.spec.ts +96 -25
  51. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/temporal.service.ts +77 -34
  52. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-callable.spec.ts +23 -34
  53. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-callable.ts +0 -21
  54. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-cancellation.spec.ts +245 -0
  55. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-compiler.service.spec.ts +639 -188
  56. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-compiler.service.ts +408 -235
  57. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-compiler.types.ts +1 -3
  58. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-data-edge.util.spec.ts +279 -95
  59. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-data-edge.util.ts +360 -80
  60. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-event-catalog.spec.ts +323 -0
  61. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-execution-idempotency.spec.ts +773 -0
  62. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-execution.dto.ts +7 -13
  63. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-export.dto.ts +0 -16
  64. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-export.service.spec.ts +184 -0
  65. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-export.service.ts +69 -138
  66. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-handle-validator.spec.ts +113 -0
  67. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-handle-validator.ts +59 -13
  68. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-runtime.facade.ts +86 -0
  69. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-switch-config.spec.ts +25 -0
  70. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-switch-config.ts +45 -0
  71. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.controller.spec.ts +78 -43
  72. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.controller.ts +103 -40
  73. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.dto.ts +57 -0
  74. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.module.ts +3 -1
  75. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.service.spec.ts +1000 -240
  76. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.service.ts +2184 -317
  77. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowConfig/node-config-validator.service.spec.ts +279 -2
  78. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowConfig/node-config-validator.service.ts +5 -1
  79. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowConfig/subject-config-validator.service.spec.ts +4 -1
  80. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowConfig/subject-config-validator.service.ts +5 -1
  81. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowConfig/widget-catalog.service.spec.ts +12 -3
  82. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowConfig/widget-catalog.service.ts +10 -1
  83. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.service.spec.ts +2 -24
  84. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.service.ts +3 -70
  85. package/dist/lib/application/files/gadmin2-game-angle-demo/web/package.json +3 -1
  86. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/RowActions.tsx +25 -5
  87. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/WorkflowActionButton.test.tsx +71 -0
  88. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/WorkflowActionButton.tsx +89 -0
  89. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/index.ts +1 -0
  90. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/layout/header.tsx +52 -12
  91. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/config/routeRegistry.tsx +12 -0
  92. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/constants/layout.ts +2 -2
  93. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/dev-shell/AddDataModal.tsx +10 -33
  94. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/dev-shell/AddPageModal.tsx +13 -37
  95. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/dev-shell/DevShell.tsx +55 -7
  96. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/dev-shell/style.css +14 -0
  97. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/helpers/http.ts +10 -0
  98. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/helpers/list.tsx +1 -0
  99. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/helpers/workflowAction.ts +19 -0
  100. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/hooks/index.ts +1 -0
  101. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/hooks/types.ts +3 -1
  102. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/hooks/useDynamicResources.tsx +1 -6
  103. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/hooks/useReferenceUpload.ts +95 -0
  104. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/locales/en/common.json +2 -2
  105. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/locales/en/workflow.json +672 -110
  106. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/locales/zh_CN/common.json +2 -2
  107. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/locales/zh_CN/workflow.json +676 -114
  108. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/plugins/devShellPlugin.ts +13 -1
  109. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agenda/index.tsx +1 -0
  110. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/CanvasEditPage.tsx +38 -4
  111. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/CanvasListPage.tsx +276 -376
  112. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/CanvasAiModal.tsx +126 -6
  113. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/human-approval/DecisionModal.test.tsx +50 -0
  114. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/human-approval/DecisionModal.tsx +48 -11
  115. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/human-approval/inbox.tsx +32 -34
  116. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/RegisterBusinessEventModal.test.tsx +111 -0
  117. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/RegisterBusinessEventModal.tsx +167 -0
  118. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/business-events.css +99 -0
  119. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/detail.test.tsx +106 -0
  120. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/detail.tsx +324 -0
  121. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/index.test.tsx +73 -0
  122. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/business-events/index.tsx +359 -0
  123. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/CanvasZoomControls.tsx +46 -0
  124. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/CreateNodeInstanceDrawer.tsx +9 -1
  125. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/CustomNode.test.tsx +105 -4
  126. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/CustomNode.tsx +90 -48
  127. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/DeletableEdge.tsx +3 -2
  128. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/DslView.test.tsx +259 -0
  129. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/DslView.tsx +167 -103
  130. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/EnhancedFlowRenderer.tsx +142 -140
  131. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ExecutionStatusNode.test.tsx +60 -15
  132. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ExecutionStatusNode.tsx +25 -12
  133. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/FlowRenderer.tsx +364 -200
  134. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NewNodeDefaults.test.tsx +220 -52
  135. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodeOutputSummary.test.tsx +260 -0
  136. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodeOutputSummary.tsx +300 -130
  137. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodePropertyPanel.test.tsx +507 -33
  138. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodePropertyPanel.tsx +630 -592
  139. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ParameterBindingEditor.tsx +67 -70
  140. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ReadonlyNodePanel.test.tsx +90 -0
  141. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ReadonlyNodePanel.tsx +325 -0
  142. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/RunWorkflowModal.test.tsx +52 -0
  143. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/RunWorkflowModal.tsx +14 -9
  144. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/StatusCards.tsx +2 -1
  145. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/VersionPanel.tsx +2 -1
  146. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/WorkflowCodeEditor.test.tsx +42 -0
  147. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/WorkflowCodeEditor.tsx +76 -0
  148. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/WorkflowWorkspaceHeader.tsx +56 -0
  149. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/parameter-binding-editor.css +46 -0
  150. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/workflow-code-editor.css +34 -0
  151. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/connections/ConnectionModal.test.tsx +53 -7
  152. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/connections/ConnectionModal.tsx +123 -62
  153. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/connections/connections.css +85 -0
  154. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/connections/connectionsApi.ts +29 -0
  155. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/connections/index.test.tsx +75 -0
  156. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/connections/index.tsx +69 -36
  157. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/editor.test.tsx +494 -0
  158. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/editor.tsx +665 -194
  159. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/hooks/useReferencedNodeInstanceConfigs.test.tsx +92 -0
  160. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/hooks/useReferencedNodeInstanceConfigs.ts +96 -0
  161. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/hooks/useWorkflowAgent.test.tsx +297 -0
  162. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/hooks/useWorkflowAgent.ts +135 -65
  163. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/index.tsx +53 -42
  164. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/instance-detail.tsx +344 -155
  165. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/instances.tsx +79 -58
  166. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/components/CreateNodeInstanceModal.tsx +123 -144
  167. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/components/NodeInstanceForm.tsx +169 -98
  168. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/components/node-instance-form.css +91 -0
  169. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/index.tsx +54 -31
  170. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/node-config.css +854 -0
  171. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/schema-form/SchemaField.tsx +41 -14
  172. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/schema-form/SchemaForm.test.tsx +75 -0
  173. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/schema-form/SchemaForm.tsx +3 -0
  174. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/schema-form/default-widgets.tsx +20 -2
  175. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/schema-form/widget-registry.tsx +2 -1
  176. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/show.tsx +61 -66
  177. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ApprovalRuleEditor.test.tsx +33 -1
  178. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ApprovalRuleEditor.tsx +47 -15
  179. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/BranchConfigEditors.test.tsx +104 -0
  180. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/CallableInputParametersEditor.tsx +22 -52
  181. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/CodeConfigEditor.test.tsx +72 -0
  182. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/CodeConfigEditor.tsx +78 -70
  183. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/CronTriggerConfigEditor.tsx +569 -0
  184. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/DbExecuteConfigEditor.tsx +130 -0
  185. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/DelayConfigEditor.tsx +100 -0
  186. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/EventTriggerConfigEditor.tsx +620 -0
  187. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ExternalRequestConfigEditor.test.tsx +22 -45
  188. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ExternalRequestConfigEditor.tsx +25 -92
  189. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ExternalWaitConfigEditor.tsx +3 -11
  190. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ForEachConfigEditor.test.tsx +58 -0
  191. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ForEachConfigEditor.tsx +107 -0
  192. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/HttpRequestConfigEditor.test.tsx +212 -31
  193. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/HttpRequestConfigEditor.tsx +214 -304
  194. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/HumanApprovalConfigEditor.test.tsx +175 -40
  195. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/HumanApprovalConfigEditor.tsx +693 -293
  196. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/IfElseConfigEditor.tsx +190 -0
  197. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ManualTriggerConfigEditor.test.tsx +152 -0
  198. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ManualTriggerConfigEditor.tsx +286 -0
  199. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ParallelConfigEditor.tsx +101 -0
  200. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ParameterBindingListEditor.tsx +99 -0
  201. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/SimplifiedNodeEditors.test.tsx +495 -0
  202. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/SubWorkflowConfigEditor.test.tsx +124 -0
  203. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/SubWorkflowConfigEditor.tsx +222 -0
  204. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/SubjectPicker.tsx +2 -4
  205. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/SwitchConfigEditor.tsx +204 -0
  206. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/UserGroupCreateModal.tsx +3 -1
  207. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/UserGroupEditModal.tsx +9 -6
  208. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/callable-workflow.ts +4 -0
  209. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/code-config.css +96 -0
  210. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/event-catalog.api.ts +117 -0
  211. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/http-request-config.css +242 -0
  212. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/human-approval-config.css +194 -0
  213. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/show.tsx +264 -167
  214. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/temporal-tenant/index.tsx +6 -9
  215. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/types/parameter-binding.ts +19 -16
  216. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/types.ts +28 -4
  217. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/useWorkflowFormValidation.test.tsx +59 -0
  218. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/useWorkflowFormValidation.ts +24 -0
  219. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/forEachConnection.test.ts +311 -0
  220. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/forEachConnection.ts +198 -0
  221. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/mainFlowConnection.test.ts +143 -0
  222. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/mainFlowConnection.ts +19 -0
  223. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/newNodeConfig.ts +103 -5
  224. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/removeWorkflowEdges.test.ts +158 -3
  225. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/removeWorkflowEdges.ts +117 -9
  226. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveEffectiveOutput.test.ts +70 -0
  227. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveEffectiveOutput.ts +48 -0
  228. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveLookupPorts.test.ts +55 -0
  229. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveLookupPorts.ts +95 -22
  230. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveOutputs.test.ts +148 -1
  231. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveOutputs.ts +62 -11
  232. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveWorkflowDisplay.test.ts +19 -0
  233. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/resolveWorkflowDisplay.ts +1 -1
  234. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/subWorkflowChange.test.ts +45 -0
  235. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/subWorkflowChange.ts +26 -0
  236. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/validateWorkflowDsl.test.ts +502 -0
  237. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/validateWorkflowDsl.ts +694 -0
  238. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowDateTime.test.ts +27 -0
  239. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowDateTime.ts +33 -0
  240. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowHistory.test.ts +34 -0
  241. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowHistory.ts +52 -0
  242. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowPublishError.test.ts +99 -0
  243. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowPublishError.ts +91 -0
  244. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowSkillPrompt.test.ts +74 -0
  245. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/workflowSkillPrompt.ts +120 -0
  246. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/workflow-ui.css +481 -0
  247. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/styles/index.css +1 -1
  248. package/package.json +1 -1
  249. package/dist/lib/application/files/gadmin2-game-angle-demo/config/ui/WorkflowEventOutbox.ts +0 -62
  250. package/dist/lib/application/files/gadmin2-game-angle-demo/server/scripts/migrate-human-approval-configs.ts +0 -86
  251. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflow-event-trigger.ts +0 -60
  252. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/human-approval.external-decision.spec.ts +0 -183
  253. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/humanApproval/legacy-approval-config-migration.ts +0 -227
  254. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-http-response.spec.ts +0 -82
  255. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-http-response.ts +0 -111
  256. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.controller.spec.ts +0 -54
  257. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.controller.ts +0 -147
  258. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.module.ts +0 -10
  259. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.service.spec.ts +0 -350
  260. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.service.ts +0 -110
  261. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/audit/index.ts +0 -1
  262. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/InstanceRequiredDialog.tsx +0 -106
  263. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/LookupConnectionDialog.test.tsx +0 -45
  264. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/LookupConnectionDialog.tsx +0 -43
  265. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodeTypeBadge.tsx +0 -36
  266. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/hooks/useNodeInstanceLibrary.ts +0 -41
  267. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ApproverSourceEditor.test.tsx +0 -47
  268. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ApproverSourceEditor.tsx +0 -182
  269. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ReturnResultConfigEditor.test.tsx +0 -34
  270. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/ReturnResultConfigEditor.tsx +0 -16
  271. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/approver-source.test.ts +0 -25
  272. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/widgets/approver-source.ts +0 -42
  273. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/lookupConnection.test.ts +0 -208
  274. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/utils/lookupConnection.ts +0 -246
  275. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/create.tsx +0 -111
  276. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/edit.tsx +0 -127
  277. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/index.tsx +0 -4
  278. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/list.tsx +0 -282
  279. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/show.tsx +0 -74
@@ -1,7 +1,10 @@
1
1
  export type DslHandleValidationCode =
2
2
  | 'EXTRA_HANDLE'
3
3
  | 'MISSING_HANDLE'
4
- | 'UNKNOWN_HANDLE';
4
+ | 'UNKNOWN_HANDLE'
5
+ | 'EXTRA_TARGET_HANDLE'
6
+ | 'MISSING_TARGET_HANDLE'
7
+ | 'UNKNOWN_TARGET_HANDLE';
5
8
 
6
9
  export interface DslHandleValidationError {
7
10
  edgeId: string;
@@ -22,6 +25,8 @@ interface DslEdge {
22
25
  source: string;
23
26
  target: string;
24
27
  sourceHandle?: string;
28
+ targetHandle?: string;
29
+ pairId?: string;
25
30
  }
26
31
 
27
32
  interface WorkflowDsl {
@@ -31,6 +36,14 @@ interface WorkflowDsl {
31
36
 
32
37
  export type NodeOutputsMap = Record<string, string[] | null>;
33
38
 
39
+ const RUNTIME_MAIN_FLOW_PORTS: Record<
40
+ string,
41
+ { input: string; output: string }
42
+ > = {
43
+ http_request: { input: 'request-in', output: 'response-out' },
44
+ code: { input: 'data-in', output: 'result-out' },
45
+ };
46
+
34
47
  export function validateWorkflowHandles(
35
48
  dsl: WorkflowDsl,
36
49
  outputsMap: NodeOutputsMap,
@@ -39,16 +52,52 @@ export function validateWorkflowHandles(
39
52
  const nodeMap = new Map(dsl.nodes.map((node) => [node.id, node]));
40
53
 
41
54
  for (const edge of dsl.edges) {
55
+ if (edge.pairId) continue;
42
56
  const sourceNode = nodeMap.get(edge.source);
43
57
  if (!sourceNode || !(sourceNode.type in outputsMap)) continue;
44
58
 
59
+ const targetNode = nodeMap.get(edge.target);
60
+ if (targetNode) {
61
+ const expectedTargetHandle =
62
+ RUNTIME_MAIN_FLOW_PORTS[targetNode.type]?.input;
63
+ if (expectedTargetHandle) {
64
+ if (edge.targetHandle == null || edge.targetHandle === '') {
65
+ errors.push({
66
+ edgeId: edge.id,
67
+ source: edge.source,
68
+ target: edge.target,
69
+ code: 'MISSING_TARGET_HANDLE',
70
+ reason: `Node "${targetNode.type}" requires targetHandle "${expectedTargetHandle}".`,
71
+ });
72
+ } else if (edge.targetHandle !== expectedTargetHandle) {
73
+ errors.push({
74
+ edgeId: edge.id,
75
+ source: edge.source,
76
+ target: edge.target,
77
+ code: 'UNKNOWN_TARGET_HANDLE',
78
+ reason: `Node "${targetNode.type}" targetHandle "${edge.targetHandle}" must be "${expectedTargetHandle}".`,
79
+ });
80
+ }
81
+ } else if (edge.targetHandle != null && edge.targetHandle !== '') {
82
+ errors.push({
83
+ edgeId: edge.id,
84
+ source: edge.source,
85
+ target: edge.target,
86
+ code: 'EXTRA_TARGET_HANDLE',
87
+ reason: `Node "${targetNode.type}" has no named main-flow input handle; edge must not set targetHandle (got "${edge.targetHandle}").`,
88
+ });
89
+ }
90
+ }
91
+
45
92
  const declaredOutputs = outputsMap[sourceNode.type];
46
- const handles =
47
- declaredOutputs === null
48
- ? deriveDynamicOutputs(sourceNode)
49
- : declaredOutputs;
93
+ const runtimeOutput = RUNTIME_MAIN_FLOW_PORTS[sourceNode.type]?.output;
94
+ const handles = runtimeOutput
95
+ ? [runtimeOutput]
96
+ : declaredOutputs === null
97
+ ? deriveDynamicOutputs(sourceNode)
98
+ : declaredOutputs;
50
99
 
51
- if (declaredOutputs !== null && handles.length === 0) {
100
+ if (!runtimeOutput && declaredOutputs !== null && handles.length === 0) {
52
101
  if (edge.sourceHandle != null && edge.sourceHandle !== '') {
53
102
  errors.push({
54
103
  edgeId: edge.id,
@@ -95,13 +144,10 @@ export function validateWorkflowHandles(
95
144
  function deriveDynamicOutputs(node: DslNode): string[] {
96
145
  if (node.type === 'switch') {
97
146
  const cases = node.config?.cases;
98
- if (!Array.isArray(cases)) return [];
99
- return cases
100
- .map((item) => item?.value)
101
- .filter(
102
- (value): value is string =>
103
- typeof value === 'string' && value.length > 0,
104
- );
147
+ const outputs = (Array.isArray(cases) ? cases : [])
148
+ .map((item) => item?.id)
149
+ .filter((id): id is string => typeof id === 'string' && id.length > 0);
150
+ return [...outputs, 'default'];
105
151
  }
106
152
 
107
153
  return [];
@@ -0,0 +1,86 @@
1
+ import { Injectable } from '@nestjs/common';
2
+ import { Prisma } from '@prisma/client';
3
+ import { WorkflowService } from './workflow.service';
4
+
5
+ export interface ExecuteManualWorkflowInput {
6
+ code: string;
7
+ workflow: Record<string, unknown>;
8
+ idempotencyKey?: string;
9
+ creator: string;
10
+ }
11
+
12
+ export interface WorkflowExecutionSummary {
13
+ instanceId: string;
14
+ status: string;
15
+ }
16
+
17
+ export interface WorkflowCancellationSummary {
18
+ instanceId: string;
19
+ status: 'CANCELLED';
20
+ }
21
+
22
+ export interface CancelWorkflowExecutionInput {
23
+ tx: Prisma.TransactionClient;
24
+ instanceId: bigint;
25
+ reason?: string;
26
+ }
27
+
28
+ export interface FindEventTriggeredExecutionInput {
29
+ tx: Prisma.TransactionClient;
30
+ workflowCode: string;
31
+ tableName: string;
32
+ operation: 'INSERT' | 'UPDATE' | 'DELETE';
33
+ primaryKey: Record<string, string | number | boolean>;
34
+ }
35
+
36
+ export interface EventTriggeredExecutionReference {
37
+ instanceId: bigint;
38
+ status: string;
39
+ }
40
+
41
+ @Injectable()
42
+ export class WorkflowRuntimeFacade {
43
+ constructor(private readonly workflows: WorkflowService) {}
44
+
45
+ async executeManualWorkflowByCode(
46
+ input: ExecuteManualWorkflowInput,
47
+ ): Promise<WorkflowExecutionSummary> {
48
+ const result = await this.workflows.executeManualWorkflowByCode(
49
+ input.code,
50
+ input.workflow,
51
+ input.idempotencyKey,
52
+ input.creator,
53
+ );
54
+ return { instanceId: result.instanceId, status: result.status };
55
+ }
56
+
57
+ async cancelExecution(
58
+ input: CancelWorkflowExecutionInput,
59
+ ): Promise<WorkflowCancellationSummary> {
60
+ await this.workflows.cancelExecutionInTransaction(
61
+ input.tx,
62
+ input.instanceId,
63
+ input.reason,
64
+ );
65
+ return { instanceId: input.instanceId.toString(), status: 'CANCELLED' };
66
+ }
67
+
68
+ findEventTriggeredExecution(
69
+ input: FindEventTriggeredExecutionInput,
70
+ ): Promise<EventTriggeredExecutionReference | null> {
71
+ return this.workflows.findEventTriggeredExecutionInTransaction(input.tx, {
72
+ workflowCode: input.workflowCode,
73
+ tableName: input.tableName,
74
+ operation: input.operation,
75
+ primaryKey: input.primaryKey,
76
+ });
77
+ }
78
+
79
+ getExecutionStatus(instanceId: bigint) {
80
+ return this.workflows.getExecutionStatus(instanceId);
81
+ }
82
+
83
+ getWorkflowStatsByCode(code: string) {
84
+ return this.workflows.getWorkflowStatsByCode(code);
85
+ }
86
+ }
@@ -0,0 +1,25 @@
1
+ import { switchCaseValidationError } from './workflow-switch-config';
2
+
3
+ describe('switchCaseValidationError', () => {
4
+ it('rejects numeric values that become equal at runtime', () => {
5
+ expect(
6
+ switchCaseValidationError([
7
+ { id: 'one', valueType: 'NUMBER', value: '1' },
8
+ { id: 'also-one', valueType: 'NUMBER', value: '1.0' },
9
+ ]),
10
+ ).toBe('多路分支不能配置运行时结果相同的重复匹配项');
11
+ });
12
+
13
+ it('rejects values the Worker cannot parse', () => {
14
+ expect(
15
+ switchCaseValidationError([
16
+ { id: 'invalid', valueType: 'NUMBER', value: 'not-a-number' },
17
+ ]),
18
+ ).toBe('多路分支的数字匹配值无效');
19
+ expect(
20
+ switchCaseValidationError([
21
+ { id: 'invalid', valueType: 'BOOLEAN', value: 'yes' },
22
+ ]),
23
+ ).toBe('多路分支的是/否匹配值无效');
24
+ });
25
+ });
@@ -0,0 +1,45 @@
1
+ export function switchCaseValidationError(value: unknown): string | undefined {
2
+ if (!Array.isArray(value)) return undefined;
3
+ const ids = new Set<string>();
4
+ const matches = new Set<string>();
5
+
6
+ for (const rawItem of value) {
7
+ const item = asObject(rawItem);
8
+ const id = String(item.id ?? '');
9
+ if (id === 'default' || ids.has(id))
10
+ return '多路分支的分支标识重复或与“其他情况”冲突';
11
+ ids.add(id);
12
+
13
+ const matchKey = normalizedMatchKey(item);
14
+ if (typeof matchKey !== 'string') return matchKey.error;
15
+ if (matches.has(matchKey))
16
+ return '多路分支不能配置运行时结果相同的重复匹配项';
17
+ matches.add(matchKey);
18
+ }
19
+ return undefined;
20
+ }
21
+
22
+ function normalizedMatchKey(
23
+ item: Record<string, unknown>,
24
+ ): string | { error: string } {
25
+ const valueType = String(item.valueType ?? '');
26
+ const value = String(item.value ?? '');
27
+ if (valueType === 'STRING') return `STRING:${value}`;
28
+ if (valueType === 'BOOLEAN') {
29
+ if (value !== 'true' && value !== 'false')
30
+ return { error: '多路分支的是/否匹配值无效' };
31
+ return `BOOLEAN:${value}`;
32
+ }
33
+ if (valueType === 'NUMBER') {
34
+ if (!value.trim() || !Number.isFinite(Number(value)))
35
+ return { error: '多路分支的数字匹配值无效' };
36
+ return `NUMBER:${Number(value)}`;
37
+ }
38
+ return { error: '多路分支的匹配值类型无效' };
39
+ }
40
+
41
+ function asObject(value: unknown): Record<string, unknown> {
42
+ return value && typeof value === 'object' && !Array.isArray(value)
43
+ ? (value as Record<string, unknown>)
44
+ : {};
45
+ }
@@ -1,59 +1,94 @@
1
1
  import { WorkflowController } from './workflow.controller';
2
2
 
3
- describe('WorkflowController — webhook HTTP response', () => {
4
- it('returns the Workflow body with its configured status and headers', async () => {
5
- const workflowService = {
6
- receiveWebhook: jest.fn().mockResolvedValue({
7
- instanceIds: ['42'],
8
- response: {
9
- statusCode: 201,
10
- headers: {
11
- 'x-workflow-result': 'created',
12
- },
13
- body: {
14
- ticketId: 'T-42',
15
- },
16
- },
3
+ describe('WorkflowController runtime contracts', () => {
4
+ it('starts manual Workflows only through the stable action code contract', async () => {
5
+ const runtime = {
6
+ executeManualWorkflowByCode: jest.fn().mockResolvedValue({
7
+ instanceId: '42',
8
+ status: 'PENDING',
17
9
  }),
18
10
  };
19
11
  const controller = new WorkflowController(
20
- workflowService as never,
21
12
  {} as never,
22
13
  {} as never,
14
+ {} as never,
15
+ runtime as never,
16
+ {} as never,
23
17
  );
24
- const response = {
25
- statusCode: 200,
26
- headers: {} as Record<string, string>,
27
- status(code: number) {
28
- this.statusCode = code;
29
- return this;
30
- },
31
- set(headers: Record<string, string>) {
32
- this.headers = headers;
33
- return this;
34
- },
18
+
19
+ await expect(
20
+ controller.executeAction(
21
+ 'asset-disposal',
22
+ 'request-1',
23
+ { user: { userid: 'tester' } },
24
+ { workflow: { assetId: 'A-1' } },
25
+ ),
26
+ ).resolves.toEqual({ instanceId: '42', status: 'PENDING' });
27
+ expect(runtime.executeManualWorkflowByCode).toHaveBeenCalledWith({
28
+ code: 'asset-disposal',
29
+ workflow: { assetId: 'A-1' },
30
+ idempotencyKey: 'request-1',
31
+ creator: 'tester',
32
+ });
33
+ });
34
+
35
+ it('always returns accepted webhook instance IDs without waiting for a result', async () => {
36
+ const workflowService = {
37
+ receiveWebhook: jest.fn().mockResolvedValue({ instanceIds: ['42'] }),
35
38
  };
39
+ const controller = new WorkflowController(
40
+ workflowService as never,
41
+ {} as never,
42
+ {} as never,
43
+ {} as never,
44
+ {} as never,
45
+ );
36
46
 
37
- const body = await controller.receiveWebhook(
38
- 'create-ticket',
39
- undefined as never,
40
- undefined as never,
41
- {
42
- method: 'POST',
43
- rawBody: Buffer.from('{}'),
44
- headers: {},
45
- } as never,
46
- {},
47
- {},
48
- response as never,
47
+ await expect(
48
+ controller.receiveWebhook(
49
+ 'create-ticket',
50
+ undefined as never,
51
+ undefined as never,
52
+ {
53
+ method: 'POST',
54
+ rawBody: Buffer.from('{}'),
55
+ headers: {},
56
+ } as never,
57
+ {},
58
+ {},
59
+ ),
60
+ ).resolves.toEqual({ instanceIds: ['42'] });
61
+ });
62
+
63
+ it('delegates management cancellation to the concurrency-safe runtime facade', async () => {
64
+ const tx = { transaction: true };
65
+ const prisma = {
66
+ $transaction: jest.fn((callback: (input: typeof tx) => unknown) =>
67
+ callback(tx),
68
+ ),
69
+ };
70
+ const runtime = {
71
+ cancelExecution: jest.fn().mockResolvedValue({
72
+ instanceId: '42',
73
+ status: 'CANCELLED',
74
+ }),
75
+ };
76
+ const controller = new WorkflowController(
77
+ {} as never,
78
+ {} as never,
79
+ {} as never,
80
+ runtime as never,
81
+ prisma as never,
49
82
  );
50
83
 
51
- expect(response.statusCode).toBe(201);
52
- expect(response.headers).toEqual({
53
- 'x-workflow-result': 'created',
84
+ await expect(controller.cancelInstance(42)).resolves.toEqual({
85
+ instanceId: '42',
86
+ status: 'CANCELLED',
54
87
  });
55
- expect(body).toEqual({
56
- ticketId: 'T-42',
88
+ expect(prisma.$transaction).toHaveBeenCalledTimes(1);
89
+ expect(runtime.cancelExecution).toHaveBeenCalledWith({
90
+ tx,
91
+ instanceId: BigInt(42),
57
92
  });
58
93
  });
59
94
  });
@@ -1,3 +1,4 @@
1
+ import { ACGuard } from '@gadmin2n/nest-common';
1
2
  import {
2
3
  Body,
3
4
  Controller,
@@ -12,39 +13,45 @@ import {
12
13
  Query,
13
14
  RawBodyRequest,
14
15
  Req,
15
- Res,
16
16
  UnauthorizedException,
17
17
  UseGuards,
18
18
  } from '@nestjs/common';
19
19
  import { ApiTags } from '@nestjs/swagger';
20
- import { Request, Response } from 'express';
21
- import AuthGuard, { AllowUnauthorizedRequest } from '../../lib/auth.guard';
20
+ import { Request } from 'express';
21
+ import { UseRoles } from 'nest-access-control';
22
+ import { PrismaService } from 'nestjs-prisma';
23
+ import { AllowUnauthorizedRequest } from '../../lib/auth.guard';
22
24
  import { TemporalService } from './temporal.service';
23
25
  import {
24
26
  ApproveInstanceDto,
25
27
  ExecuteWorkflowDto,
26
- SignalWorkflowDto,
28
+ RetryFromNodeDto,
27
29
  } from './workflow-execution.dto';
28
30
  import { ImportPayloadDto } from './workflow-export.dto';
29
31
  import { WorkflowExportService } from './workflow-export.service';
32
+ import { WorkflowRuntimeFacade } from './workflow-runtime.facade';
30
33
  import {
31
34
  CreateWorkflowDto,
32
35
  PublishVersionDto,
36
+ RegisterBusinessEventDto,
33
37
  SaveDraftDto,
34
38
  ToggleEnabledDto,
39
+ UnregisterBusinessEventDto,
35
40
  UpdateWorkflowDto,
41
+ WorkflowInstanceListQueryDto,
36
42
  WorkflowListQueryDto,
37
43
  } from './workflow.dto';
38
44
  import { WorkflowService } from './workflow.service';
39
45
 
40
46
  @ApiTags('workflow')
41
- @UseGuards(AuthGuard)
42
47
  @Controller('workflow')
43
48
  export class WorkflowController {
44
49
  constructor(
45
50
  private readonly workflowService: WorkflowService,
46
51
  private readonly temporalService: TemporalService,
47
52
  private readonly workflowExportService: WorkflowExportService,
53
+ private readonly workflowRuntime: WorkflowRuntimeFacade,
54
+ private readonly prisma: PrismaService,
48
55
  ) {}
49
56
 
50
57
  @Get()
@@ -58,6 +65,17 @@ export class WorkflowController {
58
65
  });
59
66
  }
60
67
 
68
+ @Post('event-catalog/register')
69
+ @UseGuards(ACGuard)
70
+ @UseRoles({
71
+ resource: 'workflowEventRegistration',
72
+ action: 'create',
73
+ possession: 'any',
74
+ })
75
+ registerBusinessEvent(@Body() dto: RegisterBusinessEventDto, @Req() req) {
76
+ return this.workflowService.registerBusinessEvent(dto, req.user.userid);
77
+ }
78
+
61
79
  @Get('overview')
62
80
  getOverview() {
63
81
  return this.workflowService.getOverview();
@@ -73,6 +91,44 @@ export class WorkflowController {
73
91
  return this.workflowService.findExternalInteractionOptions();
74
92
  }
75
93
 
94
+ @Get('event-catalog/overview')
95
+ findBusinessEventCatalogOverview() {
96
+ return this.workflowService.findBusinessEventCatalogOverview();
97
+ }
98
+
99
+ @Get('event-catalog/sources')
100
+ findBusinessEventSources() {
101
+ return this.workflowService.findBusinessEventSources();
102
+ }
103
+
104
+ @Get('event-catalog/:registrationCode/instances')
105
+ findBusinessEventInstances(
106
+ @Param('registrationCode') registrationCode: string,
107
+ @Query() query: WorkflowInstanceListQueryDto,
108
+ ) {
109
+ return this.workflowService.findBusinessEventInstances(registrationCode, {
110
+ status: query.status,
111
+ skip: query.skip,
112
+ limit: query.limit,
113
+ });
114
+ }
115
+
116
+ @Post('event-catalog/unregister')
117
+ @UseGuards(ACGuard)
118
+ @UseRoles({
119
+ resource: 'workflowEventRegistration',
120
+ action: 'delete',
121
+ possession: 'any',
122
+ })
123
+ unregisterBusinessEvent(@Body() dto: UnregisterBusinessEventDto) {
124
+ return this.workflowService.unregisterBusinessEvent(dto.registrationCode);
125
+ }
126
+
127
+ @Get('event-catalog')
128
+ findBusinessEventCatalog() {
129
+ return this.workflowService.findBusinessEventCatalog();
130
+ }
131
+
76
132
  // ─── Export/Import Endpoints ──────────────────────────────────────────────────
77
133
 
78
134
  @Post(':id/export-token')
@@ -167,12 +223,12 @@ export class WorkflowController {
167
223
  @Get(':id/instances')
168
224
  getInstances(
169
225
  @Param('id', ParseIntPipe) id: number,
170
- @Query() query: { status?: string; skip?: string; limit?: string },
226
+ @Query() query: WorkflowInstanceListQueryDto,
171
227
  ) {
172
228
  return this.workflowService.getInstances(BigInt(id), {
173
229
  status: query.status,
174
- skip: query.skip ? Number(query.skip) : undefined,
175
- limit: query.limit ? Number(query.limit) : undefined,
230
+ skip: query.skip,
231
+ limit: query.limit,
176
232
  });
177
233
  }
178
234
 
@@ -183,30 +239,45 @@ export class WorkflowController {
183
239
 
184
240
  // ─── Execution Endpoints ──────────────────────────────────────────────────────
185
241
 
186
- @Post(':id/execute')
187
- async execute(
188
- @Param('id', ParseIntPipe) id: number,
242
+ @Post('actions/:code/execute')
243
+ @UseGuards(ACGuard)
244
+ @UseRoles({
245
+ resource: 'workflowExecution',
246
+ action: 'create',
247
+ possession: 'any',
248
+ })
249
+ async executeAction(
250
+ @Param('code') code: string,
251
+ @Headers('idempotency-key') idempotencyKey: string | undefined,
189
252
  @Req() req,
190
253
  @Body() dto: ExecuteWorkflowDto,
191
254
  ) {
192
- return this.workflowService.executeWorkflow(
193
- BigInt(id),
194
- dto,
195
- req.user.userid,
196
- this.temporalService,
197
- );
255
+ return this.workflowRuntime.executeManualWorkflowByCode({
256
+ code,
257
+ workflow: dto.workflow ?? {},
258
+ idempotencyKey,
259
+ creator: req.user.userid,
260
+ });
198
261
  }
199
262
 
200
263
  @Get('instance/:instanceId')
201
- getInstanceDetail(@Param('instanceId', ParseIntPipe) instanceId: number) {
202
- return this.workflowService.getInstanceDetail(BigInt(instanceId));
264
+ getInstanceDetail(
265
+ @Param('instanceId', ParseIntPipe) instanceId: number,
266
+ @Req() req,
267
+ ) {
268
+ return this.workflowService.getInstanceDetail(
269
+ BigInt(instanceId),
270
+ req.user.userid,
271
+ );
203
272
  }
204
273
 
205
274
  @Post('instance/:instanceId/cancel')
206
275
  async cancelInstance(@Param('instanceId', ParseIntPipe) instanceId: number) {
207
- return this.workflowService.cancelInstance(
208
- BigInt(instanceId),
209
- this.temporalService,
276
+ return this.prisma.$transaction((tx) =>
277
+ this.workflowRuntime.cancelExecution({
278
+ tx,
279
+ instanceId: BigInt(instanceId),
280
+ }),
210
281
  );
211
282
  }
212
283
 
@@ -222,14 +293,16 @@ export class WorkflowController {
222
293
  );
223
294
  }
224
295
 
225
- @Post('instance/:instanceId/signal')
226
- async signalInstance(
296
+ @Post('instance/:instanceId/retry-from-node')
297
+ async retryInstanceFromNode(
227
298
  @Param('instanceId', ParseIntPipe) instanceId: number,
228
- @Body() dto: SignalWorkflowDto,
299
+ @Body() dto: RetryFromNodeDto,
300
+ @Req() req,
229
301
  ) {
230
- return this.workflowService.signalInstance(
302
+ return this.workflowService.retryInstanceFromNode(
231
303
  BigInt(instanceId),
232
- dto,
304
+ dto.nodeId,
305
+ req.user.userid,
233
306
  this.temporalService,
234
307
  );
235
308
  }
@@ -254,8 +327,7 @@ export class WorkflowController {
254
327
  * Request verification is configured by the matching trigger. Existing triggers
255
328
  * require HMAC-SHA256; direct triggers accept callers that cannot sign requests.
256
329
  *
257
- * By default returns 202 Accepted with the created instance IDs. A trigger in
258
- * function mode keeps this request open and returns the Workflow result instead.
330
+ * Returns 202 Accepted with all created instance IDs.
259
331
  */
260
332
  @Post('webhook/:path')
261
333
  @HttpCode(202)
@@ -267,9 +339,8 @@ export class WorkflowController {
267
339
  @Req() req: RawBodyRequest<Request>,
268
340
  @Body() body: any,
269
341
  @Query() query: any,
270
- @Res({ passthrough: true }) response: Response,
271
- ): Promise<unknown> {
272
- const result = await this.workflowService.receiveWebhook({
342
+ ): Promise<{ instanceIds: string[] }> {
343
+ return this.workflowService.receiveWebhook({
273
344
  path,
274
345
  method: req.method,
275
346
  signatureHeader: signature,
@@ -279,13 +350,5 @@ export class WorkflowController {
279
350
  headers: req.headers as Record<string, any>,
280
351
  query,
281
352
  });
282
- if (!result.response) {
283
- response.status(202);
284
- return { instanceIds: result.instanceIds };
285
- }
286
-
287
- response.status(result.response.statusCode);
288
- response.set(result.response.headers);
289
- return result.response.body;
290
353
  }
291
354
  }