koishi-plugin-chatluna 1.3.4 → 1.3.6
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/lib/chains/chain.d.ts +1 -1
- package/lib/index.cjs +48 -27
- package/lib/index.mjs +48 -27
- package/lib/llm-core/agent/openai/index.d.ts +1 -1
- package/lib/llm-core/chat/app.cjs +154 -69
- package/lib/llm-core/chat/app.mjs +159 -77
- package/lib/llm-core/chat/infinite_context.d.ts +3 -0
- package/lib/llm-core/platform/model.cjs +6 -2
- package/lib/llm-core/platform/model.mjs +6 -2
- package/lib/utils/string.cjs +2 -0
- package/lib/utils/string.d.ts +2 -0
- package/lib/utils/string.mjs +2 -0
- package/package.json +1 -1
package/lib/chains/chain.d.ts
CHANGED
|
@@ -46,7 +46,7 @@ export declare class ChainMiddleware {
|
|
|
46
46
|
constructor(name: string, execute: ChainMiddlewareFunction, graph: ChatChainDependencyGraph);
|
|
47
47
|
before<T extends keyof ChainMiddlewareName>(name: T): this;
|
|
48
48
|
after<T extends keyof ChainMiddlewareName>(name: T): this;
|
|
49
|
-
run(session: Session, options: ChainMiddlewareContext): Promise<string |
|
|
49
|
+
run(session: Session, options: ChainMiddlewareContext): Promise<string | h[] | ChainMiddlewareRunStatus | h[][]>;
|
|
50
50
|
}
|
|
51
51
|
export interface ChainMiddlewareContext {
|
|
52
52
|
config: Config;
|
package/lib/index.cjs
CHANGED
|
@@ -1046,9 +1046,13 @@ var ChatLunaChatChain = class _ChatLunaChatChain extends import_base.ChatLunaLLM
|
|
|
1046
1046
|
requests["variables"] = Object.assign(variables ?? {}, {
|
|
1047
1047
|
prompt: (0, import_string.getMessageContent)(message.content)
|
|
1048
1048
|
});
|
|
1049
|
+
requests["variables"]["built"] = {
|
|
1050
|
+
conversationId
|
|
1051
|
+
};
|
|
1049
1052
|
requests["variables_hide"] = requests["variables"];
|
|
1050
1053
|
requests["configurable"] = {
|
|
1051
|
-
session
|
|
1054
|
+
session,
|
|
1055
|
+
conversationId
|
|
1052
1056
|
};
|
|
1053
1057
|
requests["id"] = conversationId;
|
|
1054
1058
|
const response = await (0, import_base.callChatLunaChain)(
|
|
@@ -1185,12 +1189,16 @@ var ChatLunaPluginChain = class _ChatLunaPluginChain extends import_base2.ChatLu
|
|
|
1185
1189
|
requests["variables"] = Object.assign(variables ?? {}, {
|
|
1186
1190
|
prompt: (0, import_string2.getMessageContent)(message.content)
|
|
1187
1191
|
});
|
|
1192
|
+
requests["variables"]["built"] = {
|
|
1193
|
+
conversationId
|
|
1194
|
+
};
|
|
1188
1195
|
requests["after_user_message"] = new import_messages2.HumanMessage(
|
|
1189
1196
|
AGENT_AFTER_USER_PROMPT
|
|
1190
1197
|
);
|
|
1191
1198
|
requests["variables_hide"] = requests["variables"];
|
|
1192
1199
|
requests["configurable"] = {
|
|
1193
|
-
session
|
|
1200
|
+
session,
|
|
1201
|
+
conversationId
|
|
1194
1202
|
};
|
|
1195
1203
|
this._toolsRef.update(session, messages.concat(message));
|
|
1196
1204
|
const preset = this.preset.value;
|
|
@@ -5816,6 +5824,7 @@ var import_crypto7 = require("crypto");
|
|
|
5816
5824
|
var logger11;
|
|
5817
5825
|
function apply56(ctx, config, chain) {
|
|
5818
5826
|
logger11 = (0, import_logger7.createLogger)(ctx);
|
|
5827
|
+
const selectRoomForSession = /* @__PURE__ */ __name(async (session, joinedRooms) => pickContextualRoom(ctx, session, config, joinedRooms), "selectRoomForSession");
|
|
5819
5828
|
chain.middleware("resolve_room", async (session, context) => {
|
|
5820
5829
|
let joinRoom = await queryJoinedConversationRoom(
|
|
5821
5830
|
ctx,
|
|
@@ -5858,32 +5867,16 @@ function apply56(ctx, config, chain) {
|
|
|
5858
5867
|
session
|
|
5859
5868
|
);
|
|
5860
5869
|
if (joinedRooms.length > 0) {
|
|
5861
|
-
joinRoom =
|
|
5862
|
-
|
|
5863
|
-
|
|
5864
|
-
|
|
5865
|
-
|
|
5866
|
-
(room
|
|
5870
|
+
joinRoom = await selectRoomForSession(session, joinedRooms);
|
|
5871
|
+
}
|
|
5872
|
+
if (joinRoom != null) {
|
|
5873
|
+
await switchConversationRoom(ctx, session, joinRoom.roomId);
|
|
5874
|
+
logger11.success(
|
|
5875
|
+
session.text("chatluna.room.auto_switch", [
|
|
5876
|
+
session.userId,
|
|
5877
|
+
joinRoom.roomName
|
|
5878
|
+
])
|
|
5867
5879
|
);
|
|
5868
|
-
if (config.autoCreateRoomFromUser !== true && joinRoom == null) {
|
|
5869
|
-
joinRoom = // 优先加入模版克隆房间
|
|
5870
|
-
joinedRooms.find(
|
|
5871
|
-
(room) => room.visibility === "template_clone"
|
|
5872
|
-
) ?? joinedRooms[Math.floor(Math.random() * joinedRooms.length)];
|
|
5873
|
-
}
|
|
5874
|
-
if (joinRoom != null) {
|
|
5875
|
-
await switchConversationRoom(
|
|
5876
|
-
ctx,
|
|
5877
|
-
session,
|
|
5878
|
-
joinRoom.roomId
|
|
5879
|
-
);
|
|
5880
|
-
logger11.success(
|
|
5881
|
-
session.text("chatluna.room.auto_switch", [
|
|
5882
|
-
session.userId,
|
|
5883
|
-
joinRoom.roomName
|
|
5884
|
-
])
|
|
5885
|
-
);
|
|
5886
|
-
}
|
|
5887
5880
|
}
|
|
5888
5881
|
}
|
|
5889
5882
|
if (joinRoom == null && config.autoCreateRoomFromUser !== true && !session.isDirect && (context.command?.length ?? 0) < 1) {
|
|
@@ -5979,6 +5972,34 @@ function apply56(ctx, config, chain) {
|
|
|
5979
5972
|
}).after("lifecycle-prepare");
|
|
5980
5973
|
}
|
|
5981
5974
|
__name(apply56, "apply");
|
|
5975
|
+
async function pickContextualRoom(ctx, session, config, joinedRooms) {
|
|
5976
|
+
if (joinedRooms.length === 0) {
|
|
5977
|
+
return void 0;
|
|
5978
|
+
}
|
|
5979
|
+
if (!session.isDirect && config.autoCreateRoomFromUser !== true) {
|
|
5980
|
+
const groupRooms = await ctx.database.get("chathub_room_group_member", {
|
|
5981
|
+
groupId: session.guildId,
|
|
5982
|
+
roomId: { $in: joinedRooms.map((room) => room.roomId) }
|
|
5983
|
+
});
|
|
5984
|
+
if (groupRooms.length > 0) {
|
|
5985
|
+
const scopedRoomIds = new Set(groupRooms.map((room) => room.roomId));
|
|
5986
|
+
const findScopedRoom = /* @__PURE__ */ __name((matcher) => joinedRooms.find((room) => {
|
|
5987
|
+
if (!scopedRoomIds.has(room.roomId)) {
|
|
5988
|
+
return false;
|
|
5989
|
+
}
|
|
5990
|
+
return matcher ? matcher(room) : true;
|
|
5991
|
+
}), "findScopedRoom");
|
|
5992
|
+
return findScopedRoom(
|
|
5993
|
+
(room) => room.visibility === "template_clone"
|
|
5994
|
+
) ?? findScopedRoom();
|
|
5995
|
+
}
|
|
5996
|
+
return void 0;
|
|
5997
|
+
}
|
|
5998
|
+
return joinedRooms.find(
|
|
5999
|
+
(room) => room.visibility === "private" && room.roomMasterId === session.userId
|
|
6000
|
+
) ?? joinedRooms.find((room) => room.visibility === "private") ?? joinedRooms.find((room) => room.visibility !== "template_clone") ?? joinedRooms[0];
|
|
6001
|
+
}
|
|
6002
|
+
__name(pickContextualRoom, "pickContextualRoom");
|
|
5982
6003
|
|
|
5983
6004
|
// src/middlewares/room/room_info.ts
|
|
5984
6005
|
function apply57(ctx, config, chain) {
|
package/lib/index.mjs
CHANGED
|
@@ -1021,9 +1021,13 @@ var ChatLunaChatChain = class _ChatLunaChatChain extends ChatLunaLLMChainWrapper
|
|
|
1021
1021
|
requests["variables"] = Object.assign(variables ?? {}, {
|
|
1022
1022
|
prompt: getMessageContent(message.content)
|
|
1023
1023
|
});
|
|
1024
|
+
requests["variables"]["built"] = {
|
|
1025
|
+
conversationId
|
|
1026
|
+
};
|
|
1024
1027
|
requests["variables_hide"] = requests["variables"];
|
|
1025
1028
|
requests["configurable"] = {
|
|
1026
|
-
session
|
|
1029
|
+
session,
|
|
1030
|
+
conversationId
|
|
1027
1031
|
};
|
|
1028
1032
|
requests["id"] = conversationId;
|
|
1029
1033
|
const response = await callChatLunaChain(
|
|
@@ -1168,12 +1172,16 @@ var ChatLunaPluginChain = class _ChatLunaPluginChain extends ChatLunaLLMChainWra
|
|
|
1168
1172
|
requests["variables"] = Object.assign(variables ?? {}, {
|
|
1169
1173
|
prompt: getMessageContent2(message.content)
|
|
1170
1174
|
});
|
|
1175
|
+
requests["variables"]["built"] = {
|
|
1176
|
+
conversationId
|
|
1177
|
+
};
|
|
1171
1178
|
requests["after_user_message"] = new HumanMessage(
|
|
1172
1179
|
AGENT_AFTER_USER_PROMPT
|
|
1173
1180
|
);
|
|
1174
1181
|
requests["variables_hide"] = requests["variables"];
|
|
1175
1182
|
requests["configurable"] = {
|
|
1176
|
-
session
|
|
1183
|
+
session,
|
|
1184
|
+
conversationId
|
|
1177
1185
|
};
|
|
1178
1186
|
this._toolsRef.update(session, messages.concat(message));
|
|
1179
1187
|
const preset = this.preset.value;
|
|
@@ -5826,6 +5834,7 @@ import { randomUUID as randomUUID4 } from "crypto";
|
|
|
5826
5834
|
var logger11;
|
|
5827
5835
|
function apply56(ctx, config, chain) {
|
|
5828
5836
|
logger11 = createLogger7(ctx);
|
|
5837
|
+
const selectRoomForSession = /* @__PURE__ */ __name(async (session, joinedRooms) => pickContextualRoom(ctx, session, config, joinedRooms), "selectRoomForSession");
|
|
5829
5838
|
chain.middleware("resolve_room", async (session, context) => {
|
|
5830
5839
|
let joinRoom = await queryJoinedConversationRoom(
|
|
5831
5840
|
ctx,
|
|
@@ -5868,32 +5877,16 @@ function apply56(ctx, config, chain) {
|
|
|
5868
5877
|
session
|
|
5869
5878
|
);
|
|
5870
5879
|
if (joinedRooms.length > 0) {
|
|
5871
|
-
joinRoom =
|
|
5872
|
-
|
|
5873
|
-
|
|
5874
|
-
|
|
5875
|
-
|
|
5876
|
-
(room
|
|
5880
|
+
joinRoom = await selectRoomForSession(session, joinedRooms);
|
|
5881
|
+
}
|
|
5882
|
+
if (joinRoom != null) {
|
|
5883
|
+
await switchConversationRoom(ctx, session, joinRoom.roomId);
|
|
5884
|
+
logger11.success(
|
|
5885
|
+
session.text("chatluna.room.auto_switch", [
|
|
5886
|
+
session.userId,
|
|
5887
|
+
joinRoom.roomName
|
|
5888
|
+
])
|
|
5877
5889
|
);
|
|
5878
|
-
if (config.autoCreateRoomFromUser !== true && joinRoom == null) {
|
|
5879
|
-
joinRoom = // 优先加入模版克隆房间
|
|
5880
|
-
joinedRooms.find(
|
|
5881
|
-
(room) => room.visibility === "template_clone"
|
|
5882
|
-
) ?? joinedRooms[Math.floor(Math.random() * joinedRooms.length)];
|
|
5883
|
-
}
|
|
5884
|
-
if (joinRoom != null) {
|
|
5885
|
-
await switchConversationRoom(
|
|
5886
|
-
ctx,
|
|
5887
|
-
session,
|
|
5888
|
-
joinRoom.roomId
|
|
5889
|
-
);
|
|
5890
|
-
logger11.success(
|
|
5891
|
-
session.text("chatluna.room.auto_switch", [
|
|
5892
|
-
session.userId,
|
|
5893
|
-
joinRoom.roomName
|
|
5894
|
-
])
|
|
5895
|
-
);
|
|
5896
|
-
}
|
|
5897
5890
|
}
|
|
5898
5891
|
}
|
|
5899
5892
|
if (joinRoom == null && config.autoCreateRoomFromUser !== true && !session.isDirect && (context.command?.length ?? 0) < 1) {
|
|
@@ -5989,6 +5982,34 @@ function apply56(ctx, config, chain) {
|
|
|
5989
5982
|
}).after("lifecycle-prepare");
|
|
5990
5983
|
}
|
|
5991
5984
|
__name(apply56, "apply");
|
|
5985
|
+
async function pickContextualRoom(ctx, session, config, joinedRooms) {
|
|
5986
|
+
if (joinedRooms.length === 0) {
|
|
5987
|
+
return void 0;
|
|
5988
|
+
}
|
|
5989
|
+
if (!session.isDirect && config.autoCreateRoomFromUser !== true) {
|
|
5990
|
+
const groupRooms = await ctx.database.get("chathub_room_group_member", {
|
|
5991
|
+
groupId: session.guildId,
|
|
5992
|
+
roomId: { $in: joinedRooms.map((room) => room.roomId) }
|
|
5993
|
+
});
|
|
5994
|
+
if (groupRooms.length > 0) {
|
|
5995
|
+
const scopedRoomIds = new Set(groupRooms.map((room) => room.roomId));
|
|
5996
|
+
const findScopedRoom = /* @__PURE__ */ __name((matcher) => joinedRooms.find((room) => {
|
|
5997
|
+
if (!scopedRoomIds.has(room.roomId)) {
|
|
5998
|
+
return false;
|
|
5999
|
+
}
|
|
6000
|
+
return matcher ? matcher(room) : true;
|
|
6001
|
+
}), "findScopedRoom");
|
|
6002
|
+
return findScopedRoom(
|
|
6003
|
+
(room) => room.visibility === "template_clone"
|
|
6004
|
+
) ?? findScopedRoom();
|
|
6005
|
+
}
|
|
6006
|
+
return void 0;
|
|
6007
|
+
}
|
|
6008
|
+
return joinedRooms.find(
|
|
6009
|
+
(room) => room.visibility === "private" && room.roomMasterId === session.userId
|
|
6010
|
+
) ?? joinedRooms.find((room) => room.visibility === "private") ?? joinedRooms.find((room) => room.visibility !== "template_clone") ?? joinedRooms[0];
|
|
6011
|
+
}
|
|
6012
|
+
__name(pickContextualRoom, "pickContextualRoom");
|
|
5992
6013
|
|
|
5993
6014
|
// src/middlewares/room/room_info.ts
|
|
5994
6015
|
function apply57(ctx, config, chain) {
|
|
@@ -22,4 +22,4 @@ export type CreateOpenAIAgentParams = {
|
|
|
22
22
|
};
|
|
23
23
|
export declare function createOpenAIAgent({ llm, tools, prompt }: CreateOpenAIAgentParams): RunnableSequence<{
|
|
24
24
|
steps: AgentStep[];
|
|
25
|
-
}, AgentAction | AgentAction[]
|
|
25
|
+
}, AgentAction | AgentFinish | AgentAction[]>;
|
|
@@ -188,12 +188,40 @@ var InfiniteContextManager = class {
|
|
|
188
188
|
import_koishi_plugin_chatluna.logger.info(
|
|
189
189
|
`[InfiniteContext] Start compression with total tokens: ${totalTokens}, threshold: ${threshold}`
|
|
190
190
|
);
|
|
191
|
+
const filteredMessages = messages.filter(
|
|
192
|
+
(message) => !this._isToolRelatedMessage(message)
|
|
193
|
+
);
|
|
194
|
+
if (filteredMessages.length === 0) {
|
|
195
|
+
return;
|
|
196
|
+
}
|
|
197
|
+
const filteredStats = await this._calculateMessageTokenStats(
|
|
198
|
+
model,
|
|
199
|
+
filteredMessages
|
|
200
|
+
);
|
|
201
|
+
const filteredTotalTokens = filteredStats.reduce((sum, current) => sum + current.tokens, 0) + presetTokens;
|
|
202
|
+
if (filteredTotalTokens <= threshold) {
|
|
203
|
+
await this._rewriteChatHistory(filteredMessages);
|
|
204
|
+
import_koishi_plugin_chatluna.logger.info(
|
|
205
|
+
"[InfiniteContext] Filtered tool-related messages reduced tokens from %d to %d",
|
|
206
|
+
totalTokens,
|
|
207
|
+
filteredTotalTokens
|
|
208
|
+
);
|
|
209
|
+
return;
|
|
210
|
+
}
|
|
191
211
|
const compressionResult = await this._compressMessages(
|
|
192
212
|
wrapper,
|
|
193
|
-
|
|
213
|
+
filteredStats,
|
|
194
214
|
maxTokenLimit
|
|
195
215
|
);
|
|
196
216
|
if (!compressionResult) {
|
|
217
|
+
if (filteredMessages.length !== messages.length) {
|
|
218
|
+
await this._rewriteChatHistory(filteredMessages);
|
|
219
|
+
import_koishi_plugin_chatluna.logger.info(
|
|
220
|
+
"[InfiniteContext] Filtered tool-related messages (compression skipped) reduced tokens from %d to %d",
|
|
221
|
+
totalTokens,
|
|
222
|
+
filteredTotalTokens
|
|
223
|
+
);
|
|
224
|
+
}
|
|
197
225
|
return;
|
|
198
226
|
}
|
|
199
227
|
const { messages: rewrittenMessages, tokenCount } = compressionResult;
|
|
@@ -246,12 +274,9 @@ var InfiniteContextManager = class {
|
|
|
246
274
|
0,
|
|
247
275
|
contentStats.length - preserveCount
|
|
248
276
|
);
|
|
249
|
-
compressible = contentStats.filter(
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
}
|
|
253
|
-
return index < thresholdIndex;
|
|
254
|
-
});
|
|
277
|
+
compressible = contentStats.filter(
|
|
278
|
+
(stat, index) => index < thresholdIndex
|
|
279
|
+
);
|
|
255
280
|
if (compressible.length > 0) {
|
|
256
281
|
break;
|
|
257
282
|
}
|
|
@@ -272,10 +297,16 @@ var InfiniteContextManager = class {
|
|
|
272
297
|
return null;
|
|
273
298
|
}
|
|
274
299
|
const compressor = this._ensureInfiniteContextChain(wrapper);
|
|
275
|
-
const
|
|
300
|
+
const chunkSummaries = [];
|
|
301
|
+
const previousSummaries = compressible.filter((stat) => this._isCompressedMessage(stat.message)).map(
|
|
302
|
+
(stat) => (0, import_string2.getMessageContent)(stat.message.content)?.trim() ?? ""
|
|
303
|
+
).filter((text) => text.length > 0);
|
|
276
304
|
for (let index = 0; index < chunkStats.length; index++) {
|
|
277
305
|
const chunk = chunkStats[index];
|
|
278
|
-
const chunkMessages = chunk.map((item) => item.message);
|
|
306
|
+
const chunkMessages = chunk.map((item) => item.message).filter((message) => !this._isCompressedMessage(message));
|
|
307
|
+
if (chunkMessages.length === 0) {
|
|
308
|
+
continue;
|
|
309
|
+
}
|
|
279
310
|
const chunkText = this._formatChunkForCompression(chunkMessages);
|
|
280
311
|
const compressedText = await compressor.compressChunk({
|
|
281
312
|
chunk: chunkText,
|
|
@@ -284,40 +315,28 @@ var InfiniteContextManager = class {
|
|
|
284
315
|
if (!compressedText) {
|
|
285
316
|
continue;
|
|
286
317
|
}
|
|
287
|
-
|
|
318
|
+
chunkSummaries.push({
|
|
288
319
|
content: compressedText,
|
|
289
320
|
chunkIndex: index,
|
|
290
321
|
chunkSize: chunkMessages.length
|
|
291
322
|
});
|
|
292
323
|
}
|
|
293
|
-
if (
|
|
324
|
+
if (chunkSummaries.length === 0 && previousSummaries.length === 0) {
|
|
325
|
+
return null;
|
|
326
|
+
}
|
|
327
|
+
const finalSummary = await this._buildFinalSummary(
|
|
328
|
+
compressor,
|
|
329
|
+
previousSummaries,
|
|
330
|
+
chunkSummaries
|
|
331
|
+
);
|
|
332
|
+
if (!finalSummary) {
|
|
294
333
|
return null;
|
|
295
334
|
}
|
|
296
|
-
const aggregatedSummary = compressedSegments.map(
|
|
297
|
-
(segment, idx) => `### Segment ${idx + 1}
|
|
298
|
-
${segment.content.trim()}`
|
|
299
|
-
).join("\n\n");
|
|
300
|
-
const summaryMeta = {
|
|
301
|
-
source: "infinite-context",
|
|
302
|
-
segments: compressedSegments.length,
|
|
303
|
-
segmentDetail: compressedSegments.map((segment, idx) => ({
|
|
304
|
-
segment: idx + 1,
|
|
305
|
-
chunkIndex: segment.chunkIndex,
|
|
306
|
-
chunkSize: segment.chunkSize
|
|
307
|
-
}))
|
|
308
|
-
};
|
|
309
335
|
const compressedMessages = [
|
|
310
336
|
new import_messages.HumanMessage({
|
|
311
|
-
content:
|
|
312
|
-
${aggregatedSummary}
|
|
313
|
-
</infinite_context>`,
|
|
337
|
+
content: finalSummary.content,
|
|
314
338
|
name: "infinite_context",
|
|
315
|
-
additional_kwargs:
|
|
316
|
-
}),
|
|
317
|
-
new import_messages.AIMessage({
|
|
318
|
-
content: "Summary acknowledged. I will prioritise available tools when future turns involve these archived topics, and if no tools are available I will note the memory gap and ask the user to confirm the details.",
|
|
319
|
-
name: "infinite_context_ack",
|
|
320
|
-
additional_kwargs: summaryMeta
|
|
339
|
+
additional_kwargs: finalSummary.meta
|
|
321
340
|
})
|
|
322
341
|
];
|
|
323
342
|
const mergedMessages = [
|
|
@@ -345,6 +364,32 @@ ${aggregatedSummary}
|
|
|
345
364
|
const content = (0, import_string2.getMessageContent)(message?.content ?? "");
|
|
346
365
|
return typeof content === "string" && /<\/?infinite_context/iu.test(content);
|
|
347
366
|
}
|
|
367
|
+
_isToolRelatedMessage(message) {
|
|
368
|
+
if (message.getType() === "tool") {
|
|
369
|
+
return true;
|
|
370
|
+
}
|
|
371
|
+
const anyMessage = message;
|
|
372
|
+
if (Array.isArray(anyMessage.tool_calls) && anyMessage.tool_calls.length > 0) {
|
|
373
|
+
return true;
|
|
374
|
+
}
|
|
375
|
+
const additionalToolCalls = anyMessage.additional_kwargs?.["tool_calls"];
|
|
376
|
+
return Array.isArray(additionalToolCalls) && additionalToolCalls.length > 0;
|
|
377
|
+
}
|
|
378
|
+
async _rewriteChatHistory(messages) {
|
|
379
|
+
const additionalArgs = {
|
|
380
|
+
...await this.options.chatHistory.getAdditionalArgs()
|
|
381
|
+
};
|
|
382
|
+
await this.options.chatHistory.clear();
|
|
383
|
+
for (const message of messages) {
|
|
384
|
+
await this.options.chatHistory.addMessage(message);
|
|
385
|
+
}
|
|
386
|
+
if (Object.keys(additionalArgs).length > 0) {
|
|
387
|
+
await this.options.chatHistory.overrideAdditionalArgs(
|
|
388
|
+
additionalArgs
|
|
389
|
+
);
|
|
390
|
+
}
|
|
391
|
+
await this.options.chatHistory.loadConversation();
|
|
392
|
+
}
|
|
348
393
|
_splitChunksForCompression(stats, maxTokenLimit) {
|
|
349
394
|
const chunkTokenTarget = Math.max(Math.floor(maxTokenLimit * 0.15), 300);
|
|
350
395
|
const chunks = [];
|
|
@@ -384,33 +429,8 @@ ${aggregatedSummary}
|
|
|
384
429
|
const role = message.getType().toUpperCase();
|
|
385
430
|
const nameSuffix = message.name ? ` (${message.name})` : "";
|
|
386
431
|
const content = (0, import_string2.getMessageContent)(message.content).trim();
|
|
387
|
-
const extras = [];
|
|
388
|
-
const aiMessage = message;
|
|
389
|
-
if (Array.isArray(aiMessage.tool_calls) && aiMessage.tool_calls.length > 0) {
|
|
390
|
-
const toolCalls = aiMessage.tool_calls.map((call) => {
|
|
391
|
-
let args = "";
|
|
392
|
-
try {
|
|
393
|
-
args = JSON.stringify(call.args);
|
|
394
|
-
} catch (error) {
|
|
395
|
-
args = "[unserializable]";
|
|
396
|
-
}
|
|
397
|
-
return `${call.name} => ${args}`;
|
|
398
|
-
}).join("; ");
|
|
399
|
-
extras.push(`tool calls: ${toolCalls}`);
|
|
400
|
-
}
|
|
401
|
-
if (message.getType() === "tool") {
|
|
402
|
-
const toolMessage = message;
|
|
403
|
-
if (toolMessage.tool_call_id) {
|
|
404
|
-
extras.push(`tool call id: ${toolMessage.tool_call_id}`);
|
|
405
|
-
}
|
|
406
|
-
if (toolMessage.name) {
|
|
407
|
-
extras.push(`tool name: ${toolMessage.name}`);
|
|
408
|
-
}
|
|
409
|
-
}
|
|
410
|
-
const extraText = extras.length > 0 ? `
|
|
411
|
-
Meta: ${extras.join(", ")}` : "";
|
|
412
432
|
return `[${role}${nameSuffix}]
|
|
413
|
-
${content || "(empty)"}
|
|
433
|
+
${content || "(empty)"}`;
|
|
414
434
|
}).join("\n---\n");
|
|
415
435
|
}
|
|
416
436
|
_ensureInfiniteContextChain(wrapper) {
|
|
@@ -421,6 +441,64 @@ ${content || "(empty)"}${extraText}`;
|
|
|
421
441
|
}
|
|
422
442
|
return this._chain;
|
|
423
443
|
}
|
|
444
|
+
async _buildFinalSummary(compressor, previousSummaries, chunkSummaries) {
|
|
445
|
+
const cleanedPrevious = previousSummaries.filter(
|
|
446
|
+
(text) => text.trim().length > 0
|
|
447
|
+
);
|
|
448
|
+
const cleanedChunks = chunkSummaries.filter(
|
|
449
|
+
(summary) => summary.content.trim().length > 0
|
|
450
|
+
);
|
|
451
|
+
if (cleanedPrevious.length === 0 && cleanedChunks.length === 0) {
|
|
452
|
+
return null;
|
|
453
|
+
}
|
|
454
|
+
if (cleanedPrevious.length === 0 && cleanedChunks.length === 1) {
|
|
455
|
+
return {
|
|
456
|
+
content: cleanedChunks[0].content.trim(),
|
|
457
|
+
meta: {
|
|
458
|
+
source: "infinite-context",
|
|
459
|
+
mergedSegments: 1,
|
|
460
|
+
previousSummaries: 0,
|
|
461
|
+
chunkDetail: [
|
|
462
|
+
{
|
|
463
|
+
chunkIndex: cleanedChunks[0].chunkIndex,
|
|
464
|
+
chunkSize: cleanedChunks[0].chunkSize
|
|
465
|
+
}
|
|
466
|
+
]
|
|
467
|
+
}
|
|
468
|
+
};
|
|
469
|
+
}
|
|
470
|
+
const virtualTranscript = [];
|
|
471
|
+
if (cleanedPrevious.length > 0) {
|
|
472
|
+
virtualTranscript.push(
|
|
473
|
+
`Existing summary snapshot:
|
|
474
|
+
${cleanedPrevious.join("\n\n")}`
|
|
475
|
+
);
|
|
476
|
+
}
|
|
477
|
+
cleanedChunks.forEach((chunk, index) => {
|
|
478
|
+
virtualTranscript.push(
|
|
479
|
+
`Recent segment ${index + 1} (${chunk.chunkSize} turns):
|
|
480
|
+
${chunk.content}`
|
|
481
|
+
);
|
|
482
|
+
});
|
|
483
|
+
const mergedInput = virtualTranscript.join("\n\n---\n\n");
|
|
484
|
+
const refined = await compressor.compressChunk({
|
|
485
|
+
chunk: mergedInput,
|
|
486
|
+
conversationId: this.options.conversationId
|
|
487
|
+
});
|
|
488
|
+
const content = refined?.trim() || mergedInput;
|
|
489
|
+
return {
|
|
490
|
+
content,
|
|
491
|
+
meta: {
|
|
492
|
+
source: "infinite-context",
|
|
493
|
+
mergedSegments: cleanedChunks.length,
|
|
494
|
+
previousSummaries: cleanedPrevious.length,
|
|
495
|
+
chunkDetail: cleanedChunks.map((chunk) => ({
|
|
496
|
+
chunkIndex: chunk.chunkIndex,
|
|
497
|
+
chunkSize: chunk.chunkSize
|
|
498
|
+
}))
|
|
499
|
+
}
|
|
500
|
+
};
|
|
501
|
+
}
|
|
424
502
|
};
|
|
425
503
|
|
|
426
504
|
// src/llm-core/chat/app.ts
|
|
@@ -445,7 +523,7 @@ var ChatInterface = class {
|
|
|
445
523
|
_historyMemory;
|
|
446
524
|
_infiniteContextManager;
|
|
447
525
|
_chatCount = 0;
|
|
448
|
-
async handleChatError(arg, wrapper, error) {
|
|
526
|
+
async handleChatError(arg, wrapper, error, throwError = true) {
|
|
449
527
|
await this.ctx.parallel(
|
|
450
528
|
"chatluna/after-chat-error",
|
|
451
529
|
error,
|
|
@@ -455,6 +533,9 @@ var ChatInterface = class {
|
|
|
455
533
|
this,
|
|
456
534
|
wrapper
|
|
457
535
|
);
|
|
536
|
+
if (!throwError) {
|
|
537
|
+
return;
|
|
538
|
+
}
|
|
458
539
|
if (error instanceof import_error2.ChatLunaError && error.errorCode === import_error2.ChatLunaErrorCode.API_UNSAFE_CONTENT) {
|
|
459
540
|
throw error;
|
|
460
541
|
}
|
|
@@ -561,15 +642,19 @@ var ChatInterface = class {
|
|
|
561
642
|
}
|
|
562
643
|
await this.chatHistory.addMessage(saveMessage);
|
|
563
644
|
}
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
645
|
+
try {
|
|
646
|
+
await this.ctx.parallel(
|
|
647
|
+
"chatluna/after-chat",
|
|
648
|
+
arg.conversationId,
|
|
649
|
+
arg.message,
|
|
650
|
+
displayResponse,
|
|
651
|
+
{ ...arg.variables, chatCount: this._chatCount },
|
|
652
|
+
this,
|
|
653
|
+
arg.session
|
|
654
|
+
);
|
|
655
|
+
} catch (error) {
|
|
656
|
+
await this.handleChatError(arg, wrapper, error, false);
|
|
657
|
+
}
|
|
573
658
|
return { message: displayResponse };
|
|
574
659
|
}
|
|
575
660
|
async handlePostProcessing(arg, message) {
|
|
@@ -20,15 +20,12 @@ import { ChatLunaChatModel } from "koishi-plugin-chatluna/llm-core/platform/mode
|
|
|
20
20
|
import {
|
|
21
21
|
ModelCapabilities
|
|
22
22
|
} from "koishi-plugin-chatluna/llm-core/platform/types";
|
|
23
|
-
import { AIMessage
|
|
23
|
+
import { AIMessage, ToolMessage } from "@langchain/core/messages";
|
|
24
24
|
import { getMessageContent as getMessageContent3 } from "koishi-plugin-chatluna/utils/string";
|
|
25
25
|
import { computed } from "@vue/reactivity";
|
|
26
26
|
|
|
27
27
|
// src/llm-core/chat/infinite_context.ts
|
|
28
|
-
import {
|
|
29
|
-
AIMessage,
|
|
30
|
-
HumanMessage
|
|
31
|
-
} from "@langchain/core/messages";
|
|
28
|
+
import { HumanMessage } from "@langchain/core/messages";
|
|
32
29
|
import { getMessageContent as getMessageContent2 } from "koishi-plugin-chatluna/utils/string";
|
|
33
30
|
import { logger } from "koishi-plugin-chatluna";
|
|
34
31
|
|
|
@@ -185,12 +182,40 @@ var InfiniteContextManager = class {
|
|
|
185
182
|
logger.info(
|
|
186
183
|
`[InfiniteContext] Start compression with total tokens: ${totalTokens}, threshold: ${threshold}`
|
|
187
184
|
);
|
|
185
|
+
const filteredMessages = messages.filter(
|
|
186
|
+
(message) => !this._isToolRelatedMessage(message)
|
|
187
|
+
);
|
|
188
|
+
if (filteredMessages.length === 0) {
|
|
189
|
+
return;
|
|
190
|
+
}
|
|
191
|
+
const filteredStats = await this._calculateMessageTokenStats(
|
|
192
|
+
model,
|
|
193
|
+
filteredMessages
|
|
194
|
+
);
|
|
195
|
+
const filteredTotalTokens = filteredStats.reduce((sum, current) => sum + current.tokens, 0) + presetTokens;
|
|
196
|
+
if (filteredTotalTokens <= threshold) {
|
|
197
|
+
await this._rewriteChatHistory(filteredMessages);
|
|
198
|
+
logger.info(
|
|
199
|
+
"[InfiniteContext] Filtered tool-related messages reduced tokens from %d to %d",
|
|
200
|
+
totalTokens,
|
|
201
|
+
filteredTotalTokens
|
|
202
|
+
);
|
|
203
|
+
return;
|
|
204
|
+
}
|
|
188
205
|
const compressionResult = await this._compressMessages(
|
|
189
206
|
wrapper,
|
|
190
|
-
|
|
207
|
+
filteredStats,
|
|
191
208
|
maxTokenLimit
|
|
192
209
|
);
|
|
193
210
|
if (!compressionResult) {
|
|
211
|
+
if (filteredMessages.length !== messages.length) {
|
|
212
|
+
await this._rewriteChatHistory(filteredMessages);
|
|
213
|
+
logger.info(
|
|
214
|
+
"[InfiniteContext] Filtered tool-related messages (compression skipped) reduced tokens from %d to %d",
|
|
215
|
+
totalTokens,
|
|
216
|
+
filteredTotalTokens
|
|
217
|
+
);
|
|
218
|
+
}
|
|
194
219
|
return;
|
|
195
220
|
}
|
|
196
221
|
const { messages: rewrittenMessages, tokenCount } = compressionResult;
|
|
@@ -243,12 +268,9 @@ var InfiniteContextManager = class {
|
|
|
243
268
|
0,
|
|
244
269
|
contentStats.length - preserveCount
|
|
245
270
|
);
|
|
246
|
-
compressible = contentStats.filter(
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
}
|
|
250
|
-
return index < thresholdIndex;
|
|
251
|
-
});
|
|
271
|
+
compressible = contentStats.filter(
|
|
272
|
+
(stat, index) => index < thresholdIndex
|
|
273
|
+
);
|
|
252
274
|
if (compressible.length > 0) {
|
|
253
275
|
break;
|
|
254
276
|
}
|
|
@@ -269,10 +291,16 @@ var InfiniteContextManager = class {
|
|
|
269
291
|
return null;
|
|
270
292
|
}
|
|
271
293
|
const compressor = this._ensureInfiniteContextChain(wrapper);
|
|
272
|
-
const
|
|
294
|
+
const chunkSummaries = [];
|
|
295
|
+
const previousSummaries = compressible.filter((stat) => this._isCompressedMessage(stat.message)).map(
|
|
296
|
+
(stat) => getMessageContent2(stat.message.content)?.trim() ?? ""
|
|
297
|
+
).filter((text) => text.length > 0);
|
|
273
298
|
for (let index = 0; index < chunkStats.length; index++) {
|
|
274
299
|
const chunk = chunkStats[index];
|
|
275
|
-
const chunkMessages = chunk.map((item) => item.message);
|
|
300
|
+
const chunkMessages = chunk.map((item) => item.message).filter((message) => !this._isCompressedMessage(message));
|
|
301
|
+
if (chunkMessages.length === 0) {
|
|
302
|
+
continue;
|
|
303
|
+
}
|
|
276
304
|
const chunkText = this._formatChunkForCompression(chunkMessages);
|
|
277
305
|
const compressedText = await compressor.compressChunk({
|
|
278
306
|
chunk: chunkText,
|
|
@@ -281,40 +309,28 @@ var InfiniteContextManager = class {
|
|
|
281
309
|
if (!compressedText) {
|
|
282
310
|
continue;
|
|
283
311
|
}
|
|
284
|
-
|
|
312
|
+
chunkSummaries.push({
|
|
285
313
|
content: compressedText,
|
|
286
314
|
chunkIndex: index,
|
|
287
315
|
chunkSize: chunkMessages.length
|
|
288
316
|
});
|
|
289
317
|
}
|
|
290
|
-
if (
|
|
318
|
+
if (chunkSummaries.length === 0 && previousSummaries.length === 0) {
|
|
319
|
+
return null;
|
|
320
|
+
}
|
|
321
|
+
const finalSummary = await this._buildFinalSummary(
|
|
322
|
+
compressor,
|
|
323
|
+
previousSummaries,
|
|
324
|
+
chunkSummaries
|
|
325
|
+
);
|
|
326
|
+
if (!finalSummary) {
|
|
291
327
|
return null;
|
|
292
328
|
}
|
|
293
|
-
const aggregatedSummary = compressedSegments.map(
|
|
294
|
-
(segment, idx) => `### Segment ${idx + 1}
|
|
295
|
-
${segment.content.trim()}`
|
|
296
|
-
).join("\n\n");
|
|
297
|
-
const summaryMeta = {
|
|
298
|
-
source: "infinite-context",
|
|
299
|
-
segments: compressedSegments.length,
|
|
300
|
-
segmentDetail: compressedSegments.map((segment, idx) => ({
|
|
301
|
-
segment: idx + 1,
|
|
302
|
-
chunkIndex: segment.chunkIndex,
|
|
303
|
-
chunkSize: segment.chunkSize
|
|
304
|
-
}))
|
|
305
|
-
};
|
|
306
329
|
const compressedMessages = [
|
|
307
330
|
new HumanMessage({
|
|
308
|
-
content:
|
|
309
|
-
${aggregatedSummary}
|
|
310
|
-
</infinite_context>`,
|
|
331
|
+
content: finalSummary.content,
|
|
311
332
|
name: "infinite_context",
|
|
312
|
-
additional_kwargs:
|
|
313
|
-
}),
|
|
314
|
-
new AIMessage({
|
|
315
|
-
content: "Summary acknowledged. I will prioritise available tools when future turns involve these archived topics, and if no tools are available I will note the memory gap and ask the user to confirm the details.",
|
|
316
|
-
name: "infinite_context_ack",
|
|
317
|
-
additional_kwargs: summaryMeta
|
|
333
|
+
additional_kwargs: finalSummary.meta
|
|
318
334
|
})
|
|
319
335
|
];
|
|
320
336
|
const mergedMessages = [
|
|
@@ -342,6 +358,32 @@ ${aggregatedSummary}
|
|
|
342
358
|
const content = getMessageContent2(message?.content ?? "");
|
|
343
359
|
return typeof content === "string" && /<\/?infinite_context/iu.test(content);
|
|
344
360
|
}
|
|
361
|
+
_isToolRelatedMessage(message) {
|
|
362
|
+
if (message.getType() === "tool") {
|
|
363
|
+
return true;
|
|
364
|
+
}
|
|
365
|
+
const anyMessage = message;
|
|
366
|
+
if (Array.isArray(anyMessage.tool_calls) && anyMessage.tool_calls.length > 0) {
|
|
367
|
+
return true;
|
|
368
|
+
}
|
|
369
|
+
const additionalToolCalls = anyMessage.additional_kwargs?.["tool_calls"];
|
|
370
|
+
return Array.isArray(additionalToolCalls) && additionalToolCalls.length > 0;
|
|
371
|
+
}
|
|
372
|
+
async _rewriteChatHistory(messages) {
|
|
373
|
+
const additionalArgs = {
|
|
374
|
+
...await this.options.chatHistory.getAdditionalArgs()
|
|
375
|
+
};
|
|
376
|
+
await this.options.chatHistory.clear();
|
|
377
|
+
for (const message of messages) {
|
|
378
|
+
await this.options.chatHistory.addMessage(message);
|
|
379
|
+
}
|
|
380
|
+
if (Object.keys(additionalArgs).length > 0) {
|
|
381
|
+
await this.options.chatHistory.overrideAdditionalArgs(
|
|
382
|
+
additionalArgs
|
|
383
|
+
);
|
|
384
|
+
}
|
|
385
|
+
await this.options.chatHistory.loadConversation();
|
|
386
|
+
}
|
|
345
387
|
_splitChunksForCompression(stats, maxTokenLimit) {
|
|
346
388
|
const chunkTokenTarget = Math.max(Math.floor(maxTokenLimit * 0.15), 300);
|
|
347
389
|
const chunks = [];
|
|
@@ -381,33 +423,8 @@ ${aggregatedSummary}
|
|
|
381
423
|
const role = message.getType().toUpperCase();
|
|
382
424
|
const nameSuffix = message.name ? ` (${message.name})` : "";
|
|
383
425
|
const content = getMessageContent2(message.content).trim();
|
|
384
|
-
const extras = [];
|
|
385
|
-
const aiMessage = message;
|
|
386
|
-
if (Array.isArray(aiMessage.tool_calls) && aiMessage.tool_calls.length > 0) {
|
|
387
|
-
const toolCalls = aiMessage.tool_calls.map((call) => {
|
|
388
|
-
let args = "";
|
|
389
|
-
try {
|
|
390
|
-
args = JSON.stringify(call.args);
|
|
391
|
-
} catch (error) {
|
|
392
|
-
args = "[unserializable]";
|
|
393
|
-
}
|
|
394
|
-
return `${call.name} => ${args}`;
|
|
395
|
-
}).join("; ");
|
|
396
|
-
extras.push(`tool calls: ${toolCalls}`);
|
|
397
|
-
}
|
|
398
|
-
if (message.getType() === "tool") {
|
|
399
|
-
const toolMessage = message;
|
|
400
|
-
if (toolMessage.tool_call_id) {
|
|
401
|
-
extras.push(`tool call id: ${toolMessage.tool_call_id}`);
|
|
402
|
-
}
|
|
403
|
-
if (toolMessage.name) {
|
|
404
|
-
extras.push(`tool name: ${toolMessage.name}`);
|
|
405
|
-
}
|
|
406
|
-
}
|
|
407
|
-
const extraText = extras.length > 0 ? `
|
|
408
|
-
Meta: ${extras.join(", ")}` : "";
|
|
409
426
|
return `[${role}${nameSuffix}]
|
|
410
|
-
${content || "(empty)"}
|
|
427
|
+
${content || "(empty)"}`;
|
|
411
428
|
}).join("\n---\n");
|
|
412
429
|
}
|
|
413
430
|
_ensureInfiniteContextChain(wrapper) {
|
|
@@ -418,6 +435,64 @@ ${content || "(empty)"}${extraText}`;
|
|
|
418
435
|
}
|
|
419
436
|
return this._chain;
|
|
420
437
|
}
|
|
438
|
+
async _buildFinalSummary(compressor, previousSummaries, chunkSummaries) {
|
|
439
|
+
const cleanedPrevious = previousSummaries.filter(
|
|
440
|
+
(text) => text.trim().length > 0
|
|
441
|
+
);
|
|
442
|
+
const cleanedChunks = chunkSummaries.filter(
|
|
443
|
+
(summary) => summary.content.trim().length > 0
|
|
444
|
+
);
|
|
445
|
+
if (cleanedPrevious.length === 0 && cleanedChunks.length === 0) {
|
|
446
|
+
return null;
|
|
447
|
+
}
|
|
448
|
+
if (cleanedPrevious.length === 0 && cleanedChunks.length === 1) {
|
|
449
|
+
return {
|
|
450
|
+
content: cleanedChunks[0].content.trim(),
|
|
451
|
+
meta: {
|
|
452
|
+
source: "infinite-context",
|
|
453
|
+
mergedSegments: 1,
|
|
454
|
+
previousSummaries: 0,
|
|
455
|
+
chunkDetail: [
|
|
456
|
+
{
|
|
457
|
+
chunkIndex: cleanedChunks[0].chunkIndex,
|
|
458
|
+
chunkSize: cleanedChunks[0].chunkSize
|
|
459
|
+
}
|
|
460
|
+
]
|
|
461
|
+
}
|
|
462
|
+
};
|
|
463
|
+
}
|
|
464
|
+
const virtualTranscript = [];
|
|
465
|
+
if (cleanedPrevious.length > 0) {
|
|
466
|
+
virtualTranscript.push(
|
|
467
|
+
`Existing summary snapshot:
|
|
468
|
+
${cleanedPrevious.join("\n\n")}`
|
|
469
|
+
);
|
|
470
|
+
}
|
|
471
|
+
cleanedChunks.forEach((chunk, index) => {
|
|
472
|
+
virtualTranscript.push(
|
|
473
|
+
`Recent segment ${index + 1} (${chunk.chunkSize} turns):
|
|
474
|
+
${chunk.content}`
|
|
475
|
+
);
|
|
476
|
+
});
|
|
477
|
+
const mergedInput = virtualTranscript.join("\n\n---\n\n");
|
|
478
|
+
const refined = await compressor.compressChunk({
|
|
479
|
+
chunk: mergedInput,
|
|
480
|
+
conversationId: this.options.conversationId
|
|
481
|
+
});
|
|
482
|
+
const content = refined?.trim() || mergedInput;
|
|
483
|
+
return {
|
|
484
|
+
content,
|
|
485
|
+
meta: {
|
|
486
|
+
source: "infinite-context",
|
|
487
|
+
mergedSegments: cleanedChunks.length,
|
|
488
|
+
previousSummaries: cleanedPrevious.length,
|
|
489
|
+
chunkDetail: cleanedChunks.map((chunk) => ({
|
|
490
|
+
chunkIndex: chunk.chunkIndex,
|
|
491
|
+
chunkSize: chunk.chunkSize
|
|
492
|
+
}))
|
|
493
|
+
}
|
|
494
|
+
};
|
|
495
|
+
}
|
|
421
496
|
};
|
|
422
497
|
|
|
423
498
|
// src/llm-core/chat/app.ts
|
|
@@ -442,7 +517,7 @@ var ChatInterface = class {
|
|
|
442
517
|
_historyMemory;
|
|
443
518
|
_infiniteContextManager;
|
|
444
519
|
_chatCount = 0;
|
|
445
|
-
async handleChatError(arg, wrapper, error) {
|
|
520
|
+
async handleChatError(arg, wrapper, error, throwError = true) {
|
|
446
521
|
await this.ctx.parallel(
|
|
447
522
|
"chatluna/after-chat-error",
|
|
448
523
|
error,
|
|
@@ -452,6 +527,9 @@ var ChatInterface = class {
|
|
|
452
527
|
this,
|
|
453
528
|
wrapper
|
|
454
529
|
);
|
|
530
|
+
if (!throwError) {
|
|
531
|
+
return;
|
|
532
|
+
}
|
|
455
533
|
if (error instanceof ChatLunaError2 && error.errorCode === ChatLunaErrorCode2.API_UNSAFE_CONTENT) {
|
|
456
534
|
throw error;
|
|
457
535
|
}
|
|
@@ -510,7 +588,7 @@ var ChatInterface = class {
|
|
|
510
588
|
maxToken: this.preset?.value?.config?.maxOutputToken
|
|
511
589
|
});
|
|
512
590
|
const responseMessage = response.message;
|
|
513
|
-
const displayResponse = new
|
|
591
|
+
const displayResponse = new AIMessage({
|
|
514
592
|
content: responseMessage.content
|
|
515
593
|
});
|
|
516
594
|
displayResponse.additional_kwargs = responseMessage.additional_kwargs;
|
|
@@ -536,7 +614,7 @@ var ChatInterface = class {
|
|
|
536
614
|
const intermediateSteps = response["parallelIntermediateSteps"];
|
|
537
615
|
for (const parallelSteps of intermediateSteps) {
|
|
538
616
|
await this.chatHistory.addMessage(
|
|
539
|
-
new
|
|
617
|
+
new AIMessage({
|
|
540
618
|
content: "",
|
|
541
619
|
tool_calls: parallelSteps.map((step) => ({
|
|
542
620
|
id: step.action.toolCallId,
|
|
@@ -547,7 +625,7 @@ var ChatInterface = class {
|
|
|
547
625
|
);
|
|
548
626
|
for (const step of parallelSteps) {
|
|
549
627
|
await this.chatHistory.addMessage(
|
|
550
|
-
new
|
|
628
|
+
new ToolMessage({
|
|
551
629
|
content: step.observation,
|
|
552
630
|
tool_call_id: step.action.toolCallId,
|
|
553
631
|
name: step.action.tool
|
|
@@ -558,15 +636,19 @@ var ChatInterface = class {
|
|
|
558
636
|
}
|
|
559
637
|
await this.chatHistory.addMessage(saveMessage);
|
|
560
638
|
}
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
639
|
+
try {
|
|
640
|
+
await this.ctx.parallel(
|
|
641
|
+
"chatluna/after-chat",
|
|
642
|
+
arg.conversationId,
|
|
643
|
+
arg.message,
|
|
644
|
+
displayResponse,
|
|
645
|
+
{ ...arg.variables, chatCount: this._chatCount },
|
|
646
|
+
this,
|
|
647
|
+
arg.session
|
|
648
|
+
);
|
|
649
|
+
} catch (error) {
|
|
650
|
+
await this.handleChatError(arg, wrapper, error, false);
|
|
651
|
+
}
|
|
570
652
|
return { message: displayResponse };
|
|
571
653
|
}
|
|
572
654
|
async handlePostProcessing(arg, message) {
|
|
@@ -14,9 +14,12 @@ export declare class InfiniteContextManager {
|
|
|
14
14
|
compressIfNeeded(wrapper: ChatLunaLLMChainWrapper): Promise<void>;
|
|
15
15
|
private _compressMessages;
|
|
16
16
|
private _isCompressedMessage;
|
|
17
|
+
private _isToolRelatedMessage;
|
|
18
|
+
private _rewriteChatHistory;
|
|
17
19
|
private _splitChunksForCompression;
|
|
18
20
|
private _calculateMessageTokenStats;
|
|
19
21
|
private _countMessagesTokens;
|
|
20
22
|
private _formatChunkForCompression;
|
|
21
23
|
private _ensureInfiniteContextChain;
|
|
24
|
+
private _buildFinalSummary;
|
|
22
25
|
}
|
|
@@ -234,6 +234,10 @@ var ChatLunaChatModel = class extends import_chat_models.BaseChatModel {
|
|
|
234
234
|
if (maxTokenLimit != null && maxTokenLimit >= this.getModelMaxContextSize()) {
|
|
235
235
|
maxTokenLimit = this.getModelMaxContextSize();
|
|
236
236
|
}
|
|
237
|
+
let id = options?.id ?? this._options.id;
|
|
238
|
+
if (!id) {
|
|
239
|
+
id = options?.variables_hide?.["built"]?.["conversationId"];
|
|
240
|
+
}
|
|
237
241
|
return {
|
|
238
242
|
model: modelName,
|
|
239
243
|
temperature: options?.temperature ?? this._options.temperature,
|
|
@@ -244,12 +248,12 @@ var ChatLunaChatModel = class extends import_chat_models.BaseChatModel {
|
|
|
244
248
|
logitBias: options?.logitBias ?? this._options.logitBias,
|
|
245
249
|
maxTokens: options?.maxTokens ?? this._options.maxTokens,
|
|
246
250
|
maxTokenLimit,
|
|
247
|
-
variables: options?.["variables_hide"] ?? {},
|
|
251
|
+
variables: options?.["variables_hide"] ?? options?.["variables"] ?? {},
|
|
248
252
|
overrideRequestParams: options?.overrideRequestParams ?? this._options.overrideRequestParams ?? {},
|
|
249
253
|
stop: options?.stop ?? this._options.stop,
|
|
250
254
|
stream: options?.stream ?? this._options.stream,
|
|
251
255
|
tools: options?.tools ?? this._options.tools,
|
|
252
|
-
id
|
|
256
|
+
id,
|
|
253
257
|
signal: options?.signal ?? this._options.signal,
|
|
254
258
|
timeout: options?.timeout ?? this._options.timeout
|
|
255
259
|
};
|
|
@@ -216,6 +216,10 @@ var ChatLunaChatModel = class extends BaseChatModel {
|
|
|
216
216
|
if (maxTokenLimit != null && maxTokenLimit >= this.getModelMaxContextSize()) {
|
|
217
217
|
maxTokenLimit = this.getModelMaxContextSize();
|
|
218
218
|
}
|
|
219
|
+
let id = options?.id ?? this._options.id;
|
|
220
|
+
if (!id) {
|
|
221
|
+
id = options?.variables_hide?.["built"]?.["conversationId"];
|
|
222
|
+
}
|
|
219
223
|
return {
|
|
220
224
|
model: modelName,
|
|
221
225
|
temperature: options?.temperature ?? this._options.temperature,
|
|
@@ -226,12 +230,12 @@ var ChatLunaChatModel = class extends BaseChatModel {
|
|
|
226
230
|
logitBias: options?.logitBias ?? this._options.logitBias,
|
|
227
231
|
maxTokens: options?.maxTokens ?? this._options.maxTokens,
|
|
228
232
|
maxTokenLimit,
|
|
229
|
-
variables: options?.["variables_hide"] ?? {},
|
|
233
|
+
variables: options?.["variables_hide"] ?? options?.["variables"] ?? {},
|
|
230
234
|
overrideRequestParams: options?.overrideRequestParams ?? this._options.overrideRequestParams ?? {},
|
|
231
235
|
stop: options?.stop ?? this._options.stop,
|
|
232
236
|
stream: options?.stream ?? this._options.stream,
|
|
233
237
|
tools: options?.tools ?? this._options.tools,
|
|
234
|
-
id
|
|
238
|
+
id,
|
|
235
239
|
signal: options?.signal ?? this._options.signal,
|
|
236
240
|
timeout: options?.timeout ?? this._options.timeout
|
|
237
241
|
};
|
package/lib/utils/string.cjs
CHANGED
|
@@ -330,6 +330,7 @@ function getSystemPromptVariables(session, config, room) {
|
|
|
330
330
|
group_id: session.guildId ?? session.event?.guild?.id,
|
|
331
331
|
group_name: session.event?.guild?.name || session.guildId,
|
|
332
332
|
user_id: session.author?.user?.id ?? session.event?.user?.id ?? session.userId ?? "0",
|
|
333
|
+
platform: session.platform,
|
|
333
334
|
user: getNotEmptyString(
|
|
334
335
|
session.author?.nick,
|
|
335
336
|
session.author?.name,
|
|
@@ -338,6 +339,7 @@ function getSystemPromptVariables(session, config, room) {
|
|
|
338
339
|
),
|
|
339
340
|
built: {
|
|
340
341
|
preset: room.preset,
|
|
342
|
+
platform: session.platform,
|
|
341
343
|
conversationId: room.conversationId
|
|
342
344
|
},
|
|
343
345
|
noop: "",
|
package/lib/utils/string.d.ts
CHANGED
|
@@ -45,9 +45,11 @@ export declare function getSystemPromptVariables(session: Session, config: Confi
|
|
|
45
45
|
group_id: string;
|
|
46
46
|
group_name: string;
|
|
47
47
|
user_id: string;
|
|
48
|
+
platform: string;
|
|
48
49
|
user: string;
|
|
49
50
|
built: {
|
|
50
51
|
preset: string;
|
|
52
|
+
platform: string;
|
|
51
53
|
conversationId: string;
|
|
52
54
|
};
|
|
53
55
|
noop: string;
|
package/lib/utils/string.mjs
CHANGED
|
@@ -277,6 +277,7 @@ function getSystemPromptVariables(session, config, room) {
|
|
|
277
277
|
group_id: session.guildId ?? session.event?.guild?.id,
|
|
278
278
|
group_name: session.event?.guild?.name || session.guildId,
|
|
279
279
|
user_id: session.author?.user?.id ?? session.event?.user?.id ?? session.userId ?? "0",
|
|
280
|
+
platform: session.platform,
|
|
280
281
|
user: getNotEmptyString(
|
|
281
282
|
session.author?.nick,
|
|
282
283
|
session.author?.name,
|
|
@@ -285,6 +286,7 @@ function getSystemPromptVariables(session, config, room) {
|
|
|
285
286
|
),
|
|
286
287
|
built: {
|
|
287
288
|
preset: room.preset,
|
|
289
|
+
platform: session.platform,
|
|
288
290
|
conversationId: room.conversationId
|
|
289
291
|
},
|
|
290
292
|
noop: "",
|