@gadmin2n/schematics 0.0.72 → 0.0.75

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 (173) hide show
  1. package/dist/index.d.ts +2 -0
  2. package/dist/index.js +2 -0
  3. package/dist/lib/application/files/gadmin2-game-angle-demo/config/prisma/job.prisma +62 -0
  4. package/dist/lib/application/files/gadmin2-game-angle-demo/config/prisma/system.prisma +0 -21
  5. package/dist/lib/application/files/gadmin2-game-angle-demo/config/prisma/workflow.prisma +171 -0
  6. package/dist/lib/application/files/gadmin2-game-angle-demo/config/ui/AgendaJob.ts +60 -0
  7. package/dist/lib/application/files/gadmin2-game-angle-demo/config/ui/Event.ts +1 -1
  8. package/dist/lib/application/files/gadmin2-game-angle-demo/config/ui/WorkflowEventOutbox.ts +62 -0
  9. package/dist/lib/application/files/gadmin2-game-angle-demo/config/ui/WorkflowNodeInstance.ts +62 -0
  10. package/dist/lib/application/files/gadmin2-game-angle-demo/config/ui/WorkflowNodeType.ts +62 -0
  11. package/dist/lib/application/files/gadmin2-game-angle-demo/server/.env +5 -0
  12. package/dist/lib/application/files/gadmin2-game-angle-demo/server/package.json +5 -4
  13. package/dist/lib/application/files/gadmin2-game-angle-demo/server/prisma.config.ts +14 -7
  14. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/index.ts +4 -0
  15. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/permissions.ts +49 -3
  16. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflow-node-types.ts +746 -0
  17. package/dist/lib/application/files/gadmin2-game-angle-demo/server/seed/workflows.ts +786 -0
  18. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/agenda/agenda.controller.ts +6 -0
  19. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/agenda/agenda.service.ts +79 -0
  20. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/agendaJob/agendaJob.controller.spec.ts +20 -0
  21. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/agendaJob/agendaJob.controller.ts +145 -0
  22. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/agendaJob/agendaJob.module.ts +10 -0
  23. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/{canvas/canvas.service.spec.ts → agendaJob/agendaJob.service.spec.ts} +71 -65
  24. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/agendaJob/agendaJob.service.ts +83 -0
  25. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/index.ts +2 -1
  26. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/temporal.module.ts +9 -0
  27. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/temporal.service.ts +100 -0
  28. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-execution.dto.ts +19 -0
  29. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-export.dto.ts +43 -0
  30. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-export.service.ts +317 -0
  31. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-node-type.controller.ts +16 -0
  32. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow-node-type.service.ts +13 -0
  33. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.controller.ts +220 -0
  34. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.dto.ts +82 -0
  35. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.module.ts +16 -0
  36. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflow/workflow.service.ts +505 -0
  37. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.controller.spec.ts +22 -0
  38. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.controller.ts +147 -0
  39. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.module.ts +10 -0
  40. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.service.spec.ts +356 -0
  41. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowEventOutbox/workflowEventOutbox.service.ts +110 -0
  42. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.controller.spec.ts +22 -0
  43. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.controller.ts +216 -0
  44. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.module.ts +10 -0
  45. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.service.spec.ts +356 -0
  46. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeInstance/workflowNodeInstance.service.ts +168 -0
  47. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeType/workflowNodeType.controller.spec.ts +22 -0
  48. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeType/workflowNodeType.controller.ts +199 -0
  49. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeType/workflowNodeType.module.ts +10 -0
  50. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeType/workflowNodeType.service.spec.ts +348 -0
  51. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/modules/workflowNodeType/workflowNodeType.service.ts +106 -0
  52. package/dist/lib/application/files/gadmin2-game-angle-demo/server/yarn.lock +579 -1082
  53. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/README.md +278 -0
  54. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/config/development-sql.yaml +5 -0
  55. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/docker-compose.yml +25 -0
  56. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/package.json +13 -0
  57. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/sql/create-event-trigger.sql +87 -0
  58. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/.env +7 -0
  59. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/SANDBOX.md +122 -0
  60. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/package-lock.json +4285 -0
  61. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/package.json +28 -0
  62. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/__tests__/activities/code-execute.test.ts +44 -0
  63. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/__tests__/activities/http-request.test.ts +87 -0
  64. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/__tests__/helpers.test.ts +225 -0
  65. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/__tests__/node-type-consistency.test.ts +101 -0
  66. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/code-execute.ts +51 -0
  67. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/db-execute.ts +85 -0
  68. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/db-query.ts +35 -0
  69. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/http-request.ts +54 -0
  70. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/index.ts +6 -0
  71. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/reporting.ts +62 -0
  72. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/activities/send-notification.ts +47 -0
  73. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/config.ts +13 -0
  74. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/dsl/condition.ts +101 -0
  75. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/dsl/context.ts +58 -0
  76. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/dsl/graph.ts +184 -0
  77. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/dsl/helpers.ts +133 -0
  78. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/dsl/node-types.ts +57 -0
  79. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/dsl/types.ts +77 -0
  80. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/index.ts +36 -0
  81. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/outbox-poller.ts +226 -0
  82. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/src/workflows/dsl-workflow.ts +411 -0
  83. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/tsconfig.json +19 -0
  84. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/vitest.config.ts +8 -0
  85. package/dist/lib/application/files/gadmin2-game-angle-demo/temporal/worker/yarn.lock +1905 -0
  86. package/dist/lib/application/files/gadmin2-game-angle-demo/web/package-lock.json +17555 -0
  87. package/dist/lib/application/files/gadmin2-game-angle-demo/web/package.json +5 -2
  88. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/App.tsx +1 -0
  89. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/layout/sider.tsx +5 -1
  90. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/layout/title.tsx +1 -1
  91. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/config/routeRegistry.tsx +63 -0
  92. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/dev-shell/DevShell.tsx +91 -2
  93. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/helpers/list.tsx +48 -2
  94. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/helpers/show.tsx +43 -2
  95. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/locales/en/common.json +14 -9
  96. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/locales/zh_CN/common.json +14 -9
  97. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agenda/index.tsx +309 -56
  98. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agenda/show.tsx +1 -3
  99. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agendaJob/create.tsx +108 -0
  100. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agendaJob/edit.tsx +124 -0
  101. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agendaJob/index.tsx +4 -0
  102. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agendaJob/list.tsx +245 -0
  103. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/agendaJob/show.tsx +70 -0
  104. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/CanvasListPage.tsx +0 -1
  105. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/CanvasPage.tsx +160 -2
  106. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/CanvasToolbar.tsx +120 -148
  107. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/CodeFloatWindow.tsx +74 -181
  108. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/LivePreview.tsx +15 -13
  109. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/canvasConfigRegistry.tsx +2 -2
  110. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/canvasContextMenuRegistry.tsx +338 -3
  111. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/canvasDefaults.ts +18 -17
  112. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/BarChartDataSourceModal.tsx +10 -4
  113. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/LineChartDataSourceModal.tsx +10 -4
  114. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/{ChartViewerConfigModal.tsx → MultiChartConfigModal.tsx} +30 -18
  115. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/MultiChartDataSourceModal.tsx +427 -0
  116. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/NumCardDataSourceModal.tsx +10 -4
  117. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/PromptModal.tsx +6 -14
  118. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/RadarChartDataSourceModal.tsx +10 -4
  119. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/TableDataSourceModal.tsx +10 -4
  120. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/components/canvasModalProps.ts +24 -0
  121. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/canvas/demos.ts +45 -63
  122. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/CustomNode.tsx +99 -0
  123. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ExportModal.tsx +87 -0
  124. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/FlowRenderer.tsx +322 -0
  125. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/ImportModal.tsx +175 -0
  126. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodeEditModal.tsx +60 -0
  127. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/NodePropertyPanel.tsx +1150 -0
  128. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/RunWorkflowModal.tsx +101 -0
  129. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/StatusCards.tsx +198 -0
  130. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/components/VersionPanel.tsx +81 -0
  131. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/editor.tsx +566 -0
  132. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/hooks/useWorkflowAgent.ts +224 -0
  133. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/index.tsx +524 -0
  134. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/instance-detail.tsx +343 -0
  135. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/instances.tsx +243 -0
  136. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/components/CreateNodeInstanceModal.tsx +363 -0
  137. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/components/DynamicConfigForm.tsx +154 -0
  138. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/components/NodeInstanceForm.tsx +176 -0
  139. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/create.tsx +77 -0
  140. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/edit.tsx +112 -0
  141. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/index.tsx +305 -0
  142. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/node-instances/show.tsx +282 -0
  143. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/show.tsx +469 -0
  144. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflow/types.ts +92 -0
  145. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/create.tsx +111 -0
  146. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/edit.tsx +127 -0
  147. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/index.tsx +4 -0
  148. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/list.tsx +254 -0
  149. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/routes/workflowEventOutbox/show.tsx +74 -0
  150. package/dist/lib/application/files/gadmin2-game-angle-demo/web/yarn.lock +1501 -1199
  151. package/package.json +1 -1
  152. package/dist/lib/application/files/gadmin2-game-angle-demo/server/src/app.controller.spec.ts +0 -22
  153. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/BarChart/index.tsx +0 -896
  154. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/ChartSwitcher/index.tsx +0 -219
  155. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/ChartViewer/index.tsx +0 -159
  156. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/Filter/index.tsx +0 -192
  157. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/LineChart/index.tsx +0 -1034
  158. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/NumCard/NumCard.module.css +0 -8
  159. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/NumCard/index.tsx +0 -509
  160. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/NumLineCard/index.tsx +0 -66
  161. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/PieChart/index.tsx +0 -552
  162. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/RadarChart/index.tsx +0 -263
  163. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/Section/index.tsx +0 -35
  164. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/Table/index.tsx +0 -207
  165. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/TreemapChart/index.tsx +0 -382
  166. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/WorldMap/index.tsx +0 -135
  167. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/chart-constants.ts +0 -53
  168. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/icon/InfoIcon.tsx +0 -8
  169. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/icon/index.ts +0 -1
  170. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/map/config.ts +0 -31
  171. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/map/nameMap.json +0 -9
  172. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/map/world.geo.json +0 -39349
  173. package/dist/lib/application/files/gadmin2-game-angle-demo/web/src/components/canvas/metric-info-tooltip/index.tsx +0 -19
