balibabu commited on
Commit
18a496b
·
1 Parent(s): df67d7c

feat: Send message with uuid #2088 (#2149)

Browse files

### What problem does this PR solve?

feat: Send message with uuid #2088

### Type of change


- [x] New Feature (non-breaking change which adds functionality)

web/src/components/message-item/group-button.tsx CHANGED
@@ -77,11 +77,16 @@ export const AssistantGroupButton = ({
77
  );
78
  };
79
 
80
- export const UserGroupButton = () => {
 
 
 
 
 
81
  return (
82
  <Radio.Group size="small">
83
  <Radio.Button value="a">
84
- <CopyToClipboard text="xxx"></CopyToClipboard>
85
  </Radio.Button>
86
  <Radio.Button value="b">
87
  <SyncOutlined />
 
77
  );
78
  };
79
 
80
+ interface UserGroupButtonProps {
81
+ messageId: string;
82
+ content: string;
83
+ }
84
+
85
+ export const UserGroupButton = ({ content }: UserGroupButtonProps) => {
86
  return (
87
  <Radio.Group size="small">
88
  <Radio.Button value="a">
89
+ <CopyToClipboard text={content}></CopyToClipboard>
90
  </Radio.Button>
91
  <Radio.Button value="b">
92
  <SyncOutlined />
web/src/components/message-item/index.tsx CHANGED
@@ -30,6 +30,7 @@ interface IProps {
30
  nickname?: string;
31
  avatar?: string;
32
  clickDocumentButton?: (documentId: string, chunk: IChunk) => void;
 
33
  }
34
 
35
  const MessageItem = ({
@@ -38,6 +39,7 @@ const MessageItem = ({
38
  loading = false,
39
  avatar = '',
40
  clickDocumentButton,
 
41
  }: IProps) => {
42
  const isAssistant = item.role === MessageType.Assistant;
43
  const isUser = item.role === MessageType.User;
@@ -112,13 +114,18 @@ const MessageItem = ({
112
  <Flex vertical gap={8} flex={1}>
113
  <Space>
114
  {isAssistant ? (
115
- <AssistantGroupButton
116
- messageId={item.id}
117
- content={item.content}
118
- prompt={item.prompt}
119
- ></AssistantGroupButton>
 
 
120
  ) : (
121
- <UserGroupButton></UserGroupButton>
 
 
 
122
  )}
123
 
124
  {/* <b>{isAssistant ? '' : nickname}</b> */}
 
30
  nickname?: string;
31
  avatar?: string;
32
  clickDocumentButton?: (documentId: string, chunk: IChunk) => void;
33
+ index: number;
34
  }
35
 
36
  const MessageItem = ({
 
39
  loading = false,
40
  avatar = '',
41
  clickDocumentButton,
42
+ index,
43
  }: IProps) => {
44
  const isAssistant = item.role === MessageType.Assistant;
45
  const isUser = item.role === MessageType.User;
 
114
  <Flex vertical gap={8} flex={1}>
115
  <Space>
116
  {isAssistant ? (
117
+ index !== 0 && (
118
+ <AssistantGroupButton
119
+ messageId={item.id}
120
+ content={item.content}
121
+ prompt={item.prompt}
122
+ ></AssistantGroupButton>
123
+ )
124
  ) : (
125
+ <UserGroupButton
126
+ content={item.content}
127
+ messageId={item.id}
128
+ ></UserGroupButton>
129
  )}
130
 
131
  {/* <b>{isAssistant ? '' : nickname}</b> */}
web/src/hooks/chat-hooks.ts CHANGED
@@ -14,9 +14,19 @@ import { buildMessageUuid, isConversationIdExist } from '@/utils/chat';
14
  import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query';
15
  import { message } from 'antd';
16
  import dayjs, { Dayjs } from 'dayjs';
 
17
  import { useCallback, useMemo, useState } from 'react';
18
  import { useSearchParams } from 'umi';
19
 
 
 
 
 
 
 
 
 
 
20
  //#region logic
21
 
22
  export const useClickDialogCard = () => {
@@ -215,11 +225,7 @@ export const useFetchNextConversation = () => {
215
  // }
216
  const conversation = data?.data ?? {};
217
 
218
- const messageList =
219
- conversation?.message?.map((x: Message | IMessage) => ({
220
- ...x,
221
- id: buildMessageUuid(x),
222
- })) ?? [];
223
 
224
  return { ...conversation, message: messageList };
225
  }
@@ -294,7 +300,6 @@ export const useRemoveNextConversation = () => {
294
  };
295
 
296
  export const useDeleteMessage = () => {
297
- // const queryClient = useQueryClient();
298
  const { conversationId } = useGetChatSearchParams();
299
 
300
  const {
@@ -308,9 +313,7 @@ export const useDeleteMessage = () => {
308
  messageId,
309
  conversationId,
310
  });
311
- if (data.retcode === 0) {
312
- // queryClient.invalidateQueries({ queryKey: ['fetchConversationList'] });
313
- }
314
  return data.retcode;
315
  },
316
  });
@@ -471,6 +474,10 @@ export const useFetchNextSharedConversation = () => {
471
  conversationId,
472
  );
473
 
 
 
 
 
474
  return data;
475
  },
476
  });
 
14
  import { useMutation, useQuery, useQueryClient } from '@tanstack/react-query';
15
  import { message } from 'antd';
16
  import dayjs, { Dayjs } from 'dayjs';
17
+ import { set } from 'lodash';
18
  import { useCallback, useMemo, useState } from 'react';
19
  import { useSearchParams } from 'umi';
20
 
21
+ const buildMessageListWithUuid = (messages?: Message[]) => {
22
+ return (
23
+ messages?.map((x: Message | IMessage) => ({
24
+ ...x,
25
+ id: buildMessageUuid(x),
26
+ })) ?? []
27
+ );
28
+ };
29
+
30
  //#region logic
31
 
32
  export const useClickDialogCard = () => {
 
225
  // }
226
  const conversation = data?.data ?? {};
227
 
228
+ const messageList = buildMessageListWithUuid(conversation?.message);
 
 
 
 
229
 
230
  return { ...conversation, message: messageList };
231
  }
 
300
  };
301
 
302
  export const useDeleteMessage = () => {
 
303
  const { conversationId } = useGetChatSearchParams();
304
 
305
  const {
 
313
  messageId,
314
  conversationId,
315
  });
316
+
 
 
317
  return data.retcode;
318
  },
319
  });
 
