From 420aedf83e20add8583088669b2837ead9d38265 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=97=B6=E5=90=AF=E9=BE=99?= Date: Fri, 8 Aug 2025 11:11:59 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E5=A2=9E=E5=8A=A0=E8=84=9A=E6=9C=AC?= =?UTF-8?q?=E7=9A=84=20prompt?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../task/graph/maintain/SelectScript.vue | 67 +++++++++++++++---- .../graph/maintain/components/ScriptNode.vue | 2 +- 2 files changed, 55 insertions(+), 14 deletions(-) diff --git a/src/views/task/graph/maintain/SelectScript.vue b/src/views/task/graph/maintain/SelectScript.vue index f19ecc1..08d8433 100644 --- a/src/views/task/graph/maintain/SelectScript.vue +++ b/src/views/task/graph/maintain/SelectScript.vue @@ -40,7 +40,52 @@ import CodeMirror from 'cmp-element/components/code-mirror' import { last } from 'lodash-es' import { getGroup, getScriptBySimple, getScriptDetail } from 'services/task/script' +/** + * 使用管道符'|'作为分隔符,从脚本内容中解析出参数。 + * @param {string} scriptContent 用户输入的脚本内容,例如 "echo ${{name|请输入姓名}}}" + * @returns {Array<{key: string, value: string, prompt: string}>} 解析并去重后的参数数组 + */ +function parseScriptWithPipe(scriptContent) { + // 正则表达式解释: + // \${{ - 匹配字面量 "${{" + // \s* - 匹配0或多个空格 + // (\w+) - 捕获组1: key (匹配一个或多个字母、数字、下划线) + // \s* - 匹配0或多个空格 + // ( - 开始一个可选的非捕获组 (?: ... )? + // \| - 匹配转义后的管道符 '|' + // \s* - 匹配0或多个空格 + // (.*?) - 捕获组2: prompt (非贪婪模式匹配任意字符,直到下一个 "}}" ) + // )? - 整个 prompt 部分是可选的 + // \s* - 匹配0或多个空格 + // }} - 匹配字面量 "}}" + const regex = /\${{\s*(\w+)\s*(?:\|\s*(.*?))?\s*}}/g + // 使用 matchAll 获取所有匹配项的迭代器 + const matches = scriptContent.matchAll(regex) + + // 使用 Map 来根据 key 进行去重,确保每个 key 只被解析一次(以第一次出现的为准) + const paramsMap = new Map() + + for (const match of matches) { + // match[1] 是第一个捕获组,即 key + const key = match[1] + + // 如果 key 还没有在 map 中,才进行处理 + if (!paramsMap.has(key)) { + // match[2] 是第二个捕获组 (prompt),如果不存在则为 undefined + const prompt = match[2] || '' // 使用空字符串作为默认值 + + paramsMap.set(key, { + key: key, + value: '', // 初始 value 可以和 key 相同,或设为空字符串 '' + prompt: prompt.trim() // 去除 prompt 的前后多余空格 + }) + } + } + + // 将 Map 的值转换为数组并返回 + return Array.from(paramsMap.values()) +} export default { components: { CodeMirror }, props: { @@ -91,19 +136,15 @@ export default { const data = await getScriptDetail(this.scriptItem.scriptId) if (data.success) { const { category, content, name: scriptName, filename } = data.data - const reg = new RegExp(/\$\{\{(.+)\}\}/g) - const res = content.match(reg) - const params = [] - if (res) { - // ['${{hostname}}'] => ['hostname'] - const keys = [...new Set(res.map(item => item.slice(3, item.length - 2)))] - keys.forEach(element => { - params.push({ - key: element, - value: '' - }) - }) - } + // '${{hostname|请输入hostname}}' => + // [ + // { + // key: 'hostname', + // value: '', + // prompt: '请输入hostname' + // } + // ] + const params = parseScriptWithPipe(content) this.scriptItem.category = category this.scriptItem.content = content this.scriptItem.scriptName = scriptName diff --git a/src/views/task/graph/maintain/components/ScriptNode.vue b/src/views/task/graph/maintain/components/ScriptNode.vue index 65e055c..358f865 100644 --- a/src/views/task/graph/maintain/components/ScriptNode.vue +++ b/src/views/task/graph/maintain/components/ScriptNode.vue @@ -4,7 +4,7 @@ - +