mirror of
https://github.com/CherryHQ/cherry-studio.git
synced 2026-01-06 05:09:09 +08:00
refactor: streamline message editing and enhance error handling
- Removed unnecessary database update in useMessageOperations during message editing. - Improved user feedback for missing original user messages by integrating localized error messages in multiple languages. - Simplified event listener for message sending in Messages component. - Enhanced message resend logic in messages slice to ensure proper error handling and state updates.
This commit is contained in:
parent
d1087ec87c
commit
a30cfb53bf
@ -1,4 +1,3 @@
|
|||||||
import db from '@renderer/databases'
|
|
||||||
import { EVENT_NAMES, EventEmitter } from '@renderer/services/EventService'
|
import { EVENT_NAMES, EventEmitter } from '@renderer/services/EventService'
|
||||||
import store, { useAppDispatch, useAppSelector } from '@renderer/store'
|
import store, { useAppDispatch, useAppSelector } from '@renderer/store'
|
||||||
import {
|
import {
|
||||||
@ -63,11 +62,8 @@ export function useMessageOperations(topic: Topic) {
|
|||||||
updates
|
updates
|
||||||
})
|
})
|
||||||
)
|
)
|
||||||
await db.topics.update(topic.id, {
|
|
||||||
messages: messages.map((m) => (m.id === messageId ? { ...m, ...updates } : m))
|
|
||||||
})
|
|
||||||
},
|
},
|
||||||
[dispatch, messages, topic.id]
|
[dispatch, topic.id]
|
||||||
)
|
)
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@ -248,7 +248,8 @@
|
|||||||
"render": {
|
"render": {
|
||||||
"description": "Failed to render formula. Please check if the formula format is correct",
|
"description": "Failed to render formula. Please check if the formula format is correct",
|
||||||
"title": "Render Error"
|
"title": "Render Error"
|
||||||
}
|
},
|
||||||
|
"user_message_not_found": "Cannot find original user message to resend"
|
||||||
},
|
},
|
||||||
"export": {
|
"export": {
|
||||||
"assistant": "Assistant",
|
"assistant": "Assistant",
|
||||||
|
|||||||
@ -248,7 +248,8 @@
|
|||||||
"render": {
|
"render": {
|
||||||
"description": "数式のレンダリングに失敗しました。数式の形式が正しいか確認してください",
|
"description": "数式のレンダリングに失敗しました。数式の形式が正しいか確認してください",
|
||||||
"title": "レンダリングエラー"
|
"title": "レンダリングエラー"
|
||||||
}
|
},
|
||||||
|
"user_message_not_found": "元のユーザーメッセージを見つけることができませんでした"
|
||||||
},
|
},
|
||||||
"export": {
|
"export": {
|
||||||
"assistant": "アシスタント",
|
"assistant": "アシスタント",
|
||||||
|
|||||||
@ -248,7 +248,8 @@
|
|||||||
"render": {
|
"render": {
|
||||||
"description": "Не удалось рендерить формулу. Пожалуйста, проверьте, правильно ли формат формулы",
|
"description": "Не удалось рендерить формулу. Пожалуйста, проверьте, правильно ли формат формулы",
|
||||||
"title": "Ошибка рендеринга"
|
"title": "Ошибка рендеринга"
|
||||||
}
|
},
|
||||||
|
"user_message_not_found": "Не удалось найти исходное сообщение пользователя"
|
||||||
},
|
},
|
||||||
"export": {
|
"export": {
|
||||||
"assistant": "Ассистент",
|
"assistant": "Ассистент",
|
||||||
|
|||||||
@ -248,7 +248,8 @@
|
|||||||
"render": {
|
"render": {
|
||||||
"description": "渲染公式失败,请检查公式格式是否正确",
|
"description": "渲染公式失败,请检查公式格式是否正确",
|
||||||
"title": "渲染错误"
|
"title": "渲染错误"
|
||||||
}
|
},
|
||||||
|
"user_message_not_found": "无法找到原始用户消息"
|
||||||
},
|
},
|
||||||
"export": {
|
"export": {
|
||||||
"assistant": "助手",
|
"assistant": "助手",
|
||||||
|
|||||||
@ -248,7 +248,8 @@
|
|||||||
"render": {
|
"render": {
|
||||||
"description": "渲染公式失敗,請檢查公式格式是否正確",
|
"description": "渲染公式失敗,請檢查公式格式是否正確",
|
||||||
"title": "渲染錯誤"
|
"title": "渲染錯誤"
|
||||||
}
|
},
|
||||||
|
"user_message_not_found": "無法找到原始用戶訊息"
|
||||||
},
|
},
|
||||||
"export": {
|
"export": {
|
||||||
"assistant": "助手",
|
"assistant": "助手",
|
||||||
|
|||||||
@ -120,10 +120,10 @@ const MessageMenubar: FC<Props> = (props) => {
|
|||||||
) : null
|
) : null
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
if (editedText && editedText !== message.content && resendMessage) {
|
|
||||||
// 同步修改store中用户消息
|
if (editedText && editedText !== message.content) {
|
||||||
await editMessage(message.id, { content: editedText })
|
await editMessage(message.id, { content: editedText })
|
||||||
handleResendUserMessage({ ...message, content: editedText })
|
resendMessage && handleResendUserMessage({ ...message, content: editedText })
|
||||||
}
|
}
|
||||||
}, [message, editMessage, handleResendUserMessage, t])
|
}, [message, editMessage, handleResendUserMessage, t])
|
||||||
|
|
||||||
|
|||||||
@ -68,9 +68,7 @@ const Messages: React.FC<MessagesProps> = ({ assistant, topic, setActiveTopic })
|
|||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const unsubscribes = [
|
const unsubscribes = [
|
||||||
EventEmitter.on(EVENT_NAMES.SEND_MESSAGE, () => {
|
EventEmitter.on(EVENT_NAMES.SEND_MESSAGE, scrollToBottom),
|
||||||
scrollToBottom()
|
|
||||||
}),
|
|
||||||
EventEmitter.on(EVENT_NAMES.CLEAR_MESSAGES, async (data: Topic) => {
|
EventEmitter.on(EVENT_NAMES.CLEAR_MESSAGES, async (data: Topic) => {
|
||||||
const defaultTopic = getDefaultTopic(assistant.id)
|
const defaultTopic = getDefaultTopic(assistant.id)
|
||||||
|
|
||||||
|
|||||||
@ -1,6 +1,7 @@
|
|||||||
import { createAsyncThunk, createSelector, createSlice, type PayloadAction } from '@reduxjs/toolkit'
|
import { createAsyncThunk, createSelector, createSlice, type PayloadAction } from '@reduxjs/toolkit'
|
||||||
import db from '@renderer/databases'
|
import db from '@renderer/databases'
|
||||||
import { autoRenameTopic, TopicManager } from '@renderer/hooks/useTopic'
|
import { autoRenameTopic, TopicManager } from '@renderer/hooks/useTopic'
|
||||||
|
import i18n from '@renderer/i18n'
|
||||||
import { fetchChatCompletion } from '@renderer/services/ApiService'
|
import { fetchChatCompletion } from '@renderer/services/ApiService'
|
||||||
import { EVENT_NAMES, EventEmitter } from '@renderer/services/EventService'
|
import { EVENT_NAMES, EventEmitter } from '@renderer/services/EventService'
|
||||||
import { getAssistantMessage, resetAssistantMessage } from '@renderer/services/MessagesService'
|
import { getAssistantMessage, resetAssistantMessage } from '@renderer/services/MessagesService'
|
||||||
@ -8,7 +9,7 @@ import type { AppDispatch, RootState } from '@renderer/store'
|
|||||||
import type { Assistant, Message, Topic } from '@renderer/types'
|
import type { Assistant, Message, Topic } from '@renderer/types'
|
||||||
import { Model } from '@renderer/types'
|
import { Model } from '@renderer/types'
|
||||||
import { clearTopicQueue, getTopicQueue, waitForTopicQueue } from '@renderer/utils/queue'
|
import { clearTopicQueue, getTopicQueue, waitForTopicQueue } from '@renderer/utils/queue'
|
||||||
import { throttle } from 'lodash'
|
import { cloneDeep, throttle } from 'lodash'
|
||||||
|
|
||||||
export interface MessagesState {
|
export interface MessagesState {
|
||||||
messagesByTopic: Record<string, Message[]>
|
messagesByTopic: Record<string, Message[]>
|
||||||
@ -139,6 +140,9 @@ const messagesSlice = createSlice({
|
|||||||
const message = topicMessages.find((msg) => msg.id === messageId)
|
const message = topicMessages.find((msg) => msg.id === messageId)
|
||||||
if (message) {
|
if (message) {
|
||||||
Object.assign(message, updates)
|
Object.assign(message, updates)
|
||||||
|
db.topics.update(topicId, {
|
||||||
|
messages: topicMessages.map((m) => (m.id === message.id ? cloneDeep(message) : m))
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
@ -282,10 +286,9 @@ export const sendMessage =
|
|||||||
const messageToReset = options.resendAssistantMessage
|
const messageToReset = options.resendAssistantMessage
|
||||||
if (Array.isArray(messageToReset)) {
|
if (Array.isArray(messageToReset)) {
|
||||||
assistantMessages = messageToReset.map((m) => {
|
assistantMessages = messageToReset.map((m) => {
|
||||||
const { model, id } = m
|
const resetMessage = resetAssistantMessage(m, assistant.model)
|
||||||
const resetMessage = resetAssistantMessage(m, model)
|
|
||||||
// 更新状态
|
// 更新状态
|
||||||
dispatch(updateMessage({ topicId: topic.id, messageId: id, updates: resetMessage }))
|
dispatch(updateMessage({ topicId: topic.id, messageId: m.id, updates: resetMessage }))
|
||||||
// 使用重置后的消息
|
// 使用重置后的消息
|
||||||
return resetMessage
|
return resetMessage
|
||||||
})
|
})
|
||||||
@ -337,10 +340,12 @@ export const sendMessage =
|
|||||||
})
|
})
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const assistantMessage of assistantMessages) {
|
for (const assistantMessage of assistantMessages) {
|
||||||
// for of会收到await 影响,在暂停的时候会因为异步的原因有概率拿不到数据
|
// for of会收到await 影响,在暂停的时候会因为异步的原因有概率拿不到数据
|
||||||
dispatch(setStreamMessage({ topicId: topic.id, message: assistantMessage }))
|
dispatch(setStreamMessage({ topicId: topic.id, message: assistantMessage }))
|
||||||
}
|
}
|
||||||
|
|
||||||
const queue = getTopicQueue(topic.id)
|
const queue = getTopicQueue(topic.id)
|
||||||
|
|
||||||
for (const assistantMessage of assistantMessages) {
|
for (const assistantMessage of assistantMessages) {
|
||||||
@ -469,8 +474,15 @@ export const resendMessage =
|
|||||||
// 如果是助手消息,找到对应的用户消息
|
// 如果是助手消息,找到对应的用户消息
|
||||||
const userMessage = topicMessages.find((m) => m.id === message.askId && m.role === 'user')
|
const userMessage = topicMessages.find((m) => m.id === message.askId && m.role === 'user')
|
||||||
if (!userMessage) {
|
if (!userMessage) {
|
||||||
console.error('Cannot find original user message to resend')
|
dispatch(
|
||||||
return dispatch(setError('Cannot find original user message to resend'))
|
updateMessage({
|
||||||
|
topicId: topic.id,
|
||||||
|
messageId: message.id,
|
||||||
|
updates: { status: 'error', error: { message: i18n.t('error.user_message_not_found') } }
|
||||||
|
})
|
||||||
|
)
|
||||||
|
console.error(i18n.t('error.user_message_not_found'))
|
||||||
|
return dispatch(setError(i18n.t('error.user_message_not_found')))
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isMentionModel) {
|
if (isMentionModel) {
|
||||||
@ -509,6 +521,7 @@ export const loadTopicMessagesThunk = (topic: Topic) => async (dispatch: AppDisp
|
|||||||
dispatch(setTopicLoading({ topicId: topic.id, loading: false }))
|
dispatch(setTopicLoading({ topicId: topic.id, loading: false }))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Modified clearMessages thunk
|
// Modified clearMessages thunk
|
||||||
export const clearTopicMessagesThunk = (topic: Topic) => async (dispatch: AppDispatch) => {
|
export const clearTopicMessagesThunk = (topic: Topic) => async (dispatch: AppDispatch) => {
|
||||||
try {
|
try {
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user