import { type ConversationBackfillBot } from './backfill'; import type { ConversationLogBinding, ConversationLogEntryInput, ConversationLogMessage } from './types'; type RecallMessageIdentity = Pick; export declare const toBackfillChannelId: (binding: ConversationLogBinding) => string; /** 按会话管理滚动消息日志与历史预热。 */ export declare class MessageLogRegistry { private readonly conversations; register(conversationId: string, binding: ConversationLogBinding, bot?: ConversationBackfillBot): void; /** * 等待回填结束(成功、不支持或失败均算结束);失败后下次调用重新尝试。 * 永不 reject——回填只是历史预热,失败不应打断召回或提取。 */ warmup(conversationId: string): Promise; /** * 回填是否已成功完成(含适配器不支持而立即结束)。失败重试期间为 * false,供提取游标初始化等待回填落地,避免重试历史越过游标。 */ isWarm(conversationId: string): boolean; /** 捕获下一条实时消息之前的边界,回填完成后读取最终序号。 */ captureCursor(conversationId: string): () => number; appendLive(conversationId: string, item: ConversationLogEntryInput): boolean; appendReply(conversationId: string, items: ConversationLogEntryInput[]): void; lastN(conversationId: string, count: number): ConversationLogMessage[]; afterSeq(conversationId: string, seq: number): ConversationLogMessage[]; tailSeq(conversationId: string): number | null; /** * 召回历史读取:等待回填后取「当前触发消息之前」的最近 count 条。 * 当前消息经身份在日志中定位(与写入侧去重键同构:双方都有 messageId * 时只按 ID 判定,任一方缺失才按 (userId, timestamp, content) 三元组 * 兜底——同用户同秒重复内容的不同消息不得互相冒充)——等待回填或 * 画像读取期间追加的后续闲聊不会挤入边界,当前消息也不会与历史双份; * 定位失败退化为最近 count 条。 */ loadRecallHistory(conversationId: string, count: number, current: RecallMessageIdentity | null): Promise; /** 清条目并更新纪元;绑定保留,监听与游标读取继续。 */ clear(conversationId: string): void; dispose(): void; private appendTo; private startBackfill; } export {};