@lobehub/chat 1.0.11 → 1.0.13
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +50 -0
- package/locales/ar/setting.json +5 -0
- package/locales/bg-BG/setting.json +5 -0
- package/locales/de-DE/setting.json +5 -0
- package/locales/en-US/setting.json +5 -0
- package/locales/es-ES/setting.json +5 -0
- package/locales/fr-FR/setting.json +5 -0
- package/locales/it-IT/setting.json +5 -0
- package/locales/ja-JP/setting.json +5 -0
- package/locales/ko-KR/setting.json +5 -0
- package/locales/nl-NL/setting.json +5 -0
- package/locales/pl-PL/setting.json +5 -0
- package/locales/pt-BR/setting.json +5 -0
- package/locales/ru-RU/setting.json +5 -0
- package/locales/tr-TR/setting.json +5 -0
- package/locales/vi-VN/setting.json +5 -0
- package/locales/zh-CN/setting.json +5 -0
- package/locales/zh-TW/setting.json +5 -0
- package/package.json +4 -3
- package/src/app/(main)/chat/(workspace)/@conversation/default.tsx +1 -1
- package/src/app/(main)/chat/settings/features/EditPage.tsx +2 -2
- package/src/app/(main)/settings/agent/index.tsx +1 -1
- package/src/app/(main)/settings/system-agent/features/AgentMeta.tsx +58 -0
- package/src/app/(main)/settings/system-agent/features/Topic.tsx +1 -0
- package/src/app/(main)/settings/system-agent/features/Translation.tsx +1 -0
- package/src/app/(main)/settings/system-agent/index.tsx +2 -0
- package/src/app/(main)/settings/system-agent/page.tsx +1 -1
- package/src/const/settings/systemAgent.ts +1 -0
- package/src/features/AgentSetting/AgentMeta/AutoGenerateAvatar.tsx +59 -0
- package/src/features/AgentSetting/AgentMeta/index.tsx +6 -9
- package/src/features/AgentSetting/AgentSettings.tsx +24 -0
- package/src/features/AgentSetting/AgentSettingsStore.tsx +14 -0
- package/src/features/AgentSetting/StoreUpdater.tsx +10 -5
- package/src/features/AgentSetting/hooks/useAgentSettings.ts +31 -0
- package/src/features/AgentSetting/index.tsx +3 -26
- package/src/features/AgentSetting/store/action.ts +36 -18
- package/src/features/ChatInput/useSend.ts +8 -0
- package/src/features/Conversation/Error/ErrorJsonViewer.tsx +1 -1
- package/src/features/Conversation/Messages/Assistant/ToolCalls/index.tsx +3 -2
- package/src/features/Conversation/Messages/Tool/index.tsx +3 -5
- package/src/features/Conversation/Messages/components/Arguments.tsx +20 -0
- package/src/features/Conversation/Messages/hooks/useYamlArguments.ts +11 -0
- package/src/features/ModelSelect/index.tsx +6 -4
- package/src/libs/agent-runtime/anthropic/index.test.ts +1 -31
- package/src/libs/agent-runtime/anthropic/index.ts +9 -63
- package/src/libs/agent-runtime/openai/index.test.ts +7 -7
- package/src/libs/agent-runtime/openai/index.ts +0 -6
- package/src/libs/agent-runtime/utils/anthropicHelpers.ts +2 -2
- package/src/libs/agent-runtime/utils/streams/anthropic.test.ts +102 -28
- package/src/libs/agent-runtime/utils/streams/anthropic.ts +29 -12
- package/src/libs/agent-runtime/utils/streams/protocol.ts +6 -1
- package/src/locales/default/setting.ts +5 -0
- package/src/services/message/server.ts +4 -0
- package/src/services/message/type.ts +1 -1
- package/src/store/agent/slices/chat/initialState.ts +2 -0
- package/src/store/chat/slices/message/action.ts +48 -48
- package/src/store/chat/slices/message/initialState.ts +2 -0
- package/src/store/chat/slices/message/selectors.ts +3 -0
- package/src/store/chat/slices/plugin/action.test.ts +15 -15
- package/src/store/chat/slices/plugin/action.ts +128 -115
- package/src/store/chat/utils/index.ts +19 -0
- package/src/store/user/slices/settings/action.ts +8 -2
- package/src/store/user/slices/settings/selectors/systemAgent.ts +2 -0
- package/src/types/message/index.ts +1 -1
- package/src/types/user/settings/systemAgent.ts +3 -0
- /package/src/{components/StoreHydration → app/(main)/chat/(workspace)/@conversation/features}/ChatHydration/index.tsx +0 -0
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
/* eslint-disable sort-keys-fix/sort-keys-fix, typescript-sort-keys/interface */
|
|
1
2
|
import { PluginErrorType } from '@lobehub/chat-plugin-sdk';
|
|
2
3
|
import { t } from 'i18next';
|
|
3
4
|
import { Md5 } from 'ts-md5';
|
|
@@ -25,11 +26,6 @@ export interface ChatPluginAction {
|
|
|
25
26
|
triggerAiMessage?: boolean,
|
|
26
27
|
) => Promise<void>;
|
|
27
28
|
|
|
28
|
-
internal_callPluginApi: (id: string, payload: ChatToolPayload) => Promise<string | undefined>;
|
|
29
|
-
internal_invokeDifferentTypePlugin: (id: string, payload: ChatToolPayload) => Promise<any>;
|
|
30
|
-
internal_transformToolCalls: (toolCalls: MessageToolCall[]) => ChatToolPayload[];
|
|
31
|
-
internal_updatePluginError: (id: string, error: any) => Promise<void>;
|
|
32
|
-
|
|
33
29
|
invokeBuiltinTool: (id: string, payload: ChatToolPayload) => Promise<void>;
|
|
34
30
|
invokeDefaultTypePlugin: (id: string, payload: any) => Promise<string | undefined>;
|
|
35
31
|
invokeMarkdownTypePlugin: (id: string, payload: ChatToolPayload) => Promise<void>;
|
|
@@ -41,6 +37,16 @@ export interface ChatPluginAction {
|
|
|
41
37
|
|
|
42
38
|
triggerToolCalls: (id: string) => Promise<void>;
|
|
43
39
|
updatePluginState: (id: string, key: string, value: any) => Promise<void>;
|
|
40
|
+
|
|
41
|
+
internal_callPluginApi: (id: string, payload: ChatToolPayload) => Promise<string | undefined>;
|
|
42
|
+
internal_invokeDifferentTypePlugin: (id: string, payload: ChatToolPayload) => Promise<any>;
|
|
43
|
+
internal_togglePluginApiCalling: (
|
|
44
|
+
loading: boolean,
|
|
45
|
+
id?: string,
|
|
46
|
+
action?: string,
|
|
47
|
+
) => AbortController | undefined;
|
|
48
|
+
internal_transformToolCalls: (toolCalls: MessageToolCall[]) => ChatToolPayload[];
|
|
49
|
+
internal_updatePluginError: (id: string, error: any) => Promise<void>;
|
|
44
50
|
}
|
|
45
51
|
|
|
46
52
|
export const chatPlugin: StateCreator<
|
|
@@ -69,124 +75,17 @@ export const chatPlugin: StateCreator<
|
|
|
69
75
|
|
|
70
76
|
if (triggerAiMessage) await triggerAIMessage({ parentId: id });
|
|
71
77
|
},
|
|
72
|
-
internal_callPluginApi: async (id, payload) => {
|
|
73
|
-
const { internal_updateMessageContent, refreshMessages, internal_toggleChatLoading } = get();
|
|
74
|
-
let data: string;
|
|
75
|
-
|
|
76
|
-
try {
|
|
77
|
-
const abortController = internal_toggleChatLoading(
|
|
78
|
-
true,
|
|
79
|
-
id,
|
|
80
|
-
n('fetchPlugin/start') as string,
|
|
81
|
-
);
|
|
82
|
-
|
|
83
|
-
const message = chatSelectors.getMessageById(id)(get());
|
|
84
|
-
|
|
85
|
-
const res = await chatService.runPluginApi(payload, {
|
|
86
|
-
signal: abortController?.signal,
|
|
87
|
-
trace: { observationId: message?.observationId, traceId: message?.traceId },
|
|
88
|
-
});
|
|
89
|
-
data = res.text;
|
|
90
|
-
|
|
91
|
-
// save traceId
|
|
92
|
-
if (res.traceId) {
|
|
93
|
-
await messageService.updateMessage(id, { traceId: res.traceId });
|
|
94
|
-
}
|
|
95
|
-
} catch (error) {
|
|
96
|
-
console.log(error);
|
|
97
|
-
const err = error as Error;
|
|
98
|
-
|
|
99
|
-
// ignore the aborted request error
|
|
100
|
-
if (!err.message.includes('The user aborted a request.')) {
|
|
101
|
-
await messageService.updateMessageError(id, error as any);
|
|
102
|
-
await refreshMessages();
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
data = '';
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
internal_toggleChatLoading(false, id, n('fetchPlugin/end') as string);
|
|
109
|
-
// 如果报错则结束了
|
|
110
|
-
if (!data) return;
|
|
111
|
-
|
|
112
|
-
await internal_updateMessageContent(id, data);
|
|
113
|
-
|
|
114
|
-
return data;
|
|
115
|
-
},
|
|
116
|
-
|
|
117
|
-
internal_invokeDifferentTypePlugin: async (id, payload) => {
|
|
118
|
-
switch (payload.type) {
|
|
119
|
-
case 'standalone': {
|
|
120
|
-
return await get().invokeStandaloneTypePlugin(id, payload);
|
|
121
|
-
}
|
|
122
|
-
|
|
123
|
-
case 'markdown': {
|
|
124
|
-
return await get().invokeMarkdownTypePlugin(id, payload);
|
|
125
|
-
}
|
|
126
|
-
|
|
127
|
-
case 'builtin': {
|
|
128
|
-
return await get().invokeBuiltinTool(id, payload);
|
|
129
|
-
}
|
|
130
|
-
|
|
131
|
-
default: {
|
|
132
|
-
return await get().invokeDefaultTypePlugin(id, payload);
|
|
133
|
-
}
|
|
134
|
-
}
|
|
135
|
-
},
|
|
136
|
-
|
|
137
|
-
internal_transformToolCalls: (toolCalls) => {
|
|
138
|
-
return toolCalls
|
|
139
|
-
.map((toolCall): ChatToolPayload | null => {
|
|
140
|
-
let payload: ChatToolPayload;
|
|
141
|
-
|
|
142
|
-
const [identifier, apiName, type] = toolCall.function.name.split(PLUGIN_SCHEMA_SEPARATOR);
|
|
143
|
-
|
|
144
|
-
if (!apiName) return null;
|
|
145
|
-
|
|
146
|
-
payload = {
|
|
147
|
-
apiName,
|
|
148
|
-
arguments: toolCall.function.arguments,
|
|
149
|
-
id: toolCall.id,
|
|
150
|
-
identifier,
|
|
151
|
-
type: (type ?? 'default') as any,
|
|
152
|
-
};
|
|
153
|
-
|
|
154
|
-
// if the apiName is md5, try to find the correct apiName in the plugins
|
|
155
|
-
if (apiName.startsWith(PLUGIN_SCHEMA_API_MD5_PREFIX)) {
|
|
156
|
-
const md5 = apiName.replace(PLUGIN_SCHEMA_API_MD5_PREFIX, '');
|
|
157
|
-
const manifest = pluginSelectors.getPluginManifestById(identifier)(
|
|
158
|
-
useToolStore.getState(),
|
|
159
|
-
);
|
|
160
|
-
|
|
161
|
-
const api = manifest?.api.find((api) => Md5.hashStr(api.name).toString() === md5);
|
|
162
|
-
if (api) {
|
|
163
|
-
payload.apiName = api.name;
|
|
164
|
-
}
|
|
165
|
-
}
|
|
166
|
-
|
|
167
|
-
return payload;
|
|
168
|
-
})
|
|
169
|
-
.filter(Boolean) as ChatToolPayload[];
|
|
170
|
-
},
|
|
171
|
-
|
|
172
|
-
internal_updatePluginError: async (id, error) => {
|
|
173
|
-
const { refreshMessages } = get();
|
|
174
|
-
|
|
175
|
-
await messageService.updateMessage(id, { pluginError: error });
|
|
176
|
-
await refreshMessages();
|
|
177
|
-
},
|
|
178
|
-
|
|
179
78
|
invokeBuiltinTool: async (id, payload) => {
|
|
180
|
-
const {
|
|
79
|
+
const { internal_togglePluginApiCalling, internal_updateMessageContent } = get();
|
|
181
80
|
const params = JSON.parse(payload.arguments);
|
|
182
|
-
|
|
81
|
+
internal_togglePluginApiCalling(true, id, n('invokeBuiltinTool') as string);
|
|
183
82
|
let data;
|
|
184
83
|
try {
|
|
185
84
|
data = await useToolStore.getState().invokeBuiltinTool(payload.apiName, params);
|
|
186
85
|
} catch (error) {
|
|
187
86
|
console.log(error);
|
|
188
87
|
}
|
|
189
|
-
|
|
88
|
+
internal_togglePluginApiCalling(false);
|
|
190
89
|
|
|
191
90
|
if (!data) return;
|
|
192
91
|
|
|
@@ -248,6 +147,8 @@ export const chatPlugin: StateCreator<
|
|
|
248
147
|
const message = chatSelectors.getMessageById(id)(get());
|
|
249
148
|
if (!message || message.role !== 'tool' || !message.plugin) return;
|
|
250
149
|
|
|
150
|
+
get().internal_updateMessageError(id, null);
|
|
151
|
+
|
|
251
152
|
const payload: ChatToolPayload = { ...message.plugin, id: message.tool_call_id! };
|
|
252
153
|
|
|
253
154
|
await get().internal_invokeDifferentTypePlugin(id, payload);
|
|
@@ -301,4 +202,116 @@ export const chatPlugin: StateCreator<
|
|
|
301
202
|
await messageService.updateMessagePluginState(id, { [key]: value });
|
|
302
203
|
await refreshMessages();
|
|
303
204
|
},
|
|
205
|
+
|
|
206
|
+
internal_callPluginApi: async (id, payload) => {
|
|
207
|
+
const { internal_updateMessageContent, refreshMessages, internal_togglePluginApiCalling } =
|
|
208
|
+
get();
|
|
209
|
+
let data: string;
|
|
210
|
+
|
|
211
|
+
try {
|
|
212
|
+
const abortController = internal_togglePluginApiCalling(
|
|
213
|
+
true,
|
|
214
|
+
id,
|
|
215
|
+
n('fetchPlugin/start') as string,
|
|
216
|
+
);
|
|
217
|
+
|
|
218
|
+
const message = chatSelectors.getMessageById(id)(get());
|
|
219
|
+
|
|
220
|
+
const res = await chatService.runPluginApi(payload, {
|
|
221
|
+
signal: abortController?.signal,
|
|
222
|
+
trace: { observationId: message?.observationId, traceId: message?.traceId },
|
|
223
|
+
});
|
|
224
|
+
data = res.text;
|
|
225
|
+
|
|
226
|
+
// save traceId
|
|
227
|
+
if (res.traceId) {
|
|
228
|
+
await messageService.updateMessage(id, { traceId: res.traceId });
|
|
229
|
+
}
|
|
230
|
+
} catch (error) {
|
|
231
|
+
console.log(error);
|
|
232
|
+
const err = error as Error;
|
|
233
|
+
|
|
234
|
+
// ignore the aborted request error
|
|
235
|
+
if (!err.message.includes('The user aborted a request.')) {
|
|
236
|
+
await messageService.updateMessageError(id, error as any);
|
|
237
|
+
await refreshMessages();
|
|
238
|
+
}
|
|
239
|
+
|
|
240
|
+
data = '';
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
internal_togglePluginApiCalling(false, id, n('fetchPlugin/end') as string);
|
|
244
|
+
// 如果报错则结束了
|
|
245
|
+
if (!data) return;
|
|
246
|
+
|
|
247
|
+
await internal_updateMessageContent(id, data);
|
|
248
|
+
|
|
249
|
+
return data;
|
|
250
|
+
},
|
|
251
|
+
|
|
252
|
+
internal_invokeDifferentTypePlugin: async (id, payload) => {
|
|
253
|
+
switch (payload.type) {
|
|
254
|
+
case 'standalone': {
|
|
255
|
+
return await get().invokeStandaloneTypePlugin(id, payload);
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
case 'markdown': {
|
|
259
|
+
return await get().invokeMarkdownTypePlugin(id, payload);
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
case 'builtin': {
|
|
263
|
+
return await get().invokeBuiltinTool(id, payload);
|
|
264
|
+
}
|
|
265
|
+
|
|
266
|
+
default: {
|
|
267
|
+
return await get().invokeDefaultTypePlugin(id, payload);
|
|
268
|
+
}
|
|
269
|
+
}
|
|
270
|
+
},
|
|
271
|
+
|
|
272
|
+
internal_togglePluginApiCalling: (loading, id, action) => {
|
|
273
|
+
return get().internal_toggleLoadingArrays('pluginApiLoadingIds', loading, id, action);
|
|
274
|
+
},
|
|
275
|
+
|
|
276
|
+
internal_transformToolCalls: (toolCalls) => {
|
|
277
|
+
return toolCalls
|
|
278
|
+
.map((toolCall): ChatToolPayload | null => {
|
|
279
|
+
let payload: ChatToolPayload;
|
|
280
|
+
|
|
281
|
+
const [identifier, apiName, type] = toolCall.function.name.split(PLUGIN_SCHEMA_SEPARATOR);
|
|
282
|
+
|
|
283
|
+
if (!apiName) return null;
|
|
284
|
+
|
|
285
|
+
payload = {
|
|
286
|
+
apiName,
|
|
287
|
+
arguments: toolCall.function.arguments,
|
|
288
|
+
id: toolCall.id,
|
|
289
|
+
identifier,
|
|
290
|
+
type: (type ?? 'default') as any,
|
|
291
|
+
};
|
|
292
|
+
|
|
293
|
+
// if the apiName is md5, try to find the correct apiName in the plugins
|
|
294
|
+
if (apiName.startsWith(PLUGIN_SCHEMA_API_MD5_PREFIX)) {
|
|
295
|
+
const md5 = apiName.replace(PLUGIN_SCHEMA_API_MD5_PREFIX, '');
|
|
296
|
+
const manifest = pluginSelectors.getPluginManifestById(identifier)(
|
|
297
|
+
useToolStore.getState(),
|
|
298
|
+
);
|
|
299
|
+
|
|
300
|
+
const api = manifest?.api.find((api) => Md5.hashStr(api.name).toString() === md5);
|
|
301
|
+
if (api) {
|
|
302
|
+
payload.apiName = api.name;
|
|
303
|
+
}
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
return payload;
|
|
307
|
+
})
|
|
308
|
+
.filter(Boolean) as ChatToolPayload[];
|
|
309
|
+
},
|
|
310
|
+
internal_updatePluginError: async (id, error) => {
|
|
311
|
+
const { refreshMessages } = get();
|
|
312
|
+
|
|
313
|
+
get().internal_dispatchMessage({ id, type: 'updateMessages', value: { error } });
|
|
314
|
+
await messageService.updateMessage(id, { pluginError: error });
|
|
315
|
+
await refreshMessages();
|
|
316
|
+
},
|
|
304
317
|
});
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import { produce } from 'immer';
|
|
2
|
+
|
|
3
|
+
export const preventLeavingFn = (e: BeforeUnloadEvent) => {
|
|
4
|
+
// set returnValue to trigger alert modal
|
|
5
|
+
// Note: No matter what value is set, the browser will display the standard text
|
|
6
|
+
e.returnValue = '你有正在生成中的请求,确定要离开吗?';
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
export const toggleBooleanList = (ids: string[], id: string, loading: boolean) => {
|
|
10
|
+
return produce(ids, (draft) => {
|
|
11
|
+
if (loading) {
|
|
12
|
+
draft.push(id);
|
|
13
|
+
} else {
|
|
14
|
+
const index = draft.indexOf(id);
|
|
15
|
+
|
|
16
|
+
if (index >= 0) draft.splice(index, 1);
|
|
17
|
+
}
|
|
18
|
+
});
|
|
19
|
+
};
|
|
@@ -8,7 +8,13 @@ import { userService } from '@/services/user';
|
|
|
8
8
|
import type { UserStore } from '@/store/user';
|
|
9
9
|
import { LocaleMode } from '@/types/locale';
|
|
10
10
|
import { LobeAgentSettings } from '@/types/session';
|
|
11
|
-
import {
|
|
11
|
+
import {
|
|
12
|
+
SystemAgentItem,
|
|
13
|
+
UserGeneralConfig,
|
|
14
|
+
UserKeyVaults,
|
|
15
|
+
UserSettings,
|
|
16
|
+
UserSystemAgentConfigKey,
|
|
17
|
+
} from '@/types/user/settings';
|
|
12
18
|
import { switchLang } from '@/utils/client/switchLang';
|
|
13
19
|
import { difference } from '@/utils/difference';
|
|
14
20
|
import { merge } from '@/utils/merge';
|
|
@@ -25,7 +31,7 @@ export interface UserSettingsAction {
|
|
|
25
31
|
updateGeneralConfig: (settings: Partial<UserGeneralConfig>) => Promise<void>;
|
|
26
32
|
updateKeyVaults: (settings: Partial<UserKeyVaults>) => Promise<void>;
|
|
27
33
|
|
|
28
|
-
updateSystemAgent: (key:
|
|
34
|
+
updateSystemAgent: (key: UserSystemAgentConfigKey, value: SystemAgentItem) => Promise<void>;
|
|
29
35
|
}
|
|
30
36
|
|
|
31
37
|
export const createSettingsSlice: StateCreator<
|
|
@@ -9,8 +9,10 @@ const currentSystemAgent = (s: UserStore) =>
|
|
|
9
9
|
|
|
10
10
|
const translation = (s: UserStore) => currentSystemAgent(s).translation;
|
|
11
11
|
const topic = (s: UserStore) => currentSystemAgent(s).topic;
|
|
12
|
+
const agentMeta = (s: UserStore) => currentSystemAgent(s).agentMeta;
|
|
12
13
|
|
|
13
14
|
export const systemAgentSelectors = {
|
|
15
|
+
agentMeta,
|
|
14
16
|
topic,
|
|
15
17
|
translation,
|
|
16
18
|
};
|