Skip to content

Commit 031e77f

Browse files
committed
feat: Support edit last question
1 parent fcaac9c commit 031e77f

File tree

7 files changed

+105
-15
lines changed

7 files changed

+105
-15
lines changed

apps/application/chat_pipeline/step/chat_step/i_chat_step.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,7 @@ class InstanceSerializer(serializers.Serializer):
6969
# 是否使用流的形式输出
7070
stream = serializers.BooleanField(required=False, label=_("Streaming Output"))
7171
chat_user_id = serializers.CharField(required=True, label=_("Chat user id"))
72+
chat_record_id = serializers.CharField(required=False, label=_("Chat record id"))
7273

7374
chat_user_type = serializers.CharField(required=True, label=_("Chat user Type"))
7475
# 未查询到引用分段

apps/application/chat_pipeline/step/chat_step/impl/base_chat_step.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -351,7 +351,7 @@ def execute_stream(self, message_list: List[BaseMessage],
351351
mcp_servers, mcp_source, tool_enable, tool_ids,
352352
application_enable, application_ids,
353353
mcp_output_enable)
354-
chat_record_id = uuid.uuid7()
354+
chat_record_id = self.context.get('step_args',{}).get('chat_record_id') if self.context.get('step_args',{}).get('chat_record_id') else uuid.uuid7()
355355
r = StreamingHttpResponse(
356356
streaming_content=event_content(chat_result, chat_id, chat_record_id, paragraph_list,
357357
post_response_handler, manage, self, chat_model, message_list, problem_text,

apps/application/flow/i_step_node.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ def handler(self, workflow):
6464
answer_text_list)
6565
if workflow.chat_record is not None:
6666
chat_record = workflow.chat_record
67+
chat_record.problem_text = question
6768
chat_record.answer_text = answer_text
6869
chat_record.details = details
6970
chat_record.message_tokens = message_tokens

apps/application/flow/workflow_manage.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -563,7 +563,7 @@ def get_runtime_details(self, get_details=lambda n, index: n.get_details(index))
563563
details_result = {}
564564
for index in range(len(self.node_context)):
565565
node = self.node_context[index]
566-
if self.chat_record is not None and self.chat_record.details is not None:
566+
if self.chat_record is not None and self.chat_record.details is not None and self.start_node:
567567
details = self.chat_record.details.get(node.runtime_node_id)
568568
if details is not None and self.start_node.runtime_node_id != node.runtime_node_id:
569569
details_result[node.runtime_node_id] = details

apps/chat/serializers/chat.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -327,6 +327,7 @@ def chat_simple(self, chat_info: ChatInfo, instance, base_to_response):
327327
chat_user_id = self.data.get('chat_user_id')
328328
chat_user_type = self.data.get('chat_user_type')
329329
form_data = instance.get("form_data")
330+
chat_record_id = instance.get('chat_record_id')
330331
pipeline_manage_builder = PipelineManage.builder()
331332
# 如果开启了问题优化,则添加上问题优化步骤
332333
if chat_info.application.problem_optimization:
@@ -350,6 +351,8 @@ def chat_simple(self, chat_info: ChatInfo, instance, base_to_response):
350351
# 构建运行参数
351352
params = chat_info.to_pipeline_manage_params(message, get_post_handler(chat_info), exclude_paragraph_id_list,
352353
chat_user_id, chat_user_type, stream, form_data)
354+
if chat_record_id:
355+
params['chat_record_id'] = chat_record_id
353356
chat_info.set_chat(message)
354357
# 运行流水线作业
355358
pipeline_message.run(params)

ui/src/components/ai-chat/component/question-content/index.vue

Lines changed: 95 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,20 @@
11
<template>
22
<!-- 问题内容 -->
3-
<div class="question-content item-content mb-16 lighter">
4-
<div class="content p-12-16 border-r-8" :class="getClassName">
3+
<div class="question-content item-content mb-4 lighter">
4+
<div v-if="!isReQuestion" class="content p-12-16 border-r-8" :class="getClassName">
55
<div class="text break-all pre-wrap">
66
<div class="mb-8" v-if="document_list.length">
77
<el-space wrap class="w-full media-file-width">
88
<template v-for="(item, index) in document_list" :key="index">
99
<el-card shadow="never" style="--el-card-padding: 8px" class="download-file cursor">
1010
<div class="download-button flex align-center" @click="downloadFile(item)">
1111
<el-icon class="mr-4">
12-
<Download/>
12+
<Download />
1313
</el-icon>
1414
{{ $t('chat.download') }}
1515
</div>
1616
<div class="show flex align-center">
17-
<img :src="getImgUrl(item && item?.name)" alt="" width="24"/>
17+
<img :src="getImgUrl(item && item?.name)" alt="" width="24" />
1818
<div class="ml-4 ellipsis-1" :title="item && item?.name">
1919
{{ item && item?.name }}
2020
</div>
@@ -78,12 +78,12 @@
7878
<el-card shadow="never" style="--el-card-padding: 8px" class="download-file cursor">
7979
<div class="download-button flex align-center" @click="downloadFile(item)">
8080
<el-icon class="mr-4">
81-
<Download/>
81+
<Download />
8282
</el-icon>
8383
{{ $t('chat.download') }}
8484
</div>
8585
<div class="show flex align-center">
86-
<img :src="getImgUrl(item && item?.name)" alt="" width="24"/>
86+
<img :src="getImgUrl(item && item?.name)" alt="" width="24" />
8787
<div class="ml-4 ellipsis-1" :title="item && item?.name">
8888
{{ item && item?.name }}
8989
</div>
@@ -95,6 +95,20 @@
9595
<span> {{ chatRecord.problem_text }}</span>
9696
</div>
9797
</div>
98+
<el-input v-else v-model="editText">
99+
<template #append>
100+
<div class="flex" style="gap: 8px">
101+
<el-button-group class="flex ml-8 mr-8">
102+
<el-button class="flex mr-8" text @click="cancelReQuestion"
103+
><el-icon><Close /></el-icon
104+
></el-button>
105+
<el-button :disabled="!editText.trim()" text @click="sendReQuestionMessage(chatRecord)">
106+
<el-icon><Comment /></el-icon>
107+
</el-button>
108+
</el-button-group>
109+
</div>
110+
</template>
111+
</el-input>
98112
<div class="avatar ml-8" v-if="showAvatar">
99113
<el-image
100114
v-if="application.user_avatar"
@@ -104,23 +118,51 @@
104118
style="width: 28px; height: 28px; display: block"
105119
/>
106120
<el-avatar v-else :size="28">
107-
<img src="@/assets/user-icon.svg" style="width: 50%" alt=""/>
121+
<img src="@/assets/user-icon.svg" style="width: 50%" alt="" />
108122
</el-avatar>
109123
</div>
110124
</div>
125+
<div
126+
class="text-right mb-8"
127+
:style="{
128+
'padding-right': showAvatar ? '36px' : '0',
129+
}"
130+
v-if="!isReQuestion"
131+
>
132+
<div class="text-right">
133+
<el-tooltip effect="dark" :content="$t('common.edit')" placement="top" v-if="props.isLast">
134+
<el-button text @click="handleEdit(chatRecord)">
135+
<AppIcon iconName="app-edit"></AppIcon>
136+
</el-button>
137+
</el-tooltip>
138+
<el-tooltip effect="dark" :content="$t('common.copy')" placement="top">
139+
<el-button text @click="copyClick(chatRecord?.problem_text)">
140+
<AppIcon iconName="app-copy"></AppIcon>
141+
</el-button>
142+
</el-tooltip>
143+
</div>
144+
</div>
111145
</template>
112146
<script setup lang="ts">
113-
import {type chatType} from '@/api/type/application'
114-
import {getImgUrl, downloadByURL} from '@/utils/common'
115-
import {getAttrsArray} from '@/utils/array'
116-
import {onMounted, computed} from 'vue'
147+
import { type chatType } from '@/api/type/application'
148+
import { getImgUrl, downloadByURL } from '@/utils/common'
149+
import { getAttrsArray } from '@/utils/array'
150+
import { onMounted, computed, ref } from 'vue'
151+
import { copyClick } from '@/utils/clipboard'
117152
118153
const props = defineProps<{
119154
application: any
120155
chatRecord: chatType
156+
chatManagement: any
157+
sendMessage: (question: string, other_params_data?: any, chat?: chatType) => Promise<boolean>
121158
type: 'log' | 'ai-chat' | 'debug-ai-chat'
159+
isLast: boolean
122160
}>()
123161
162+
const isReQuestion = ref<boolean>(false)
163+
const editText = ref<string>('')
164+
const direction = ref<'horizontal' | 'vertical'>('horizontal')
165+
124166
const showAvatar = computed(() => {
125167
return props.application.show_user_avatar == undefined ? true : props.application.show_user_avatar
126168
})
@@ -184,8 +226,48 @@ function downloadFile(item: any) {
184226
downloadByURL(item.url, item.name)
185227
}
186228
187-
onMounted(() => {
188-
})
229+
function handleEdit(chatRecord: any) {
230+
isReQuestion.value = true
231+
editText.value = chatRecord.problem_text
232+
}
233+
234+
const cancelReQuestion = () => {
235+
isReQuestion.value = false
236+
}
237+
238+
const emit = defineEmits(['reQuestion'])
239+
240+
function sendReQuestionMessage(chat: chatType) {
241+
const container = props.chatRecord?.upload_meta
242+
? props.chatRecord.upload_meta
243+
: props.chatRecord.execution_details?.find((detail) => detail.type === 'start-node')
244+
245+
props.chatRecord.problem_text = editText.value
246+
reset_answer_text_list(props.chatRecord.answer_text_list)
247+
props.chatRecord.write_ed = false
248+
249+
isReQuestion.value = false
250+
props.sendMessage(
251+
editText.value,
252+
{
253+
re_chat: true,
254+
image_list: container?.image_list || [],
255+
document_list: container?.document_list || [],
256+
audio_list: container?.audio_list || [],
257+
video_list: container?.video_list || [],
258+
other_list: container?.other_list || [],
259+
chat_record_id: props.chatRecord.record_id ? props.chatRecord.record_id : props.chatRecord.id,
260+
},
261+
{ ...props.chatRecord, problem_text: editText.value },
262+
)
263+
}
264+
265+
const reset_answer_text_list = (answer_text_list: any) => {
266+
answer_text_list.splice(0, answer_text_list.length)
267+
answer_text_list.push([])
268+
}
269+
270+
onMounted(() => {})
189271
</script>
190272
<style lang="scss" scoped>
191273
.question-content {

ui/src/components/ai-chat/index.vue

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,9 +36,12 @@
3636
<template v-for="(item, index) in chatList" :key="index">
3737
<!-- 问题 -->
3838
<QuestionContent
39+
:chat-management="ChatManagement"
3940
:type="type"
4041
:application="applicationDetails"
42+
:send-message="sendMessage"
4143
:chat-record="item"
44+
:is-last="index >= chatList.length - 1"
4245
></QuestionContent>
4346
<!-- 回答 -->
4447
<AnswerContent

0 commit comments

Comments
 (0)