diff --git a/apps/application/flow/step_node/variable_assign_node/impl/base_variable_assign_node.py b/apps/application/flow/step_node/variable_assign_node/impl/base_variable_assign_node.py index f1711009a47..30340d5fb81 100644 --- a/apps/application/flow/step_node/variable_assign_node/impl/base_variable_assign_node.py +++ b/apps/application/flow/step_node/variable_assign_node/impl/base_variable_assign_node.py @@ -38,6 +38,37 @@ def out_evaluation(self, variable, value): else: self.workflow_manage.out_context[variable['fields'][1]] = value + def convert(self, val, target_type): + if not target_type or val is None: + return val + + if target_type == 'json_object': + if isinstance(val, dict) or isinstance(val, list): + return val + return json.loads(val) + elif target_type == 'json_string': + if isinstance(val, str): + return val + return json.dumps(val, ensure_ascii=False) + elif target_type == 'string': + if isinstance(val, str): + return val + return str(val) + elif target_type == 'int': + if isinstance(val, int): + return val + return int(val) + elif target_type == 'float': + if isinstance(val, float): + return val + return float(val) + elif target_type == 'boolean': + if isinstance(val, bool): + return val + return bool(val) + else: + return val + def handle(self, variable, evaluation): result = { 'name': variable['name'], @@ -49,44 +80,56 @@ def handle(self, variable, evaluation): val = variable['value'] else: val = json.loads(variable['value']) + val = self.convert(val, variable.get('target_type')) evaluation(variable, val) result['output_value'] = variable['value'] = val elif variable['type'] == 'string': # 变量解析 例如:{{global.xxx}} val = self.workflow_manage.generate_prompt(variable['value']) + val = self.convert(val, variable.get('target_type')) evaluation(variable, val) result['output_value'] = val else: val = variable['value'] + val = self.convert(val, variable.get('target_type')) evaluation(variable, val) result['output_value'] = val + elif variable['source'] == 'null': + val = None + evaluation(variable, val) + result['output_value'] = val else: reference = self.get_reference_content(variable['reference']) + reference = self.convert(reference, variable.get('target_type')) evaluation(variable, reference) result['output_value'] = reference + + result['input_type'] = type(result.get('input_value')).__name__ if result.get('input_value') is not None else 'null' + result['output_type'] = type(result.get('output_value')).__name__ if result.get('output_value') is not None else 'null' return result def execute(self, variable_list, **kwargs) -> NodeResult: - # result_list = [] - is_chat = False + contains_chat_variable = False for variable in variable_list: if 'fields' not in variable: continue + if 'global' == variable['fields'][0]: result = self.handle(variable, self.global_evaluation) result_list.append(result) - if 'chat' == variable['fields'][0]: + elif 'chat' == variable['fields'][0]: result = self.handle(variable, self.chat_evaluation) result_list.append(result) - is_chat = True - if 'loop' == variable['fields'][0]: + contains_chat_variable = True + elif 'loop' == variable['fields'][0]: result = self.handle(variable, self.loop_evaluation) result_list.append(result) - if 'output' == variable['fields'][0]: + elif 'output' == variable['fields'][0]: result = self.handle(variable, self.out_evaluation) result_list.append(result) - if is_chat: + + if contains_chat_variable: from application.flow.loop_workflow_manage import LoopWorkflowManage if isinstance(self.workflow_manage, LoopWorkflowManage): self.workflow_manage.parentWorkflowManage.get_chat_info().set_chat_variable( diff --git a/ui/src/components/execution-detail-card/index.vue b/ui/src/components/execution-detail-card/index.vue index 347ee55ea46..255ec043837 100644 --- a/ui/src/components/execution-detail-card/index.vue +++ b/ui/src/components/execution-detail-card/index.vue @@ -882,7 +882,7 @@
- {{ f.name }}: {{ f.input_value }} + {{ f.name }} ({{ f.input_type }}): {{ f.input_value }}
@@ -892,7 +892,7 @@
- {{ f.name }}: {{ f.output_value }} + {{ f.name }} ({{ f.output_type }}): {{ f.output_value }}
diff --git a/ui/src/locales/lang/en-US/workflow.ts b/ui/src/locales/lang/en-US/workflow.ts index d4268a6f242..e39d262a977 100644 --- a/ui/src/locales/lang/en-US/workflow.ts +++ b/ui/src/locales/lang/en-US/workflow.ts @@ -200,18 +200,18 @@ export default { label: 'Question Optimization', text: 'Optimize and improve the current question based on historical chat records to better match knowledge segments', result: 'Optimized Question Result', - systemDefault: `#Role + systemDefault: `# Role You are a master of problem optimization, adept at accurately inferring user intentions based on context and optimizing the questions raised by users. -##Skills -###Skill 1: Optimizing Problems -2. Receive user input questions. -3. Carefully analyze the meaning of the problem based on the context. -4. Output optimized problems. +## Skills +### Skill 1: Optimizing Problems +1. Receive user input questions. +2. Carefully analyze the meaning of the problem based on the context. +3. Output optimized problems. -##Limitations: --Only return the optimized problem without any additional explanation or clarification. --Ensure that the optimized problem accurately reflects the original problem intent and does not alter the original intention.`, +## Limitations: +- Only return the optimized problem without any additional explanation or clarification. +- Ensure that the optimized problem accurately reflects the original problem intent and does not alter the original intention.`, }, conditionNode: { label: 'Conditional Branch', @@ -318,6 +318,8 @@ You are a master of problem optimization, adept at accurately inferring user int label: 'Variable Assign', text: 'Update the value of the global variable', assign: 'Set Value', + convertType: 'Convert type', + doNotConvert: 'Do not convert', }, variableAggregationNode: { label: 'Variable Aggregation', diff --git a/ui/src/locales/lang/zh-CN/workflow.ts b/ui/src/locales/lang/zh-CN/workflow.ts index cdb243d9d6a..3c004d437c2 100644 --- a/ui/src/locales/lang/zh-CN/workflow.ts +++ b/ui/src/locales/lang/zh-CN/workflow.ts @@ -205,9 +205,9 @@ export default { ## 技能 ### 技能 1: 优化问题 -2. 接收用户输入的问题。 -3. 依据上下文仔细分析问题含义。 -4. 输出优化后的问题。 +1. 接收用户输入的问题。 +2. 依据上下文仔细分析问题含义。 +3. 输出优化后的问题。 ## 限制: - 仅返回优化后的问题,不进行额外解释或说明。 @@ -318,6 +318,8 @@ export default { label: '变量赋值', text: '更新全局变量的值', assign: '赋值', + convertType: '转换类型', + doNotConvert: '不转换', }, mcpNode: { label: 'MCP 调用', diff --git a/ui/src/locales/lang/zh-Hant/workflow.ts b/ui/src/locales/lang/zh-Hant/workflow.ts index 51ceadff86a..a7fd05c9f1b 100644 --- a/ui/src/locales/lang/zh-Hant/workflow.ts +++ b/ui/src/locales/lang/zh-Hant/workflow.ts @@ -205,9 +205,9 @@ export default { ## 技能 ### 技能 1: 優化問題 -2. 接收用戶輸入的問題。 -3. 依據上下文仔細分析問題含義。 -4. 輸出優化後的問題。 +1. 接收用戶輸入的問題。 +2. 依據上下文仔細分析問題含義。 +3. 輸出優化後的問題。 ## 限制: - 僅返回優化後的問題,不進行額外解釋或說明。 @@ -317,6 +317,8 @@ export default { label: '變數賦值', text: '更新全域變數的值', assign: '賦值', + convertType: '轉換類型', + doNotConvert: '不轉換', }, variableAggregationNode: { label: '變量聚合', diff --git a/ui/src/workflow/nodes/variable-assign-node/index.ts b/ui/src/workflow/nodes/variable-assign-node/index.ts index 567bf425ae1..6c50d4b73cd 100644 --- a/ui/src/workflow/nodes/variable-assign-node/index.ts +++ b/ui/src/workflow/nodes/variable-assign-node/index.ts @@ -7,8 +7,14 @@ class VariableAssignNode extends AppNode { } } +class VariableAssignModel extends AppNodeModel { + get_width() { + return 450 + } +} + export default { type: 'variable-assign-node', - model: AppNodeModel, + model: VariableAssignModel, view: VariableAssignNode } diff --git a/ui/src/workflow/nodes/variable-assign-node/index.vue b/ui/src/workflow/nodes/variable-assign-node/index.vue index a455730e0d6..a78b477e8f3 100644 --- a/ui/src/workflow/nodes/variable-assign-node/index.vue +++ b/ui/src/workflow/nodes/variable-assign-node/index.vue @@ -45,6 +45,7 @@ + @@ -67,6 +68,7 @@ @@ -141,15 +142,28 @@ + + + + - + + + + + @@ -174,6 +188,15 @@ const workflowMode = inject('workflowMode') as WorkflowMode const props = defineProps<{ nodeModel: any }>() const typeOptions = ['string', 'num', 'json', 'bool'] +const targetTypeOptions = [ + { label: t('workflow.nodes.variableAssignNode.doNotConvert'), key: '' }, + { label: 'string', key: 'string' }, + { label: 'int', key: 'int' }, + { label: 'float', key: 'float' }, + { label: 'json_object', key: 'json_object' }, + { label: 'json_string', key: 'json_string' }, + { label: 'boolean', key: 'boolean' }, +] const wheel = (e: any) => { if (e.ctrlKey === true) {