Skip to content

Commit 6d1dbce

Browse files
authored
feat: Migration direct reply node (#6330)
1 parent 70207b1 commit 6d1dbce

3 files changed

Lines changed: 73 additions & 6 deletions

File tree

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
# coding=utf-8
2+
"""
3+
@project: MaxKB
4+
@Author:虎虎虎
5+
@file: __init__.py
6+
@date:2026/7/2 10:00
7+
@desc:
8+
"""
9+
from .reply_node import ReplyNode
Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
# coding=utf-8
2+
"""
3+
@project: MaxKB
4+
@Author:虎虎虎
5+
@file: reply_node.py
6+
@date:2026/7/2 10:00
7+
@desc:
8+
"""
9+
from typing import List
10+
11+
from django.utils.translation import gettext_lazy as _
12+
from rest_framework import serializers
13+
14+
from application.workflow.common import WorkflowType
15+
from application.workflow.i_node import INode
16+
from application.workflow.message.struct.content import NodeInfo
17+
from application.workflow.message.struct.text_content import TextContent
18+
from application.workflow.status import Status
19+
20+
21+
class ReplyNodeSerializer(serializers.Serializer):
22+
reply_type = serializers.CharField(required=True, label=_("Response Type"))
23+
fields = serializers.ListField(required=False, label=_("Reference Field"))
24+
content = serializers.CharField(required=False, allow_blank=True, allow_null=True,
25+
label=_("Direct answer content"))
26+
is_result = serializers.BooleanField(required=False, label=_('Whether to return content'))
27+
28+
29+
class ReplyNode(INode):
30+
serializer_class = ReplyNodeSerializer
31+
supported_workflow_type_list = [WorkflowType.APPLICATION, WorkflowType.KNOWLEDGE, WorkflowType.TOOL]
32+
type = 'reply-node'
33+
34+
def execute(self):
35+
node_params = self.get_parameters()
36+
workflow_params = self.get_workflow_parameters()
37+
chat_record_id = workflow_params.get('chat_record_id')
38+
39+
reply_type = node_params.get('reply_type')
40+
fields = node_params.get('fields')
41+
content = node_params.get('content')
42+
is_result = node_params.get('is_result', False)
43+
44+
if reply_type == 'referencing':
45+
result = self._get_reference_content(fields)
46+
else:
47+
result = self._generate_reply_content(content)
48+
49+
self.write_context('answer', result)
50+
51+
if is_result:
52+
node_info = NodeInfo(self.get_node_id(), self.get_node_name(), Status.SUCCESS)
53+
self.write(TextContent(str(chat_record_id), result, Status.SUCCESS, node_info))
54+
55+
def _generate_reply_content(self, prompt):
56+
if prompt is None:
57+
return ''
58+
return self.workflow_manage.generate_prompt(prompt)
59+
60+
def _get_reference_content(self, fields: List[str]):
61+
if fields and len(fields) >= 2:
62+
return str(self.workflow_manage.get_reference_field(fields[0], fields[1:]))
63+
return ''

apps/application/workflow/workflow_manage.py

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -62,10 +62,10 @@ def run(self):
6262
工作流执行
6363
@return: None
6464
"""
65+
self.nodes.append(self.start_node)
6566
self._run_async(self.start_node)
6667

6768
def _run(self, node):
68-
self.nodes.append(node)
6969
node.run()
7070

7171
def next_nodes(self, nodes: Optional[List[Node]]):
@@ -84,16 +84,11 @@ def next_nodes(self, nodes: Optional[List[Node]]):
8484
self._run_async(inst)
8585

8686
def assertion_end(self):
87-
"""
88-
如果节点执行结束没有下一个节点 就结束工作流
89-
@return:
90-
"""
9187
with self._lock:
9288
if self.done:
9389
return
9490
if not self.is_end():
9591
return
96-
self.done = True
9792
self.end()
9893

9994
def is_end(self):

0 commit comments

Comments
 (0)