474
  conversationId,
475
  );
476
 
477
+ const messageList = buildMessageListWithUuid(data?.data?.message);
478
+
479
+ set(data, 'data.message', messageList);
480
+
481
  return data;
482
  },
483
  });
web/src/pages/chat/chat-container/index.tsx CHANGED
@@ -68,6 +68,7 @@ const ChatContainer = () => {
68
  avatar={userInfo.avatar}
69
  reference={buildMessageItemReference(conversation, message)}
70
  clickDocumentButton={clickDocumentButton}
 
71
  ></MessageItem>
72
  );
73
  })}
 
68
  avatar={userInfo.avatar}
69
  reference={buildMessageItemReference(conversation, message)}
70
  clickDocumentButton={clickDocumentButton}
71
+ index={i}
72
  ></MessageItem>
73
  );
74
  })}
web/src/pages/chat/hooks.ts CHANGED
@@ -26,9 +26,9 @@ import {
26
  } from '@/interfaces/database/chat';
27
  import { IChunk } from '@/interfaces/database/knowledge';
28
  import { getFileExtension } from '@/utils';
 
29
  import { useMutationState } from '@tanstack/react-query';
30
  import { get } from 'lodash';
31
- import omit from 'lodash/omit';
32
  import trim from 'lodash/trim';