@@ -0,0 +1,77 @@
1
+ import React, { useEffect, useState } from 'react';
2
+ import { Form, Spin, message } from 'antd';
3
+ import { useNavigate } from 'react-router-dom';
4
+ import { customRequest } from 'helpers/http';
5
+ import { NodeInstanceForm } from './components/NodeInstanceForm';
6
+ import type { WorkflowNodeType } from '../types';
7
+
8
+ export default function NodeInstanceCreatePage() {
9
+ const navigate = useNavigate();
10
+ const [form] = Form.useForm();
11
+ const [nodeTypes, setNodeTypes] = useState<WorkflowNodeType[]>([]);
12
+ const [loading, setLoading] = useState(true);
13
+ const [submitting, setSubmitting] = useState(false);
14
+
15
+ useEffect(() => {
16
+ customRequest<WorkflowNodeType[]>('workflow-node-types', 'GET')
17
+ .then((res) => {
18
+ setNodeTypes(res);
19
+ setLoading(false);
20
+ })
21
+ .catch(() => setLoading(false));
22
+ }, []);
23
+
24
+ // Reset config when nodeType changes
25
+ const selectedNodeTypeId = Form.useWatch('nodeTypeId', form);
26
+ useEffect(() => {
27
+ if (selectedNodeTypeId) {
28
+ form.setFieldValue('config', undefined);
29
+ }
30
+ }, [selectedNodeTypeId, form]);
31
+
32
+ async function handleSubmit() {
33
+ try {
34
+ const values = await form.validateFields();
35
+ setSubmitting(true);
36
+ await customRequest('workflowNodeInstance/createOne', 'POST', {
37
+ nodeType: { connect: { id: Number(values.nodeTypeId) } },
38
+ name: values.name,
39
+ description: values.description || null,
40
+ config: JSON.stringify(values.config ?? {}),
41
+ isEnabled: values.isEnabled ?? true,
42
+ creator: '',
43
+ });
44
+ message.success('Created successfully');
45
+ navigate('/admin/workflow/node-instances');
46
+ } catch (e: any) {
47
+ if (e?.errorFields) return;
48
+ message.error(e?.message ?? 'Create failed');
49
+ } finally {
50
+ setSubmitting(false);
51
+ }
52
+ }
53
+
54
+ if (loading) {
55
+ return (
56
+ <div
57
+ style={{ display: 'flex', justifyContent: 'center', paddingTop: 120 }}
58
+ >
59
+ <Spin size="large" />
60
+ </div>
61
+ );
62
+ }
63
+
64
+ return (
65
+ <Form.Provider>
66
+ <NodeInstanceForm
67
+ form={form}
68
+ nodeTypes={nodeTypes}
69
+ title="Create Node Instance"
70
+ submitText="Create"
71
+ submitting={submitting}
72
+ onSubmit={handleSubmit}
73
+ onBack={() => navigate('/admin/workflow/node-instances')}
74
+ />
75
+ </Form.Provider>
76
+ );
77
+ }
@@ -0,0 +1,112 @@
1
+ import React, { useCallback, useEffect, useState } from 'react';
2
+ import { Form, Spin, message } from 'antd';
3
+ import { useNavigate, useParams } from 'react-router-dom';
4
+ import { customRequest } from 'helpers/http';
5
+ import { NodeInstanceForm } from './components/NodeInstanceForm';
6
+ import type { WorkflowNodeType } from '../types';
7
+
8
+ interface NodeInstance {
9
+ id: string;
10
+ nodeTypeId: string;
11
+ name: string;
12
+ description: string | null;
13
+ config: Record<string, any>;
14
+ isEnabled: boolean;
15
+ }
16
+
17
+ export default function NodeInstanceEditPage() {
18
+ const { id } = useParams<{ id: string }>();
19
+ const navigate = useNavigate();
20
+ const [form] = Form.useForm();
21
+ const [nodeTypes, setNodeTypes] = useState<WorkflowNodeType[]>([]);
22
+ const [loading, setLoading] = useState(true);
23
+ const [submitting, setSubmitting] = useState(false);
24
+ const [record, setRecord] = useState<NodeInstance | null>(null);
25
+
26
+ const fetchData = useCallback(async () => {
27
+ try {
28
+ const [ntRes, recordRes] = await Promise.all([
29
+ customRequest<WorkflowNodeType[]>('workflow-node-types', 'GET'),
30
+ customRequest<NodeInstance>(
31
+ `workflowNodeInstance/findUnique/${id}`,
32
+ 'POST',
33
+ {
34
+ id: true,
35
+ nodeTypeId: true,
36
+ name: true,
37
+ description: true,
38
+ config: true,
39
+ isEnabled: true,
40
+ nodeType: {
41
+ select: { label: true, category: true, configSchema: true },
42
+ },
43
+ },
44
+ ),
45
+ ]);
46
+ setNodeTypes(ntRes);
47
+ setRecord(recordRes);
48
+ form.setFieldsValue({
49
+ nodeTypeId: String(recordRes.nodeTypeId),
50
+ name: recordRes.name,
51
+ description: recordRes.description ?? '',
52
+ isEnabled: recordRes.isEnabled,
53
+ config:
54
+ typeof recordRes.config === 'string'
55
+ ? JSON.parse(recordRes.config)
56
+ : recordRes.config,
57
+ });
58
+ } catch (e: any) {
59
+ message.error(e?.message ?? 'Failed to load');
60
+ } finally {
61
+ setLoading(false);
62
+ }
63
+ }, [id, form]);
64
+
65
+ useEffect(() => {
66
+ fetchData();
67
+ }, [fetchData]);
68
+
69
+ async function handleSubmit() {
70
+ try {
71
+ const values = await form.validateFields();
72
+ setSubmitting(true);
73
+ await customRequest(`workflowNodeInstance/updateUnique/${id}`, 'PATCH', {
74
+ nodeTypeId: Number(values.nodeTypeId),
75
+ name: values.name,
76
+ description: values.description || null,
77
+ config: JSON.stringify(values.config ?? {}),
78
+ isEnabled: values.isEnabled ?? true,
79
+ });
80
+ message.success('Updated successfully');
81
+ navigate('/admin/workflow/node-instances');
82
+ } catch (e: any) {
83
+ if (e?.errorFields) return;
84
+ message.error(e?.message ?? 'Update failed');
85
+ } finally {
86
+ setSubmitting(false);
87
+ }
88
+ }
89
+
90
+ if (loading) {
91
+ return (
92
+ <div
93
+ style={{ display: 'flex', justifyContent: 'center', paddingTop: 120 }}
94
+ >
95
+ <Spin size="large" />
96
+ </div>
97
+ );
98
+ }
99
+
100
+ return (
101
+ <NodeInstanceForm
102
+ form={form}
103
+ nodeTypes={nodeTypes}
104
+ title={record?.name || 'Edit Node Instance'}
105
+ submitText="Save"
106
+ submitting={submitting}
107
+ disableNodeType
108
+ onSubmit={handleSubmit}
109
+ onBack={() => navigate('/admin/workflow/node-instances')}
110
+ />
111
+ );
112
+ }
@@ -0,0 +1,305 @@
1
+ import React, { useCallback, useEffect, useRef, useState } from 'react';
2
+ import {
3
+ Button,
4
+ Card,
5
+ Input,
6
+ Popconfirm,
7
+ Select,
8
+ Space,
9
+ Switch,
10
+ Table,
11
+ Tag,
12
+ Tooltip,
13
+ Typography,
14
+ message,
15
+ } from 'antd';
16
+ import {
17
+ DeleteOutlined,
18
+ EditOutlined,
19
+ EyeOutlined,
20
+ PlusOutlined,
21
+ ReloadOutlined,
22
+ } from '@ant-design/icons';
23
+ import { useSearchParams, useNavigate } from 'react-router-dom';
24
+ import { customRequest } from 'helpers/http';
25
+ import type { WorkflowNodeType } from '../types';
26
+
27
+ const { Title } = Typography;
28
+ const PAGE_SIZE = 20;
29
+
30
+ interface NodeInstance {
31
+ id: string;
32
+ nodeTypeId: string;
33
+ name: string;
34
+ description: string | null;
35
+ config: Record<string, any>;
36
+ isEnabled: boolean;
37
+ creator: string;
38
+ createdAt: string;
39
+ updatedAt: string;
40
+ nodeType?: { label: string; category: string };
41
+ }
42
+
43
+ export default function NodeInstanceListPage() {
44
+ const navigate = useNavigate();
45
+ const [data, setData] = useState<NodeInstance[]>([]);
46
+ const [total, setTotal] = useState(0);
47
+ const [loading, setLoading] = useState(false);
48
+ const [nodeTypes, setNodeTypes] = useState<WorkflowNodeType[]>([]);
49
+
50
+ const [searchParams, setSearchParams] = useSearchParams();
51
+ const filterNodeType = searchParams.get('nodeTypeId') || undefined;
52
+ const filterName = searchParams.get('name') || undefined;
53
+ const page = Number(searchParams.get('page')) || 1;
54
+
55
+ const debounceRef = useRef<ReturnType<typeof setTimeout> | null>(null);
56
+
57
+ const updateParams = useCallback(
58
+ (updates: Record<string, string | undefined>) => {
59
+ setSearchParams(
60
+ (prev) => {
61
+ const next = new URLSearchParams(prev);
62
+ for (const [k, v] of Object.entries(updates)) {
63
+ if (v) next.set(k, v);
64
+ else next.delete(k);
65
+ }
66
+ return next;
67
+ },
68
+ { replace: true },
69
+ );
70
+ },
71
+ [setSearchParams],
72
+ );
73
+
74
+ const fetchData = useCallback(async () => {
75
+ setLoading(true);
76
+ try {
77
+ const where: Record<string, any> = {};
78
+ if (filterNodeType) where.nodeTypeId = Number(filterNodeType);
79
+ if (filterName) where.name = { contains: filterName };
80
+
81
+ const res = await customRequest<{
82
+ data: NodeInstance[];
83
+ meta: { itemCount: number };
84
+ }>('workflowNodeInstance/findMany', 'POST', {
85
+ skip: (page - 1) * PAGE_SIZE,
86
+ take: PAGE_SIZE,
87
+ where,
88
+ orderBy: { id: 'desc' },
89
+ include: { nodeType: { select: { label: true, category: true } } },
90
+ });
91
+ setData(res.data);
92
+ setTotal(res.meta.itemCount);
93
+ } catch (e: any) {
94
+ message.error(e?.message ?? 'Failed to fetch data');
95
+ } finally {
96
+ setLoading(false);
97
+ }
98
+ }, [page, filterNodeType, filterName]);
99
+
100
+ useEffect(() => {
101
+ fetchData();
102
+ }, [fetchData]);
103
+
104
+ // Load node types for filter
105
+ useEffect(() => {
106
+ customRequest<WorkflowNodeType[]>('workflow-node-types', 'GET')
107
+ .then(setNodeTypes)
108
+ .catch(() => {});
109
+ }, []);
110
+
111
+ async function handleToggleEnabled(record: NodeInstance) {
112
+ try {
113
+ await customRequest(
114
+ `workflowNodeInstance/updateUnique/${record.id}`,
115
+ 'PATCH',
116
+ {
117
+ isEnabled: !record.isEnabled,
118
+ },
119
+ );
120
+ message.success(record.isEnabled ? 'Disabled' : 'Enabled');
121
+ fetchData();
122
+ } catch (e: any) {
123
+ message.error(e?.message ?? 'Update failed');
124
+ }
125
+ }
126
+
127
+ async function handleDelete(id: string) {
128
+ try {
129
+ await customRequest(`workflowNodeInstance/deleteUnique/${id}`, 'DELETE');
130
+ message.success('Deleted');
131
+ fetchData();
132
+ } catch (e: any) {
133
+ message.error(e?.message ?? 'Delete failed');
134
+ }
135
+ }
136
+
137
+ const columns = [
138
+ {
139
+ title: '',
140
+ dataIndex: 'isEnabled',
141
+ key: 'isEnabled',
142
+ width: 50,
143
+ render: (val: boolean, record: NodeInstance) => (
144
+ <Popconfirm
145
+ title={
146
+ val ? 'Disable this node instance?' : 'Enable this node instance?'
147
+ }
148
+ onConfirm={() => handleToggleEnabled(record)}
149
+ okText="Confirm"
150
+ cancelText="Cancel"
151
+ >
152
+ <Switch size="small" checked={val} />
153
+ </Popconfirm>
154
+ ),
155
+ },
156
+ {
157
+ title: 'Name',
158
+ dataIndex: 'name',
159
+ key: 'name',
160
+ render: (name: string, record: NodeInstance) => (
161
+ <a
162
+ onClick={() =>
163
+ navigate(`/admin/workflow/node-instances/show/${record.id}`)
164
+ }
165
+ >
166
+ {name}
167
+ </a>
168
+ ),
169
+ },
170
+ {
171
+ title: 'Node Type',
172
+ key: 'nodeType',
173
+ render: (_: any, record: NodeInstance) => (
174
+ <Tag>{record.nodeType?.label ?? '—'}</Tag>
175
+ ),
176
+ },
177
+ {
178
+ title: 'Updated',
179
+ dataIndex: 'updatedAt',
180
+ key: 'updatedAt',
181
+ width: 150,
182
+ render: (v: string) => (
183
+ <Tooltip title={new Date(v).toLocaleString()}>
184
+ <span>{new Date(v).toLocaleDateString()}</span>
185
+ </Tooltip>
186
+ ),
187
+ },
188
+ {
189
+ title: 'Actions',
190
+ key: 'actions',
191
+ width: 120,
192
+ render: (_: any, record: NodeInstance) => (
193
+ <Space>
194
+ <Tooltip title="View">
195
+ <Button
196
+ size="small"
197
+ icon={<EyeOutlined />}
198
+ onClick={() =>
199
+ navigate(`/admin/workflow/node-instances/show/${record.id}`)
200
+ }
201
+ />
202
+ </Tooltip>
203
+ <Tooltip title="Edit">
204
+ <Button
205
+ size="small"
206
+ icon={<EditOutlined />}
207
+ onClick={() =>
208
+ navigate(`/admin/workflow/node-instances/edit/${record.id}`)
209
+ }
210
+ />
211
+ </Tooltip>
212
+ <Popconfirm
213
+ title="Delete this instance?"
214
+ okText="Delete"
215
+ cancelText="Cancel"
216
+ okButtonProps={{ danger: true }}
217
+ onConfirm={() => handleDelete(record.id)}
218
+ >
219
+ <Tooltip title="Delete">
220
+ <Button size="small" danger icon={<DeleteOutlined />} />
221
+ </Tooltip>
222
+ </Popconfirm>
223
+ </Space>
224
+ ),
225
+ },
226
+ ];
227
+
228
+ return (
229
+ <div style={{ background: '#f0f2f5', minHeight: 'calc(100vh - 64px)' }}>
230
+ <Card style={{ marginBottom: 16 }}>
231
+ <div
232
+ style={{
233
+ display: 'flex',
234
+ justifyContent: 'space-between',
235
+ alignItems: 'center',
236
+ }}
237
+ >
238
+ <Title level={4} style={{ margin: 0 }}>
239
+ Node Instance Mgnt
240
+ </Title>
241
+ <Space>
242
+ <Button icon={<ReloadOutlined />} onClick={fetchData} />
243
+ <Button
244
+ type="primary"
245
+ icon={<PlusOutlined />}
246
+ onClick={() => navigate('/admin/workflow/node-instances/create')}
247
+ >
248
+ New Instance
249
+ </Button>
250
+ </Space>
251
+ </div>
252
+ </Card>
253
+
254
+ <Card style={{ marginBottom: 16 }}>
255
+ <Space wrap>
256
+ <Select
257
+ placeholder="Node Type"
258
+ allowClear
259
+ value={filterNodeType}
260
+ onChange={(v) => updateParams({ nodeTypeId: v, page: undefined })}
261
+ style={{ width: 200 }}
262
+ showSearch
263
+ optionFilterProp="label"
264
+ options={nodeTypes.map((nt) => ({
265
+ label: `${nt.label} (${nt.category})`,
266
+ value: String(nt.id),
267
+ }))}
268
+ />
269
+ <Input
270
+ placeholder="Search by name"
271
+ allowClear
272
+ defaultValue={filterName}
273
+ onChange={(e) => {
274
+ const v = e.target.value;
275
+ if (debounceRef.current) clearTimeout(debounceRef.current);
276
+ debounceRef.current = setTimeout(
277
+ () => updateParams({ name: v || undefined, page: undefined }),
278
+ 300,
279
+ );
280
+ }}
281
+ style={{ width: 220 }}
282
+ />
283
+ </Space>
284
+ </Card>
285
+
286
+ <Card>
287
+ <Table
288
+ rowKey="id"
289
+ loading={loading}
290
+ columns={columns}
291
+ dataSource={data}
292
+ pagination={{
293
+ current: page,
294
+ pageSize: PAGE_SIZE,
295
+ total,
296
+ onChange: (p) =>
297
+ updateParams({ page: p > 1 ? String(p) : undefined }),
298
+ showTotal: (t) => `Total ${t}`,
299
+ }}
300
+ size="small"
301
+ />
302
+ </Card>
303
+ </div>
304
+ );
305
+ }