From e0c489b4de4d3ff1c9e6a44630978e2e125cf627 Mon Sep 17 00:00:00 2001 From: ZLY Date: Tue, 21 Oct 2025 10:03:53 +0800 Subject: [PATCH] =?UTF-8?q?feat(flow):=20=E6=B7=BB=E5=8A=A0=E6=B5=81?= =?UTF-8?q?=E7=A8=8B=E7=BC=96=E8=BE=91=E5=99=A8=E9=80=9A=E7=94=A8=E5=B7=A5?= =?UTF-8?q?=E5=85=B7=E5=87=BD=E6=95=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 新增获取handle类型的函数getHandleType- 实现数据类型验证函数validateDataType - 添加根据节点类型获取组件的函数getNodeComponent - 支持BASIC、SWITCH、IMAGE、CODE、REST等多种节点类型- 处理api和data两种handle类型的数据匹配验证 - 提供默认节点组件LocalNode作为兜底选项 --- src/utils/flowCommon.ts | 103 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 103 insertions(+) create mode 100644 src/utils/flowCommon.ts diff --git a/src/utils/flowCommon.ts b/src/utils/flowCommon.ts new file mode 100644 index 0000000..ee4cc19 --- /dev/null +++ b/src/utils/flowCommon.ts @@ -0,0 +1,103 @@ +import { defaultNodeTypes } from '@/components/FlowEditor/node/types/defaultType'; +import BasicNode from '@/components/FlowEditor/node/basicNode/BasicNode'; +import SwitchNode from '@/components/FlowEditor/node/switchNode/SwitchNode'; +import ImageNode from '@/components/FlowEditor/node/imageNode/ImageNode'; +import CodeNode from '@/components/FlowEditor/node/codeNode/CodeNode'; +import RestNode from '@/components/FlowEditor/node/restNode/RestNode'; +import LocalNode from '@/components/FlowEditor/node/localNode/LocalNode'; + +// 获取handle类型 (api或data) +const getHandleType = (handleId: string, nodeParams: any) => { + // 检查是否为api类型的handle + const apiOuts = nodeParams.apiOuts || []; + const apiIns = nodeParams.apiIns || []; + + if (apiOuts.some((api: any) => (api.name || api.id) === handleId) || + apiIns.some((api: any) => (api.name || api.id) === handleId) || (handleId.includes('loop'))) { + return 'api'; + } + + // 检查是否为data类型的handle + const dataOuts = nodeParams.dataOuts || []; + const dataIns = nodeParams.dataIns || []; + + if (dataOuts.some((data: any) => (data.name || data.id) === handleId) || + dataIns.some((data: any) => (data.name || data.id) === handleId)) { + return 'data'; + } + + // 默认为data类型 + return 'data'; +}; + +// 验证数据类型是否匹配 +const validateDataType = (sourceNode: defaultNodeTypes, targetNode: defaultNodeTypes, sourceHandleId: string, targetHandleId: string) => { + const sourceParams = sourceNode.data?.parameters || {}; + const targetParams = targetNode.data?.parameters || {}; + + // 获取源节点的输出参数 + let sourceDataType = ''; + const sourceApiOuts = sourceParams.apiOuts || []; + const sourceDataOuts = sourceParams.dataOuts || []; + + // 查找源handle的数据类型 + const sourceApi = sourceApiOuts.find((api: any) => api.name === sourceHandleId); + const sourceData = sourceDataOuts.find((data: any) => data.name === sourceHandleId); + + if (sourceApi) { + sourceDataType = sourceApi.dataType || ''; + } + else if (sourceData) { + sourceDataType = sourceData.dataType || ''; + } + + // 获取目标节点的输入参数 + let targetDataType = ''; + const targetApiIns = targetParams.apiIns || []; + const targetDataIns = targetParams.dataIns || []; + + // 查找目标handle的数据类型 + const targetApi = targetApiIns.find((api: any) => api.name === targetHandleId); + const targetData = targetDataIns.find((data: any) => data.name === targetHandleId); + + if (targetApi) { + targetDataType = targetApi.dataType || ''; + } + else if (targetData) { + targetDataType = targetData.dataType || ''; + } + + // 如果任一数据类型为空,则允许连接 + if (!sourceDataType || !targetDataType) { + return true; + } + + // 比较数据类型是否匹配 + return sourceDataType === targetDataType; +}; + + +// 根据节点类型获取对应的节点组件 +const getNodeComponent = (nodeType: string) => { + switch (nodeType) { + case 'BASIC': + return BasicNode; + case 'SWITCH': + return SwitchNode; + case 'IMAGE': + return ImageNode; + case 'CODE': + return CodeNode; + case 'REST': + return RestNode; + default: + return LocalNode; + } +}; + + +export { + getHandleType, + validateDataType, + getNodeComponent +}; \ No newline at end of file