fix: 智能自动模式对话和图片合并发送
修复流程: 1. 用户发送请求 2. 显示占位图 3. 图片生成后显示(对话文字 + 图片) - 将对话消息和图片合并成一条消息 - 对话文字在前,图片在后 - 占位图显示到图片出现为止 Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
6462fe2456
commit
73d1ab7912
@ -1032,36 +1032,6 @@ export async function POST(request: Request) {
|
||||
});
|
||||
}
|
||||
|
||||
// 🆕 如果是智能模式且有对话回复,先发送对话消息
|
||||
if (smartAutoFriendlyMessage) {
|
||||
const chatMessageId = generateUUID();
|
||||
console.log("[Chat API] 💬 Sending conversational reply first:", smartAutoFriendlyMessage);
|
||||
|
||||
// 写入对话消息到流
|
||||
writer.write({
|
||||
type: "data-appendMessage",
|
||||
data: JSON.stringify({
|
||||
id: chatMessageId,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: smartAutoFriendlyMessage }],
|
||||
}),
|
||||
});
|
||||
|
||||
// 保存对话消息到数据库
|
||||
await saveMessages({
|
||||
messages: [
|
||||
{
|
||||
id: chatMessageId,
|
||||
chatId: id,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: smartAutoFriendlyMessage }],
|
||||
attachments: [],
|
||||
createdAt: new Date(),
|
||||
},
|
||||
],
|
||||
});
|
||||
}
|
||||
|
||||
// 转换消息(阿里生图支持 URL,会自动上传 base64)
|
||||
const modelMessages = await convertMessagesWithImages(messagesForAlibaba, "alibaba-image");
|
||||
|
||||
@ -1075,20 +1045,25 @@ export async function POST(request: Request) {
|
||||
const imageMarkdown = result.text || "图片生成失败";
|
||||
console.log("[Chat API] Alibaba generated, length:", imageMarkdown.length);
|
||||
|
||||
// 生成消息 ID(图片消息)
|
||||
// 生成消息 ID
|
||||
const messageId = generateUUID();
|
||||
|
||||
// 写入图片消息到流
|
||||
// 合并对话和图片的完整内容
|
||||
const fullContent = smartAutoFriendlyMessage
|
||||
? `${smartAutoFriendlyMessage}\n\n${imageMarkdown}`
|
||||
: imageMarkdown;
|
||||
|
||||
// 写入完整消息到流
|
||||
writer.write({
|
||||
type: "data-appendMessage",
|
||||
data: JSON.stringify({
|
||||
id: messageId,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: imageMarkdown }],
|
||||
parts: [{ type: "text", text: fullContent }],
|
||||
}),
|
||||
});
|
||||
|
||||
// 保存图片消息到数据库
|
||||
// 保存完整消息到数据库
|
||||
try {
|
||||
await saveMessages({
|
||||
messages: [
|
||||
@ -1096,7 +1071,7 @@ export async function POST(request: Request) {
|
||||
id: messageId,
|
||||
chatId: id,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: imageMarkdown }],
|
||||
parts: [{ type: "text", text: fullContent }],
|
||||
attachments: [],
|
||||
createdAt: new Date(),
|
||||
videoStorageStatus: null,
|
||||
@ -1200,36 +1175,6 @@ export async function POST(request: Request) {
|
||||
const volcanoStream = createUIMessageStream({
|
||||
execute: async ({ writer }) => {
|
||||
try {
|
||||
// 🆕 如果是智能模式且有对话回复,先发送对话消息
|
||||
if (smartAutoFriendlyMessage) {
|
||||
const chatMessageId = generateUUID();
|
||||
console.log("[Chat API] 💬 Volcano: Sending conversational reply first:", smartAutoFriendlyMessage);
|
||||
|
||||
// 写入对话消息到流
|
||||
writer.write({
|
||||
type: "data-appendMessage",
|
||||
data: JSON.stringify({
|
||||
id: chatMessageId,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: smartAutoFriendlyMessage }],
|
||||
}),
|
||||
});
|
||||
|
||||
// 保存对话消息到数据库
|
||||
await saveMessages({
|
||||
messages: [
|
||||
{
|
||||
id: chatMessageId,
|
||||
chatId: id,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: smartAutoFriendlyMessage }],
|
||||
attachments: [],
|
||||
createdAt: new Date(),
|
||||
},
|
||||
],
|
||||
});
|
||||
}
|
||||
|
||||
// 转换消息,火山引擎支持 URL 和 base64
|
||||
const modelMessages = await convertMessagesWithImages(messagesForVolcano, "volcano");
|
||||
|
||||
@ -1242,20 +1187,25 @@ export async function POST(request: Request) {
|
||||
console.log("[Chat API] Volcano Vision generated, length:", imageMarkdown.length);
|
||||
console.log("[Chat API] Volcano Vision image markdown:", imageMarkdown.substring(0, 200));
|
||||
|
||||
// 生成一个统一的消息 ID(图片消息)
|
||||
// 生成消息 ID
|
||||
const messageId = generateUUID();
|
||||
|
||||
// 写入图片消息到流
|
||||
// 合并对话和图片的完整内容
|
||||
const fullContent = smartAutoFriendlyMessage
|
||||
? `${smartAutoFriendlyMessage}\n\n${imageMarkdown}`
|
||||
: imageMarkdown;
|
||||
|
||||
// 写入完整消息到流
|
||||
writer.write({
|
||||
type: "data-appendMessage",
|
||||
data: JSON.stringify({
|
||||
id: messageId,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: imageMarkdown }],
|
||||
parts: [{ type: "text", text: fullContent }],
|
||||
}),
|
||||
});
|
||||
|
||||
// 保存图片消息到数据库
|
||||
// 保存完整消息到数据库
|
||||
try {
|
||||
await saveMessages({
|
||||
messages: [
|
||||
@ -1263,7 +1213,7 @@ export async function POST(request: Request) {
|
||||
id: messageId,
|
||||
chatId: id,
|
||||
role: "assistant",
|
||||
parts: [{ type: "text", text: imageMarkdown }],
|
||||
parts: [{ type: "text", text: fullContent }],
|
||||
attachments: [], // 必须提供 attachments 字段(数据库 notNull)
|
||||
createdAt: new Date(),
|
||||
videoStorageStatus: null,
|
||||
|
||||
@ -169,16 +169,18 @@ function PureMessages({
|
||||
// 判断是否是图片生成模型(包括 Gemini、火山、阿里)
|
||||
const isImageGenModel = isGeminiModel || isVolcanoVisionModel || isAlibabaImageModel;
|
||||
|
||||
// 🆕 智能自动模式:检查用户消息是否包含图片,如果有则视为图片编辑场景
|
||||
const isAutoModeWithImage = selectedModelId === "auto" && lastMessage?.role === "user" &&
|
||||
lastMessage.parts?.some((p: any) => p.type === "file" || p.type === "image");
|
||||
// 🆕 智能自动模式:检查用户最后一条消息是否包含图片,如果有则视为图片编辑场景
|
||||
// 注意:需要找用户的最后一条消息,而不是整个对话的最后一条
|
||||
const lastUserMessage = [...messages].reverse().find(m => m.role === "user");
|
||||
const isAutoModeWithImage = selectedModelId === "auto" &&
|
||||
lastUserMessage?.parts?.some((p: any) => p.type === "file" || p.type === "image");
|
||||
|
||||
// 根据模型类型判断是否有有效内容
|
||||
let hasContent = false;
|
||||
if (isQianwenVideoModel || isVideoModel) {
|
||||
hasContent = hasVideoContent ?? false; // 视频模型:只有真正的视频才算有内容
|
||||
} else if (isImageGenModel || isAutoModeWithImage) {
|
||||
hasContent = hasImageContent ?? false; // 图片模型或智能自动+图片:只有图片才算有内容
|
||||
hasContent = hasImageContent ?? false; // 图片模型或智能自动+图片:只有图片才算有内容(文字不算)
|
||||
} else {
|
||||
hasContent = hasTextContent ?? false; // 其他模型:任何文本都算有内容
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user