From d4f4639079eb19ba9d688609935c25089df311c7 Mon Sep 17 00:00:00 2001 From: Wx-2025 <351320169@qq.com> Date: Tue, 23 Dec 2025 08:22:00 +0800 Subject: [PATCH] =?UTF-8?q?=E9=87=8D=E6=9E=84=E6=AC=A1=E8=A6=81=E5=A1=AB?= =?UTF-8?q?=E5=85=85=E6=B6=88=E6=81=AF=E5=A4=84=E7=90=86=E9=80=BB=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 重构次要填充逻辑以改进消息处理及批处理和实时模式的处理。 --- core/table-system/secondary-filler.js | 44 +++------------------------ 1 file changed, 4 insertions(+), 40 deletions(-) diff --git a/core/table-system/secondary-filler.js b/core/table-system/secondary-filler.js index 7011091..68cc8cf 100644 --- a/core/table-system/secondary-filler.js +++ b/core/table-system/secondary-filler.js @@ -96,17 +96,13 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { } try { - // --- 分步/批量填表逻辑 (重构版) --- const bufferSize = parseInt(settings.secondary_filler_buffer || 0, 10); - const batchSize = parseInt(settings.secondary_filler_batch || 0, 10); // 0 = 实时/单条模式 + const batchSize = parseInt(settings.secondary_filler_batch || 0, 10); const contextLimit = parseInt(settings.secondary_filler_context || 2, 10); const chat = context.chat; const totalMessages = chat.length; - // 计算有效填表区域的终点(排除 Buffer) - // 例如:总长10,Buffer 2。ValidEnd = 10 - 1 - 2 = 7。 - // 即 index 8, 9 在 Buffer 内,不能填。 const validEndIndex = totalMessages - 1 - bufferSize; if (validEndIndex < 0) { @@ -114,31 +110,25 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { return; } - // 收集需要填表的目标消息 let targetMessages = []; let needsProcessing = false; - // 简单的内容哈希生成器 const getContentHash = (content) => { let hash = 0, i, chr; if (content.length === 0) return hash; for (i = 0; i < content.length; i++) { chr = content.charCodeAt(i); hash = ((hash << 5) - hash) + chr; - hash |= 0; // Convert to 32bit integer + hash |= 0; } return hash; }; - // 从 ValidEndIndex 往前扫描,寻找未处理或已变更的消息 for (let i = validEndIndex; i >= 0; i--) { const msg = chat[i]; - // 默认只处理 AI 消息用于填表核心(用户消息作为上下文) - // 如果以后需要处理用户消息填表,这里需要调整 if (msg.is_user) continue; - // 检查状态 const currentHash = getContentHash(msg.mes); const savedHash = msg.metadata?.Amily2_Process_Hash; @@ -148,38 +138,26 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { if (isUnprocessed || isChanged) { targetMessages.unshift({ index: i, msg: msg, hash: currentHash }); - // 如果是 Batch 模式,且攒够了 if (batchSize > 0 && targetMessages.length >= batchSize) { needsProcessing = true; break; } } else { - // 如果遇到一个已经处理且没变的消息 - // 在 Batch 模式下,我们要保持连续性吗? - // 假设我们只处理最新的一批未处理消息。 - // 如果中间夹杂了已处理的,我们可能应该停止扫描? - // 简化逻辑:只要遇到已处理的,就认为之前的都处理好了(除非用户回删)。 - // 为稳健起见,我们只向回扫描直到遇到已处理消息,或者扫完。 - break; + continue; } } - // 决策逻辑 if (targetMessages.length === 0) { console.log("[Amily2-副API] 没有发现需要处理的消息。"); return; } if (batchSize > 0) { - // 批量模式 if (targetMessages.length < batchSize) { - console.log(`[Amily2-副API] 批量模式: 累积 ${targetMessages.length}/${batchSize} 条,暂不触发。`); + console.log(`[Amily2-副API] 批量模式: 当前累积 ${targetMessages.length}/${batchSize} 条未处理消息,暂不触发。`); return; } } else { - // 实时模式 (Batch=0) - // 仅处理最新的一条有效消息(通常是 ValidEndIndex 那条,或者是刚重Roll的那条) - // 如果扫描出多条(比如之前关了插件),为避免瞬间大量请求,我们只取最后一条(最新的)。 targetMessages = [targetMessages[targetMessages.length - 1]]; } @@ -192,7 +170,6 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { exclusionRules = settings.table_exclusion_rules || []; } - // 构建核心处理内容 (Core Content) let coreContentText = ""; const userName = context.name1 || '用户'; const characterName = context.name2 || '角色'; @@ -216,10 +193,7 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { return; } - // 构建上下文 (History Context) - // 上下文应该截止到 targetMessages 第一条消息的前面 const historyEndIndex = targetMessages[0].index - 1; - // 使用用户设置的 history_limit (contextLimit) let historyContextStr = ""; if (contextLimit > 0 && historyEndIndex >= 0) { @@ -268,10 +242,6 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { } break; case 'contextHistory': - // 旧的 contextHistory 逻辑已被上面的 historyContextStr 替代并整合进 coreContent - // 但为了兼容 Preset 顺序,我们可以把 historyContextStr 放在这里单独发, - // 或者上面的 coreContent 只放核心内容。 - // 修正:将 historyContextStr 作为 System 消息在这里发送,currentInteractionContent 只包含 coreContent if (historyContextStr) { messages.push({ role: "system", content: historyContextStr }); } @@ -312,21 +282,15 @@ export async function fillWithSecondaryApi(latestMessage, forceRun = false) { updateTableFromText(rawContent); - // 保存状态到最后一条处理的消息(或者所有处理的消息?) - // 通常表格数据是依附在最后一条消息上的。 - // 但我们需要标记所有 processed 的消息,防止重复处理。 const memoryState = getMemoryState(); - // 我们需要把状态保存到 targetMessages 的最后一条(时间最近的一条) const lastProcessedMsg = targetMessages[targetMessages.length - 1].msg; - // 标记所有已处理消息 for (const target of targetMessages) { if (!target.msg.metadata) target.msg.metadata = {}; target.msg.metadata.Amily2_Process_Hash = target.hash; } - // 保存 MemoryState 到最后一条 if (saveStateToMessage(memoryState, lastProcessedMsg)) { renderTables(); updateOrInsertTableInChat();