33
  import {
34
  ChangeEventHandler,
@@ -252,23 +252,22 @@ export const useSelectCurrentConversation = () => {
252
  const { data: dialog } = useFetchNextDialog();
253
  const { conversationId, dialogId } = useGetChatSearchParams();
254
 
 
255
  const addNewestConversation = useCallback(
256
- (message: Partial<Message>, answer: string = '') => {
257
  setCurrentConversation((pre) => {
258
  return {
259
  ...pre,
260
  message: [
261
  ...pre.message,
262
  {
263
- role: MessageType.User,
264
- content: message.content,
265
- doc_ids: message.doc_ids,
266
- id: uuid(),
267
  } as IMessage,
268
  {
269
  role: MessageType.Assistant,
270
  content: answer,
271
- id: uuid(),
272
  reference: {},
273
  } as IMessage,
274
  ],
@@ -278,6 +277,7 @@ export const useSelectCurrentConversation = () => {
278
  [],
279
  );
280
 
 
281
  const addNewestAnswer = useCallback((answer: IAnswer) => {
282
  setCurrentConversation((pre) => {
283
  const latestMessage = pre.message?.at(-1);
@@ -291,6 +291,11 @@ export const useSelectCurrentConversation = () => {
291
  ...latestMessage,
292
  content: answer.answer,
293
  reference: answer.reference,
 
 
 
 
 
294
  } as IMessage,
295
  ],
296
  };
@@ -415,15 +420,13 @@ export const useSendMessage = (
415
  const { send, answer, done, setDone } = useSendMessageWithSse();
416
 
417
  const sendMessage = useCallback(
418
- async (message: string, documentIds: string[], id?: string) => {
419
  const res = await send({
420
  conversation_id: id ?? conversationId,
421
  messages: [
422
- ...(conversation?.message ?? []).map((x: IMessage) => omit(x, 'id')),
423
  {
424
- id: uuid(),
425
- role: MessageType.User,
426
- content: message,
427
  doc_ids: documentIds,
428
  },
429
  ],
@@ -431,7 +434,7 @@ export const useSendMessage = (
431
 
432
  if (res && (res?.response.status !== 200 || res?.data?.retcode !== 0)) {
433
  // cancel loading
434
- setValue(message);
435
  console.info('removeLatestMessage111');
436
  removeLatestMessage();
437
  } else {
@@ -456,11 +459,11 @@ export const useSendMessage = (
456
  );
457
 
458
  const handleSendMessage = useCallback(
459
- async (message: string, documentIds: string[]) => {
460
  if (conversationId !== '') {
461
  sendMessage(message, documentIds);
462
  } else {
463
- const data = await setConversation(message);
464
  if (data.retcode === 0) {
465
  const id = data.data.id;
466
  sendMessage(message, documentIds, id);
@@ -487,11 +490,20 @@ export const useSendMessage = (
487
  const handlePressEnter = useCallback(
488
  (documentIds: string[]) => {
489
  if (trim(value) === '') return;
 
490
 
491
- addNewestConversation({ content: value, doc_ids: documentIds });
 
 
 
 
 
492
  if (done) {
493
  setValue('');
494
- handleSendMessage(value.trim(), documentIds);
 
 
 
495
  }
496
  },
497
  [addNewestConversation, handleSendMessage, done, setValue, value],
 
26
  } from '@/interfaces/database/chat';
27
  import { IChunk } from '@/interfaces/database/knowledge';
28
  import { getFileExtension } from '@/utils';
29
+ import { buildMessageUuid } from '@/utils/chat';
30
  import { useMutationState } from '@tanstack/react-query';
31
  import { get } from 'lodash';
 
32
  import trim from 'lodash/trim';
33
  import {
34
  ChangeEventHandler,
 
252
  const { data: dialog } = useFetchNextDialog();
253
  const { conversationId, dialogId } = useGetChatSearchParams();
254
 
255
+ // Show the entered message in the conversation immediately after sending the message
256
  const addNewestConversation = useCallback(
257
+ (message: Message, answer: string = '') => {
258
  setCurrentConversation((pre) => {
259
  return {
260
  ...pre,
261
  message: [
262
  ...pre.message,
263
  {
264
+ ...message,
265
+ id: buildMessageUuid(message),
 
 
266
  } as IMessage,
267
  {
268
  role: MessageType.Assistant,
269
  content: answer,
270
+ id: buildMessageUuid({ ...message, role: MessageType.Assistant }),
271
  reference: {},
272
  } as IMessage,
273
  ],
 
277
  [],
278
  );
279
 
280
+ // Add the streaming message to the last item in the message list
281
  const addNewestAnswer = useCallback((answer: IAnswer) => {
282
  setCurrentConversation((pre) => {
283
  const latestMessage = pre.message?.at(-1);
 
291
  ...latestMessage,
292
  content: answer.answer,
293
  reference: answer.reference,
294
+ id: buildMessageUuid({
295
+ id: answer.id,
296
+ role: MessageType.Assistant,
297
+ }),
298
+ prompt: answer.prompt,
299
  } as IMessage,
300
  ],
301
  };
 
420
  const { send, answer, done, setDone } = useSendMessageWithSse();
421
 
422
  const sendMessage = useCallback(
423
+ async (message: Message, documentIds: string[], id?: string) => {
424
  const res = await send({
425
  conversation_id: id ?? conversationId,
426
  messages: [
427
+ ...(conversation?.message ?? []),
428
  {
429
+ ...message,
 
 
430
  doc_ids: documentIds,
431
  },
432
  ],
 
434
 
435
  if (res && (res?.response.status !== 200 || res?.data?.retcode !== 0)) {
436
  // cancel loading
437
+ setValue(message.content);
438
  console.info('removeLatestMessage111');
439
  removeLatestMessage();
440
  } else {
 
459
  );
460
 
461
  const handleSendMessage = useCallback(
462
+ async (message: Message, documentIds: string[]) => {
463
  if (conversationId !== '') {
464
  sendMessage(message, documentIds);
465
  } else {
466
+ const data = await setConversation(message.content);
467
  if (data.retcode === 0) {
468
  const id = data.data.id;
469
  sendMessage(message, documentIds, id);
 
490
  const handlePressEnter = useCallback(
491
  (documentIds: string[]) => {
492
  if (trim(value) === '') return;
493
+ const id = uuid();
494
 
495
+ addNewestConversation({
496
+ content: value,
497
+ doc_ids: documentIds,
498
+ id,
499
+ role: MessageType.User,
500
+ });
501
  if (done) {
502
  setValue('');
503
+ handleSendMessage(
504
+ { id, content: value.trim(), role: MessageType.User },
505
+ documentIds,
506
+ );
507
  }
508
  },
509
  [addNewestConversation, handleSendMessage, done, setValue, value],
web/src/pages/chat/markdown-content/index.tsx CHANGED
@@ -134,8 +134,8 @@ const MarkdownContent = ({
134
  let replacedText = reactStringReplace(text, reg, (match, i) => {
135
  const chunkIndex = getChunkIndex(match);
136
  return (
137
- <Popover content={getPopoverContent(chunkIndex)}>
138
- <InfoCircleOutlined key={i} className={styles.referenceIcon} />
139
  </Popover>
140
  );
141
  });
 
134
  let replacedText = reactStringReplace(text, reg, (match, i) => {
135
  const chunkIndex = getChunkIndex(match);
136
  return (
137
+ <Popover content={getPopoverContent(chunkIndex)} key={i}>
138
+ <InfoCircleOutlined className={styles.referenceIcon} />
139
  </Popover>
140
  );
141
  });
web/src/pages/chat/share/large.tsx CHANGED
@@ -58,6 +58,7 @@ const ChatContainer = () => {
58
  sendLoading &&
59
  conversation?.message.length - 1 === i
60
  }
 
61
  ></MessageItem>
62
  );
63
  })}
 
58
  sendLoading &&
59
  conversation?.message.length - 1 === i
60
  }
61
+ index={i}
62
  ></MessageItem>
63
  );
64
  })}
web/src/pages/chat/shared-hooks.ts CHANGED
@@ -6,7 +6,7 @@ import {
6
  import { useSendMessageWithSse } from '@/hooks/logic-hooks';
7
  import { IAnswer, Message } from '@/interfaces/database/chat';
8
  import api from '@/utils/api';
9
- import omit from 'lodash/omit';
10
  import trim from 'lodash/trim';
11
  import {
12
  Dispatch,
@@ -60,15 +60,13 @@ export const useSelectCurrentSharedConversation = (conversationId: string) => {
60
  message: [
61
  ...(pre.message ?? []),
62
  {
63
- role: MessageType.User,
64
- content: message.content,
65
- doc_ids: message.doc_ids,
66
- id: uuid(),
67
  } as IMessage,
68
  {
69
  role: MessageType.Assistant,
70
  content: '',
71
- id: uuid(),
72
  reference: {},
73
  } as IMessage,
74
  ],
@@ -89,6 +87,11 @@ export const useSelectCurrentSharedConversation = (conversationId: string) => {
89
  ...latestMessage,
90
  content: answer.answer,
91
  reference: answer.reference,
 
 
 
 
 
92
  } as IMessage,
93
  ],
94
  };
@@ -152,22 +155,16 @@ export const useSendSharedMessage = (
152
  );
153
 
154
  const sendMessage = useCallback(
155
- async (message: string, id?: string) => {
156
  const res = await send({
157
  conversation_id: id ?? conversationId,
158
  quote: false,
159
- messages: [
160
- ...(conversation?.message ?? []).map((x: IMessage) => omit(x, 'id')),
161
- {
162
- role: MessageType.User,
163
- content: message,
164
- },
165
- ],
166
  });
167
 
168
  if (res && (res?.response.status !== 200 || res?.data?.retcode !== 0)) {
169
  // cancel loading
170
- setValue(message);
171
  removeLatestMessage();
172
  }
173
  },
@@ -183,7 +180,7 @@ export const useSendSharedMessage = (
183
  );
184
 
185
  const handleSendMessage = useCallback(
186
- async (message: string) => {
187
  if (conversationId !== '') {
188
  sendMessage(message);
189
  } else {
@@ -206,10 +203,20 @@ export const useSendSharedMessage = (
206
  const handlePressEnter = useCallback(
207
  (documentIds: string[]) => {
208
  if (trim(value) === '') return;
 
209
  if (done) {
210
  setValue('');
211
- addNewestConversation({ content: value, doc_ids: documentIds });
212
- handleSendMessage(value.trim());
 
 
 
 
 
 
 
 
 
213
  }
214
  },
215
  [addNewestConversation, done, handleSendMessage, setValue, value],
 
6
  import { useSendMessageWithSse } from '@/hooks/logic-hooks';
7
  import { IAnswer, Message } from '@/interfaces/database/chat';
8
  import api from '@/utils/api';
9
+ import { buildMessageUuid } from '@/utils/chat';
10
  import trim from 'lodash/trim';
11
  import {
12
  Dispatch,
 
60
  message: [
61
  ...(pre.message ?? []),
62
  {
63
+ ...message,
64
+ id: buildMessageUuid(message),
 
 
65
  } as IMessage,
66
  {
67
  role: MessageType.Assistant,
68
  content: '',
69
+ id: buildMessageUuid({ ...message, role: MessageType.Assistant }),
70
  reference: {},
71
  } as IMessage,
72
  ],
 
87
  ...latestMessage,
88
  content: answer.answer,
89
  reference: answer.reference,
90
+ id: buildMessageUuid({
91
+ id: answer.id,
92
+ role: MessageType.Assistant,
93
+ }),
94
+ prompt: answer.prompt,
95
  } as IMessage,
96
  ],
97
  };
 
155
  );
156
 
157
  const sendMessage = useCallback(
158
+ async (message: Message, id?: string) => {
159
  const res = await send({
160
  conversation_id: id ?? conversationId,
161
  quote: false,
162
+ messages: [...(conversation?.message ?? []), message],
 
 
 
 
 
 
163
  });
164
 
165
  if (res && (res?.response.status !== 200 || res?.data?.retcode !== 0)) {
166
  // cancel loading
167
+ setValue(message.content);
168
  removeLatestMessage();
169
  }
170
  },
 
180
  );
181
 
182
  const handleSendMessage = useCallback(
183
+ async (message: Message) => {
184
  if (conversationId !== '') {
185
  sendMessage(message);
186
  } else {
 
203
  const handlePressEnter = useCallback(
204
  (documentIds: string[]) => {
205
  if (trim(value) === '') return;
206
+ const id = uuid();
207
  if (done) {
208
  setValue('');
209
+ addNewestConversation({
210
+ content: value,
211
+ doc_ids: documentIds,
212
+ id,
213
+ role: MessageType.User,
214
+ });
215
+ handleSendMessage({
216
+ content: value.trim(),
217
+ id,
218
+ role: MessageType.User,
219
+ });
220
  }
221
  },
222
  [addNewestConversation, done, handleSendMessage, setValue, value],
web/src/pages/flow/chat/box.tsx CHANGED
@@ -57,6 +57,7 @@ const FlowChatBox = () => {
57
  message,
58
  )}
59
  clickDocumentButton={clickDocumentButton}
 
60
  ></MessageItem>
61
  );
62
  })}
 
57
  message,
58
  )}
59
  clickDocumentButton={clickDocumentButton}
60
+ index={i}
61
  ></MessageItem>
62
  );
63
  })}
web/src/pages/flow/chat/hooks.ts CHANGED
@@ -5,10 +5,12 @@ import {
5
  useScrollToBottom,
6
  useSendMessageWithSse,
7
  } from '@/hooks/logic-hooks';
8
- import { IAnswer } from '@/interfaces/database/chat';
9
  import { IMessage } from '@/pages/chat/interface';
10
  import api from '@/utils/api';
 
11
  import { message } from 'antd';
 
12
  import { useCallback, useEffect, useState } from 'react';
13
  import { useParams } from 'umi';
14
  import { v4 as uuid } from 'uuid';
@@ -27,19 +29,18 @@ export const useSelectCurrentMessages = () => {
27
  const ref = useScrollToBottom(currentMessages);
28
 
29
  const addNewestQuestion = useCallback(
30
- (message: string, answer: string = '') => {
31
  setCurrentMessages((pre) => {
32
  return [
33
  ...pre,
34
  {
35
- role: MessageType.User,
36
- content: message,
37
- id: uuid(),
38
  },
39
  {
40
  role: MessageType.Assistant,
41
  content: answer,
42
- id: uuid(),
43
  },
44
  ];
45
  });
@@ -52,10 +53,13 @@ export const useSelectCurrentMessages = () => {
52
  return [
53
  ...pre.slice(0, -1),
54
  {
55
- id: uuid(),
56
  role: MessageType.Assistant,
57
  content: answer.answer,
58
  reference: answer.reference,
 
 
 
 
59
  },
60
  ];
61
  });
@@ -88,7 +92,7 @@ export const useSelectCurrentMessages = () => {
88
  };
89
 
90
  export const useSendMessage = (
91
- addNewestQuestion: (message: string, answer?: string) => void,
92
  removeLatestMessage: () => void,
93
  addNewestAnswer: (answer: IAnswer) => void,
94
  ) => {
@@ -99,12 +103,13 @@ export const useSendMessage = (
99
  const { send, answer, done } = useSendMessageWithSse(api.runCanvas);
100
 
101
  const sendMessage = useCallback(
102
- async (message: string) => {
103
  const params: Record<string, unknown> = {
104
  id: flowId,
105
  };
106
- if (message) {
107
- params.message = message;
 
108
  }
109
  const res = await send(params);
110
 
@@ -112,7 +117,7 @@ export const useSendMessage = (
112
  antMessage.error(res?.data?.retmsg);
113
 
114
  // cancel loading
115
- setValue(message);
116
  removeLatestMessage();
117
  } else {
118
  refetch(); // pull the message list after sending the message successfully
@@ -122,7 +127,7 @@ export const useSendMessage = (
122
  );
123
 
124
  const handleSendMessage = useCallback(
125
- async (message: string) => {
126
  sendMessage(message);
127
  },
128
  [sendMessage],
@@ -135,11 +140,17 @@ export const useSendMessage = (
135
  }, [answer, addNewestAnswer]);
136
 
137
  const handlePressEnter = useCallback(() => {
 
 
138
  if (done) {
139
  setValue('');
140
- handleSendMessage(value.trim());
141
  }
142
- addNewestQuestion(value);
 
 
 
 
143
  }, [addNewestQuestion, handleSendMessage, done, setValue, value]);
144
 
145
  return {
 
5
  useScrollToBottom,
6
  useSendMessageWithSse,
7
  } from '@/hooks/logic-hooks';
8
+ import { IAnswer, Message } from '@/interfaces/database/chat';
9
  import { IMessage } from '@/pages/chat/interface';
10
  import api from '@/utils/api';
11
+ import { buildMessageUuid } from '@/utils/chat';
12
  import { message } from 'antd';
13
+ import trim from 'lodash/trim';
14
  import { useCallback, useEffect, useState } from 'react';
15
  import { useParams } from 'umi';
16
  import { v4 as uuid } from 'uuid';
 
29
  const ref = useScrollToBottom(currentMessages);
30
 
31
  const addNewestQuestion = useCallback(
32
+ (message: Message, answer: string = '') => {
33
  setCurrentMessages((pre) => {
34
  return [
35
  ...pre,
36
  {
37
+ ...message,
38
+ id: buildMessageUuid(message),
 
39
  },
40
  {
41
  role: MessageType.Assistant,
42
  content: answer,
43
+ id: buildMessageUuid({ ...message, role: MessageType.Assistant }),
44
  },
45
  ];
46
  });
 
53
  return [
54
  ...pre.slice(0, -1),
55
  {
 
56
  role: MessageType.Assistant,
57
  content: answer.answer,
58
  reference: answer.reference,
59
+ id: buildMessageUuid({
60
+ id: answer.id,
61
+ role: MessageType.Assistant,
62
+ }),
63
  },
64
  ];
65
  });
 
92
  };
93
 
94
  export const useSendMessage = (
95
+ addNewestQuestion: (message: Message, answer?: string) => void,
96
  removeLatestMessage: () => void,
97
  addNewestAnswer: (answer: IAnswer) => void,
98
  ) => {
 
103
  const { send, answer, done } = useSendMessageWithSse(api.runCanvas);
104
 
105
  const sendMessage = useCallback(
106
+ async (message: Message) => {
107
  const params: Record<string, unknown> = {
108
  id: flowId,
109
  };
110
+ if (message.content) {
111
+ params.message = message.content;
112
+ params.message_id = message.id;
113
  }
114
  const res = await send(params);
115
 
 
117
  antMessage.error(res?.data?.retmsg);
118
 
119
  // cancel loading
120
+ setValue(message.content);
121
  removeLatestMessage();
122
  } else {
123
  refetch(); // pull the message list after sending the message successfully
 
127
  );
128
 
129
  const handleSendMessage = useCallback(
130
+ async (message: Message) => {
131
  sendMessage(message);
132
  },
133
  [sendMessage],
 
140
  }, [answer, addNewestAnswer]);
141
 
142
  const handlePressEnter = useCallback(() => {
143
+ if (trim(value) === '') return;
144
+ const id = uuid();
145
  if (done) {
146
  setValue('');
147
+ handleSendMessage({ id, content: value.trim(), role: MessageType.User });
148
  }
149
+ addNewestQuestion({
150
+ content: value,
151
+ id,
152
+ role: MessageType.User,
153
+ });
154
  }, [addNewestQuestion, handleSendMessage, done, setValue, value]);
155
 
156
  return {
web/src/utils/chat.ts CHANGED
@@ -7,7 +7,7 @@ export const isConversationIdExist = (conversationId: string) => {
7
  return conversationId !== EmptyConversationId && conversationId !== '';
8
  };
9
 
10
- export const buildMessageUuid = (message: Message | IMessage) => {
11
  if ('id' in message && message.id) {
12
  return message.role === MessageType.User
13
  ? `${MessageType.User}_${message.id}`
 
7
  return conversationId !== EmptyConversationId && conversationId !== '';
8
  };
9
 
10
+ export const buildMessageUuid = (message: Partial<Message | IMessage>) => {
11
  if ('id' in message && message.id) {
12
  return message.role === MessageType.User
13
  ? `${MessageType.User}_${message.id}`