From 8e2afcbaa67ba1eec261caf27213e00d24020d0f Mon Sep 17 00:00:00 2001 From: lixiaolong <702156524@qq.com> Date: Fri, 7 Aug 2026 11:28:01 +0800 Subject: [PATCH] =?UTF-8?q?feat(flow):=20=E6=B7=BB=E5=8A=A0=E5=8D=95?= =?UTF-8?q?=E8=8A=82=E7=82=B9=E6=89=A7=E8=A1=8C=E6=9C=BA=E5=99=A8=E4=BA=BA?= =?UTF-8?q?=E9=80=89=E6=8B=A9=E8=AE=B0=E5=BF=86=E5=8A=9F=E8=83=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - 引入 watch 监听器和相关变量用于缓存单节点机器人选择 - 实现按节点ID缓存机器人选择,新节点默认沿用最近一次选择 - 在单节点执行前后记录当前机器人选择到缓存中 - 修改NodeTitle组件传递节点ID用于按节点恢复机器人选择 - 添加试运行参数缓存功能,支持按流程缓存整套参数 - 实现参数层级缓存值恢复,兼容参数结构变化 - 优化试运行关闭和确认时的数据缓存处理逻辑 --- src/views/flow/components/NodeTitle.vue | 3 +- src/views/flow/components/TestRun.vue | 37 +++++++++++++++++++++++-- src/views/flow/index.vue | 26 +++++++++++++++-- 3 files changed, 60 insertions(+), 6 deletions(-) diff --git a/src/views/flow/components/NodeTitle.vue b/src/views/flow/components/NodeTitle.vue index 2f0a7f3..78fdde4 100644 --- a/src/views/flow/components/NodeTitle.vue +++ b/src/views/flow/components/NodeTitle.vue @@ -159,7 +159,8 @@ const execute = () => { document.dispatchEvent(new CustomEvent("singleNodeExecution", { bubbles: false, cancelable: false, - detail: { ...props.nodeProperties }, + // 携带节点 ID,供单节点执行弹窗按节点恢复上次选择的机器人。 + detail: { ...props.nodeProperties, nodeId: props.nodeId }, })); }; diff --git a/src/views/flow/components/TestRun.vue b/src/views/flow/components/TestRun.vue index 47daa2c..a2b586d 100644 --- a/src/views/flow/components/TestRun.vue +++ b/src/views/flow/components/TestRun.vue @@ -90,14 +90,42 @@ const props = defineProps({ const ruleFormRef = ref() const rules = ref({}); const tableData = ref([]) +// 按流程缓存整套试运行参数,关闭或执行后再次打开时继续使用。 +const trialRunCache = new Map() const bindingLoading = ref(false) const emptyBindingSummary = (robotId = '') => ({ robotId, matched: 0, missing: 0, untouched: 0 }) const bindingSummary = ref(emptyBindingSummary()) const emits = defineEmits(['close', 'changeState']) +const cloneData = (data) => JSON.parse(JSON.stringify(data || [])) + +// 根据参数层级恢复缓存值,同时兼容流程参数结构发生增删的情况。 +const mergeCachedValues = (source, cached) => { + const cachedByName = new Map((cached || []).map(item => [item.name, item])) + return (source || []).map((item, index) => { + const cachedAtIndex = cached?.[index] + const cachedItem = cachedAtIndex?.name === item.name ? cachedAtIndex : cachedByName.get(item.name) + if (!cachedItem) return item + const merged = { ...item, value: cachedItem.value } + if (Array.isArray(item.children)) { + merged.children = mergeCachedValues(item.children, cachedItem.children) + } + return merged + }) +} + +const cacheKey = () => props.flowId || '__new_flow__' + +// 深拷贝快照,避免后续表单编辑直接修改缓存内容。 +const rememberTrialRunParams = () => { + if (!tableData.value.length) return + trialRunCache.set(cacheKey(), cloneData(tableData.value)) +} + const handleClose = () => { - ruleFormRef.value?.resetFields() + rememberTrialRunParams() + ruleFormRef.value?.clearValidate() emits('close') } @@ -105,14 +133,17 @@ watch(() => props.drawer, (newVal) => { if (newVal) { const data = getStartNodeFormData() - tableData.value = data - bindingSummary.value = emptyBindingSummary() + const cached = trialRunCache.get(cacheKey()) + tableData.value = mergeCachedValues(data, cached) + const robotId = tableData.value.find(item => item.name === 'robotId')?.value || '' + bindingSummary.value = emptyBindingSummary(robotId) loadRobotOptions() } } ) const confirm = () => { + rememberTrialRunParams() lf.fitView() ruleFormRef.value.validate().then(async () => { const formData = formatTableData(tableData.value) diff --git a/src/views/flow/index.vue b/src/views/flow/index.vue index d66ea0c..f620e56 100644 --- a/src/views/flow/index.vue +++ b/src/views/flow/index.vue @@ -245,7 +245,7 @@