feat(context): 新增上下文记忆功能,支持在对话中保持用户输入上下文信息
This commit is contained in:
parent
87efcdd296
commit
a289db56c7
|
|
@ -152,6 +152,15 @@ async function handleSend(text: string, attachments: Attachment[], options?: { d
|
||||||
chatStore.createConversation();
|
chatStore.createConversation();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 从当前会话中提取历史消息(用于上下文记忆),在添加新消息之前提取
|
||||||
|
const existingMessages = currentConversation.value?.messages || [];
|
||||||
|
const MAX_HISTORY_ROUNDS = 20; // 最多保留最近 20 轮(40 条消息)
|
||||||
|
const historyMessages = existingMessages
|
||||||
|
.filter((m: any) => m.role === MessageRole.USER || m.role === MessageRole.ASSISTANT)
|
||||||
|
.filter((m: any) => m.content?.text) // 过滤掉空消息
|
||||||
|
.slice(-(MAX_HISTORY_ROUNDS * 2))
|
||||||
|
.map((m: any) => ({ role: m.role, content: m.content.text }));
|
||||||
|
|
||||||
// 添加用户消息
|
// 添加用户消息
|
||||||
chatStore.addMessage(MessageRole.USER, {
|
chatStore.addMessage(MessageRole.USER, {
|
||||||
type: MessageType.TEXT,
|
type: MessageType.TEXT,
|
||||||
|
|
@ -189,9 +198,10 @@ async function handleSend(text: string, attachments: Attachment[], options?: { d
|
||||||
message: text,
|
message: text,
|
||||||
conversationId: currentConversation.value?.id || "",
|
conversationId: currentConversation.value?.id || "",
|
||||||
images: imageUrls,
|
images: imageUrls,
|
||||||
files: fileUrls, // 传递文件 URL,后端会读取内容
|
files: fileUrls,
|
||||||
model: settings.value.defaultModel,
|
model: settings.value.defaultModel,
|
||||||
stream: true,
|
stream: true,
|
||||||
|
history: historyMessages,
|
||||||
deepSearch: options?.deepSearch,
|
deepSearch: options?.deepSearch,
|
||||||
webSearch: options?.webSearch,
|
webSearch: options?.webSearch,
|
||||||
deepThinking: options?.deepThinking,
|
deepThinking: options?.deepThinking,
|
||||||
|
|
@ -259,6 +269,15 @@ async function handleRetry(messageId: string) {
|
||||||
const userMessage = messages.value[messageIndex - 1];
|
const userMessage = messages.value[messageIndex - 1];
|
||||||
if (userMessage.role !== MessageRole.USER) return;
|
if (userMessage.role !== MessageRole.USER) return;
|
||||||
|
|
||||||
|
// 提取重试位置之前的历史消息(用于上下文记忆)
|
||||||
|
const MAX_HISTORY_ROUNDS = 20;
|
||||||
|
const priorMessages = messages.value
|
||||||
|
.slice(0, messageIndex - 1) // 不包含当前 user 消息和要重试的 assistant 消息
|
||||||
|
.filter((m: any) => m.role === MessageRole.USER || m.role === MessageRole.ASSISTANT)
|
||||||
|
.filter((m: any) => m.content?.text)
|
||||||
|
.slice(-(MAX_HISTORY_ROUNDS * 2))
|
||||||
|
.map((m: any) => ({ role: m.role, content: m.content.text }));
|
||||||
|
|
||||||
// 重置消息状态
|
// 重置消息状态
|
||||||
chatStore.updateMessage(messageId, {
|
chatStore.updateMessage(messageId, {
|
||||||
isError: false,
|
isError: false,
|
||||||
|
|
@ -279,6 +298,7 @@ async function handleRetry(messageId: string) {
|
||||||
conversationId: currentConversation.value?.id,
|
conversationId: currentConversation.value?.id,
|
||||||
model: settings.value.defaultModel,
|
model: settings.value.defaultModel,
|
||||||
stream: true,
|
stream: true,
|
||||||
|
history: priorMessages,
|
||||||
},
|
},
|
||||||
abortController.value.signal,
|
abortController.value.signal,
|
||||||
);
|
);
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,8 @@ export interface ChatRequest {
|
||||||
maxTokens?: number;
|
maxTokens?: number;
|
||||||
systemPrompt?: string;
|
systemPrompt?: string;
|
||||||
stream?: boolean;
|
stream?: boolean;
|
||||||
|
// 历史对话消息(用于上下文记忆)
|
||||||
|
history?: { role: string; content: string }[];
|
||||||
// 扩展选项
|
// 扩展选项
|
||||||
deepSearch?: boolean;
|
deepSearch?: boolean;
|
||||||
webSearch?: boolean;
|
webSearch?: boolean;
|
||||||
|
|
@ -107,22 +109,26 @@ class ChatApi {
|
||||||
}
|
}
|
||||||
|
|
||||||
// 将前端简化的请求翻译为 OpenAI 兼容的规范请求体
|
// 将前端简化的请求翻译为 OpenAI 兼容的规范请求体
|
||||||
|
// 构建 messages 数组:system + 历史消息 + 当前用户消息
|
||||||
|
const systemMessage = {
|
||||||
|
role: "system",
|
||||||
|
content: request.systemPrompt || "你是一个智能助手,可以分析用户发送的文字,文件或图片内容,并进行回答。",
|
||||||
|
};
|
||||||
|
const currentUserMessage = {
|
||||||
|
role: "user",
|
||||||
|
content: userContent,
|
||||||
|
};
|
||||||
|
const allMessages = request.history && request.history.length > 0
|
||||||
|
? [systemMessage, ...request.history, currentUserMessage]
|
||||||
|
: [systemMessage, currentUserMessage];
|
||||||
|
|
||||||
const openAiRequest = {
|
const openAiRequest = {
|
||||||
model: request.model || "glm-4-flash", // 可能需要指定支持视觉的模型
|
model: request.model || "glm-4-flash",
|
||||||
messages: [
|
messages: allMessages,
|
||||||
{
|
|
||||||
role: "system",
|
|
||||||
content: request.systemPrompt || "你是一个智能助手,可以分析用户发送的文字,文件或图片内容,并进行回答。",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
role: "user",
|
|
||||||
content: userContent,
|
|
||||||
},
|
|
||||||
],
|
|
||||||
stream: true,
|
stream: true,
|
||||||
temperature: request.temperature,
|
temperature: request.temperature,
|
||||||
max_tokens: request.maxTokens,
|
max_tokens: request.maxTokens,
|
||||||
files: request.files || [], // 传递文件 URL 列表给后端
|
files: request.files || [],
|
||||||
// 扩展参数传递给我们的 Python 后端进行特殊处理
|
// 扩展参数传递给我们的 Python 后端进行特殊处理
|
||||||
deepSearch: request.deepSearch,
|
deepSearch: request.deepSearch,
|
||||||
webSearch: request.webSearch,
|
webSearch: request.webSearch,
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue