1. 概述

MemoryConfigAgentScope 框架 Agent 运行层的长期记忆流水线统一配置类,统一管理三大 LLM 驱动记忆流程的全部参数:

  • Flush(会话持久落盘记忆):从对话窗口提取长期记忆写入每日账本 memory/YYYY-MM-DD.md
  • Consolidation(记忆合并归档):定时合并多日账本,生成精简总记忆文件 MEMORY.md
  • Compaction(上下文压缩摘要):对话前缀压缩,该逻辑配置独立放在 CompactionConfig,本类仅关联不实现

2. 常量定义

常量定义解读:

// 合并操作最大Token配额默认值
public static final int DEFAULT_CONSOLIDATION_MAX_TOKENS = 4_000;
// 两次记忆合并最小间隔:30分钟
public static final Duration DEFAULT_CONSOLIDATION_MIN_GAP = Duration.ofMinutes(30);
// 每日账本保留90天后归档
public static final int DEFAULT_DAILY_FILE_RETENTION_DAYS = 90;
// 会话日志JSONL保留180天后清理
public static final int DEFAULT_SESSION_RETENTION_DAYS = 180;

3. 核心字段

核心字段说明表:

字段 类型 作用 null 逻辑 / 约束
model Model 记忆流水线专用大模型 null = 复用 Agent 主推理模型
flushPrompt String 记忆落盘阶段自定义系统提示词 null = 使用 MemoryFlushManager 默认提示词,无占位符要求
consolidationPrompt String 记忆合并阶段自定义提示词 null = 使用 MemoryConsolidator 默认提示词;自定义文本必须包含恰好 2 个 %d 占位符
consolidationMaxTokens int 记忆合并时传给 LLM 的 Token 上限 默认 4000,数值必须大于 0
consolidationMinGap Duration 两次记忆合并维护操作的最小间隔 默认 30 分钟,不允许 null、不允许负时长
dailyFileRetentionDays int 每日记忆账本文件留存天数 默认 90,数值必须大于 0,到期移入归档目录
sessionRetentionDays int 会话交互 JSONL 日志留存天数 默认 180,数值必须大于 0,到期自动清理
flushTrigger FlushTrigger 每次 Agent 调用后的记忆落盘触发策略 默认 FlushTrigger.always(),构造时禁止传入 null

4. Flush 模式

控制每次 Agent 调用时的第一层记忆落盘策略:

枚举值 含义
ALWAYS 每次 Agent 调用后强制落盘(Builder 默认值)
NEVER 关闭单次调用触发落盘,仅后台离线落盘生效
THROTTLED 节流模式,最小间隔内只执行一次落盘

4.1 节流模式

默认情况下,每次 Agent 调用结束都做一次强制落盘,对长会话来说成本不低。

Flush 存在 3 条触发路径:

  • 路径 1per-call flush(单次 Agent 调用后置落盘)
  • 路径 2:压缩前置 flush
  • 路径 3:溢出兜底 flush

注意事项:

  • THROTTLED 只影响路径 1per-call flush)。压缩前置的 flush(路径 2)和兜底 flush(路径 3)按各自的触发条件照常跑 —— 压缩很少发生,那两条本来就不频繁。
  • 用户每一轮完整对话消息(sessions/<会话ID>.log.jsonl)不受影响,session JSONL 仍然每次写完整。session_search 和会话恢复正常工作。

示例,节流到「最多每 10 分钟一次」:

        HarnessAgent agent = HarnessAgent.builder()
                .name("harness-demo")
                .description("HarnessAgent Demo")
                .model(model)
                .memory(MemoryConfig.builder()
                        .flushTrigger(MemoryConfig.FlushTrigger.throttled(Duration.ofMinutes(10)))
                        .build())
                .workspace(workspacePath)
                .maxIters(5)
                .build();

4.2 关闭模式

可完全关闭每次 call() 结束时的 Flush ,只有压缩发生时才会 Flush

示例 :

                .memory(MemoryConfig.builder()
                        .flushTrigger(MemoryConfig.FlushTrigger.never())
                        .build())

5. 关闭记忆

flushTrigger(FlushTrigger.never()) 仅关闭 Agent 每轮 call() 结束后的记忆 Flush ,使用 .disableMemoryHooks() 可以完全关闭整套记忆管线

全部禁用

  • 所有三条 Flush 触发路径(per-call / 压缩前置 / 溢出兜底)
  • 后台 Consolidation 定时合并维护任务
  • 不再生成 memory/YYYY-MM-DD.mdMEMORY.md 两层长期记忆文件

仅保留Offload 原始会话 jsonl 落盘(原始对话日志持久化不受此开关影响)

适用场景:完全不需要 Agent 跨会话记忆、不需要长期记忆汇总,只留存原始会话日志用于检索审计

关键差异对比表:

配置方式 per-call flush(路径1) 压缩前置flush(路径2) 溢出兜底flush(路径3) 后台Consolidation合并 长期记忆文件(memory/*) session jsonl原始日志offload
flushTrigger(NEVER) ❌ 关闭 ✅ 正常执行 ✅ 正常执行 ✅ 定时运行 ✅ 正常生成 ✅ 每次完整写入
.disableMemoryHooks() ❌ 关闭 ❌ 关闭 ❌ 关闭 ❌ 停止运行 ❌ 不再生成 ✅ 每次完整写入

示例:

HarnessAgent.builder()
    ...
    .disableMemoryHooks()      // 关掉 flush + 后台维护
    .disableMemoryTools()      // 不注册 memory_search / memory_get / session_search
    .build();

6. Flush 提示词

6.1 默认提示词

框架内置默认的记忆抽取提示词(翻译后):

public static final String DEFAULT_FLUSH_PROMPT =
        """
你是一名记忆提取助手。请分析下方对话内容,提取出需要留存、供后续会话参考的关键事实、决策、用户偏好与上下文信息。

仅以 Markdown 无序列表格式输出提取到的记忆内容。每条记录需简洁完整、独立表意;如有日期、人名、具体细节务必一并保留。

若无任何值得留存的信息,严格只输出:NO_REPLY

提取规范:
- 提取用户偏好、个人信息、项目相关决议
- 记录重要技术方案及背后考量依据
- 记下各类承诺、截止时间、待执行事项
- 留存人员协作关系(人员分工、团队组织架构)
- 忽略常规寒暄、工具调用过程、临时瞬时状态信息

重要写入与追加规则:
- 你本次写入的是**今日每日记忆流水账**(memory/YYYY-MM-DD.md),而非全局汇总文件 MEMORY.md。每日流水账仅支持追加写入,你的输出会追加到文件已有内容末尾。
- MEMORY.md 是整理后的长期记忆文件,仅作为只读参考上下文。不要重复记录已在 MEMORY.md 或今日早前条目里存在的内容;系统会通过独立的合并任务,定期将每日新增记录汇总至 MEMORY.md。
- 每条列表条目需独立完整,便于单独检索查询。
        """;

这是 Flush 记忆抽取流程专用系统提示词,供给 LLM 使用,对应三条 Flush 触发路径(每次调用后置、压缩前置、溢出兜底),统一指导大模型从当前对话里筛选、提炼长期记忆并按规范输出。

6.2 追加规则

复用框架内置默认的记忆抽取提示词,在末尾拼接项目专属约束规则,无需完整重写整套 flush 提示词,减少重复代码。

示例:

.memory(MemoryConfig.builder()
    // 在框架默认的记忆抽取提示词尾部,追加项目专属约束规则
    .flushPrompt(MemoryFlushManager.DEFAULT_FLUSH_PROMPT + """

        额外项目规范要求:
        - 禁止记录客户隐私敏感信息(姓名、邮箱、手机号)。
        - 项目内部专有术语统一使用中文描述。
        """)
    .build())

##3 完全自定义

可以完全自定义记忆抽取提示词,注意事项:

  • 必须包含恰好两个 %d 占位符,顺序依次为最大 Token 上限、最大字符上限。如果不满足该要求,Builder 在构建配置时会直接抛出异常拒绝创建对象。
  • 该设计目的是提前拦截配置错误,避免程序运行阶段才抛出 MissingFormatArgumentException 格式化缺失异常。

示例:

.memory(MemoryConfig.builder()
    // 完全自定义记忆合并提示词
    .consolidationPrompt("""
        你需要将多份每日记忆流水账合并汇总写入 MEMORY.md 全局长期记忆文件。
        输出内容总长度不能超过 %d Token(约 %d 字符)。以完整 Markdown 格式输出整个文件内容。
        ……此处填写你自定义的合并规则……
        """)
    .build())

7. 后台维护

配置项说明:

配置项 本次设置值 默认值 作用说明
consolidationMinGap 2小时 30分钟 控制后台合并每日账本生成MEMORY.md的最小间隔,拉长间隔减少LLM调用频次,节约token
dailyFileRetentionDays 30天 90天 每日记忆流水账YYYY-MM-DD.md留存天数,到期移入archive归档目录,释放磁盘
sessionRetentionDays 60天 180天 会话原始日志sessions/*.jsonl保存时长,到期自动删除原始对话日志
consolidationMaxTokens 8000 tokens 4000 tokens 合并生成全局长期记忆时LLM输出token上限,放宽后可容纳更多历史记忆,推理时消耗更多输入token

示例:

.memory(MemoryConfig.builder()
    // 两次后台记忆合并任务的最小间隔:至少间隔2小时才会执行一次合并
    .consolidationMinGap(Duration.ofHours(2))
    // 每日记忆账本文件(YYYY-MM-DD.md)留存30天,到期移入归档目录
    .dailyFileRetentionDays(30)
    // 会话原始日志session/*.jsonl保留60天,到期自动清理删除
    .sessionRetentionDays(60)
    // 合并生成全局长期记忆MEMORY.md时,允许LLM最大输出Token提升至8000
    .consolidationMaxTokens(8_000)
    .build())

8. 配置小模型

记忆抽取Flush)、记忆合并Consolidation)、上下文摘要压缩Compaction)都属于辅助文本加工任务,不需要强大复杂推理能力,不需要主推理级别的高精度大模型;

因此框架支持为这三类记忆流水线单独配置轻量化低成本小模型,大幅降低整体 Token 调用成本。

示例:

HarnessAgent.builder()
    .model("openai:o3")                   // 主推理模型
    .memory(MemoryConfig.builder()
        .model("openai:gpt-4.1-mini")     // 记忆操作用小模型
        .build())
    .compaction(CompactionConfig.builder()
        .model("openai:gpt-4.1-mini")     // 压缩摘要也用小模型
        .build())
    .build();

9. 记忆工具

只要开启记忆管线(不配置 .disableMemoryHooks()),框架会自动给 Agent 注册两个内置工具,Agent 可以主动调用工具查询历史记忆,弥补 MEMORY.md 容量有限、旧记忆被截断的问题。

记忆工具:

  • memory_search:全文关键词检索所有记忆文件
  • memory_get:按文件路径 + 行号分片读取详情

9.1 记忆检索工具

核心注解定义对外工具信息:

	@Tool(
        name = "memory_search",
        readOnly = true, // 只读,不会修改文件
        description = "检索长期记忆文件,查询过往工作、决策、日期、人员、偏好、待办前使用"
	)
    public String memorySearch(
            RuntimeContext runtimeContext,
            @ToolParam(name = "query", description = "Keywords to search for in memory files")
                    String query) {

入参 query:检索关键词,模糊匹配入口

核心检索逻辑

  1. 获取全部记忆文件列表:通过 workspaceManager.listMemoryFilePaths(rc) 加载 MEMORY.mdmemory/*.md
  2. 构造忽略大小写匹配规则:Pattern.quote(query) 转义特殊字符,仅纯文本匹配,不支持复杂正则
  3. 逐文件逐行遍历检索,命中记录格式 Source: 文件路径#行号: 匹配内容
  4. 组装返回结果:无匹配则返回空结果提示;有匹配则输出命中总数+全部条目

9.2 记忆分片读取工具

核心注解定义对外工具信息:

	@Tool(
        name = "memory_get",
        readOnly = true,
        description = "读取记忆文件指定行,一般在 memory_search 命中后调取完整上下文"
	)
    public String memoryGet(
            RuntimeContext runtimeContext,
            @ToolParam(
                            name = "path",
                            description =
                                    "Relative path to the memory file (e.g., MEMORY.md or"
                                            + " memory/2026-04-01.md)")
                    String path,
            @ToolParam(name = "startLine", description = "Start line number (1-based, inclusive)")
                    int startLine,
            @ToolParam(name = "endLine", description = "End line number (1-based, inclusive)")
                    int endLine) 

入参三要素

  • path:记忆文件相对工作区路径(MEMORY.md / memory/2026-06-18.md
  • startLine:起始行(从 1 开始,包含)
  • endLine:结束行(从 1 开始,包含)

核心处理逻辑

  1. 参数校验:校验文件路径非空,无参数直接返回错误
  2. 安全防护:路径归一化校验,禁止 ../ 跨工作区目录穿越
  3. 读取文件:通过工作区管理器读取目标记忆文件,文件不存在返回报错
  4. 行号转换:对外行号从1开始,内部转为数组0下标,边界截断避免越界
  5. 边界判断:起始行超过文件总行数直接返回错误提示
  6. 分段输出:循环读取指定区间行,按 行号|单行内容 格式拼接返回

9.3 协作流程

在这里插入图片描述

协作流程

  1. Agent 遇到需要查询历史跨会话信息,发现 MEMORY.md 存在 Token 截断,信息不全
  2. Agent 主动调用 memory_search,传入检索关键词
  3. memory_search 遍历所有记忆文件,返回一批命中条目(文件路径+行号+片段)
  4. Agent 根据关键命中线索,调用 memory_get,传入文件路径、起止行号
  5. memory_get 做路径安全校验,读取对应区间完整原文上下文
  6. 完整历史内容注入当前对话上下文,辅助模型完成回答
Logo

脑启社区是一个专注类脑智能领域的开发者社区。欢迎加入社区,共建类脑智能生态。社区为开发者提供了丰富的开源类脑工具软件、类脑算法模型及数据集、类脑知识库、类脑技术培训课程以及类脑应用案例等资源。

更多推荐