首页
/ Mem0 插件 tour 技能解析:按类别浏览、语义检索与跨项目汇总 AI 代理项目记忆

Mem0 插件 tour 技能解析:按类别浏览、语义检索与跨项目汇总 AI 代理项目记忆

2026-09-04 23:11:52作者:凌朦慧Richard

本文以 Mem0 插件中的 tour 技能文档为核心,完整拆解 /mem0:tour 命令的三种运行模式(单项目完整漫游、peek 紧凑检索、跨项目汇总)及其背后的 get_memories / search_memories 调用规范、过滤器构造与类别分组规则;并结合插件源码中的身份解析、项目 ID 解析、类别体系与共享检索脚本,说明这些参数在真实实现中如何被填充与消费,帮助读者在 Claude Code、Cursor、Codex 等 AI 编码环境中把 tour 作为项目记忆审阅、团队 onboarding 与知识盘点的主要入口。

一、tour 技能是什么:定位与入口

tour 是 Mem0 插件(位于 integrations/mem0-plugin 目录)内置的 17 个 slash 技能之一,定义在 skills/tour/SKILL.md。技能文件的 frontmatter 明确其用途:

Browses all stored memories grouped by category with full content display. Use when reviewing all project memories, exploring stored knowledge, onboarding to a project, or getting an overview of captured decisions, conventions, and learnings.

翻译过来即:按类别浏览当前项目已存储的全部记忆并完整展示内容,典型场景是审阅项目记忆、探索已沉淀的知识、新项目 onboarding,或总览已捕获的决策、约定与经验教训。插件 README 的技能表把它描述为 /mem0:tour —— "Browse all memories grouped by category",并将其列为安装验证步骤之一("Try /mem0:remember "we use TypeScript" then /mem0:tour to see it stored"),即写完一条记忆后立刻用 tour 验证它是否落库。

tour 与同目录下的 skills/peek/SKILL.md 是"重/轻"互补关系:peek 是带查询词的紧凑单行检索("Lighter than /mem0:tour"),tour 则是无查询词时的全量类别化浏览。tour 本身也吸收了 peek 的紧凑模式(见下文 peek mode),因此 tour 技能文档实际上覆盖了三条执行路径。

二、三条执行路径:tour 的模式路由

tour 技能文档把调用参数解析为互斥的三种模式,路由规则非常明确:

调用形式 模式 数据范围 输出形态
/mem0:tour 完整漫游 当前项目全部记忆 按类别分组、完整内容、降序计数
/mem0:tour <query> Peek mode 当前项目语义检索 紧凑单行结果
/mem0:tour --all-projects [query] 跨项目模式 全部项目 app_id 再按类别分组

文档中的路由原文:"If --all-projects is NOT present, use the standard single-project flow below"(无跨项目标志时走单项目流程);"If no query argument and no --all-projects flag, use the full tour flow below"(既无查询词也无标志时走完整漫游)。即:先判 --all-projects,再判 query 是否存在,最后才落到完整漫游。

三种模式共同依赖两个 MCP 工具——get_memories(带过滤与分页的记忆列表)和 search_memories(带过滤与重排的语义搜索)。这两个工具来自插件连接到的 Mem0 远端 MCP 服务器,连接配置见 mcp_config.json(以 MEM0_API_KEY 环境变量插值 Authorization: Token ${MEM0_API_KEY} 请求头),工具全集见 README 的 "MCP Tools" 表:add_memorysearch_memoriesget_memoriesget_memoryupdate_memorydelete_memorydelete_all_memoriesdelete_entitieslist_entities

三、完整漫游:六步执行流程

无参数调用 /mem0:tour 时,技能文档定义了六步流程。

Step 1:拉取项目全量记忆

调用 get_memories,过滤条件与分页参数固定:

filters={"AND": [{"user_id": "<active_user_id>"}, {"app_id": "<active_project_id>"}]}
page_size=100

这里的两个占位符不是装饰。user_idapp_id 正是 Mem0 平台给记忆打的两级作用域:记忆按"用户 × 项目"归属,所有检索都必须显式声明范围。插件侧对这两个值有确定性的解析规则(见第五节源码剖析):user_id 默认取 MEM0_USER_ID 环境变量,缺失时回退到系统 $USER,再回退到 default;app_id(项目 ID)优先取 MEM0_PROJECT_ID,其次查 ~/.mem0/project_map.json 的本地映射,再回退到 git remote 的 slug(如 owner-repo 形式),最后才是当前目录 basename。这意味着 tour 的"当前项目"边界是可预测、可覆写的——/mem0:switch-project 技能正是通过覆写这一解析来切换作用域。

Step 2:三个并行的补充语义检索

在拉取全量的同时,并行发起三条 search_memories 调用,针对关键主题拿一份按相关性排序的结果:

query="architecture decisions design choices"
query="bugs errors failures anti-patterns"
query="project setup tooling conventions preferences"

三者统一参数:filters={"AND": [{"user_id": "<id>"}, {"app_id": "<pid>"}]}top_k=10rerank=true

文档中有一条关键警告:

Do NOT filter by metadata.type in these calls. The platform auto-assigns categories — filtering on metadata.type misses memories that were auto-categorized but don't have an explicit metadata.type.

不要在这三个调用里按 metadata.type 过滤:Mem0 平台会自动给记忆分配 categories 字段,而自动归类出来的记忆往往没有显式的 metadata.type,一旦加了该过滤条件,这部分记忆就会被漏掉。这是 tour 文档中最容易踩的坑,也解释了为什么 Step 3 的分组规则把平台 categories 字段放在第一优先级。

Step 3:合并去重与类别归组

所有结果(全量列表 + 三路检索)按记忆 ID 合并去重,然后为每条记忆确定分组,优先级为:

  1. 平台 categories 字段(每条记忆上的数组,由 Mem0 自动分配),取第一个类别值;
  2. metadata.type 字段(如存在,通常由 hooks/agent 显式写入),作为无 categories 时的回退;
  3. 两者皆无则归入 "other" 桶。

类别名到显示名的映射表(需完整继承):

Platform category / metadata.type Display name
architecture decisionsarchitecture_decisionsdecision Architecture Decisions
anti patternsanti_patternsanti_pattern Anti-Patterns
task learningstask_learningstask_learning Task Learnings
coding conventionscoding_conventionsconvention Coding Conventions
user preferencesuser_preferencesuser_preference User Preferences
project profileproject_profile Project Profile
tooling setuptooling_setupenvironmental Tooling & Setup
technologyprofessional_details Tooling & Setup
session_state Session State
compact_summary Compact Summaries
其他任何值 Other

注意这张表同时兼容空格/下划线/单复数/中文命名习惯的多种写法——因为 categories(平台自动分配,自然语言风格)与 metadata.type(hook 写入,蛇形命名)两种来源的取值风格并不统一,映射表就是两者的归一化层。

Step 4:展示规则

分组按记忆数降序排列;每个非空组输出:

## <display_name> (<count> memories)
- <full_memory_content> (score: <similarity_score_if_available>)
- ...

三条展示纪律:

  • 每条记忆展示完整文本,不截断(与 peek 模式的 80 字符截断形成对比);
  • 某组超过 10 条时,按新近度(来自检索调用的则按相似度分)展示前 10 条,并标注 ... and <N> more;
  • 空组整组跳过,不打印空标题。

Step 5 / Step 6:汇总行与空态

结尾输出总数行:

<N> memories across <M> categories — project: <project_id>, branch: <active_branch>

若本项目零记忆,输出空态提示:

No memories stored yet for project <project_id>.
Run /mem0:onboard to import project files, or start working — mem0 captures learnings automatically.

这里把空态直接引向 /mem0:onboard(项目文件导入向导)——tour 因此同时承担了"记忆系统是否在工作"的健康检查职能,与 /mem0:health/mem0:stats 一起构成 README 推荐的三步验证链。

四、Peek 模式与跨项目模式:紧凑检索与多项目汇总

Peek mode(带 query、无 --all-projects)

/mem0:tour auth middleware 这类调用走紧凑模式,执行两个并行search_memories:

  • 宽检索:query=<query>,filters={"AND": [{"user_id": "<id>"}, {"app_id": "<pid>"}]}top_k=10rerank=true;
  • 定向检索:在宽检索基础上追加 {"metadata": {"type": "decision"}} 过滤,top_k=5rerank=true

注意与完整漫游 Step 2 的差别:peek 模式允许metadata.type=decision 做定向召回(它只要紧凑的 top 结果,丢一点自动归类记忆无妨),而完整漫游的三路补充检索则禁止该过滤(要保证类别全景)。两路结果按 ID 去重后,以固定格式输出:

## mem0 search: "<query>" (<N> results)

1. [decision] Auth module uses JWT with RS256 keys (2025-05-15) [mem0:a3f8b2c1]
2. [anti_pattern] Don't use symmetric HS256 — leaked in env (2025-05-10) [mem0:7e2d9f4a]
3. [convention] All middleware in src/middleware/ (2025-05-08) [mem0:c4d5e6f7]

单行格式为 <number>. [<type>] <content, 80 chars> (<date>) [mem0:<short_id>]——内容截断 80 字符,[mem0:<short_id>] 是 8 位十六进制短引用,与 peek 技能的"引用解析"能力打通:/mem0:peek 或 tour 结果中的 [mem0:a3f8b2c1] 可以直接作为参数回查单条记忆的全文。无结果时输出 No memories matching "<query>" for project <project_id>.

Cross-project 模式(--all-projects)

/mem0:tour --all-projects [query] 跨全部项目搜索,核心变化只有一个:去掉 app_id 过滤

  1. get_memoriesfilters={"AND": [{"user_id": "<active_user_id>"}]}page_size=200——无 app_id;
  2. 若同时给了 query,再跑 search_memories,top_k=20,同样无 app_id;
  3. 结果先按 app_id 分组,再在每个项目内按类别分组;
  4. 展示模板:
## <app_id_1> (<N> memories) ← current
**Architecture Decisions** — <memory content>
...

## <app_id_2> (<N> memories)
...

<N> memories across <M> projects
  1. 当前项目在标题行以 ← (current) 标记。

app_id 过滤的有/无,就是"单项目"与"跨项目"的全部区别,这与第五节中 _search.py 的过滤器构造逻辑完全一致。

五、源码纵深:tour 参数背后的解析与消费链路

tour 文档中的占位符(<active_user_id><active_project_id>rerankfilters 结构)在插件脚本里都有确定的实现,理解它们能预判 tour 的边界行为。

user_id 与 API key 的解析

scripts/_identity.py 给出两级解析链:

  • API key 按序取:MEM0_API_KEY 环境变量 → CLAUDE_PLUGIN_OPTION_API_KEY(Claude Code userConfig 注入)→ 旧版 CLAUDE_PLUGIN_OPTION_MEM0_API_KEY → 正则扫描 ~/.zshrc~/.bashrc 等 profile 文件(专门覆盖桌面应用不继承 shell 环境变量的场景);
  • resolve_user_id():MEM0_USER_ID 显式覆写 → $USER → 字面量 "default"

所以 tour 的 <active_user_id> 在多数机器上就是系统用户名;多身份协作场景用 MEM0_USER_ID 切换即可,且该覆写同时影响 rememberpeek 等所有技能的读写作用域。

app_id 的四级回退

scripts/_project.pyresolve_project_id() 实现了四级回退:MEM0_PROJECT_ID 环境变量 → ~/.mem0/project_map.json 按 cwd 查表(附带按 remote hash 的"自愈"查表,目录改名后仍能命中并回写新 key)→ git remote get-url origin 转 slug → cwd 的 basename。这意味着:tour 末尾汇总行里的 project: <project_id> 对 git 仓库通常是 owner-repo 形式;同一仓库被 clone 到不同路径不会分裂成两个项目(只要 remote 一致),而纯本地目录则以目录名作为项目 ID。resolve_branch() 则从 git 解析当前分支,对应汇总行尾的 branch: <active_branch>

过滤器构造与 rerank 默认值

scripts/_search.py 是所有预取 hook 共享的检索助手,把 POST https://api.mem0.ai/v3/memories/search/ 封装为一次函数调用,其构造逻辑与 tour 文档的 filter 写法一一对应:

  • 非全局检索时,过滤条件组装为 {"AND": [{"user_id": ...}, {"app_id": ...}, (可选 "metadata": {"type": ...})]}——与 tour Step 1/2 的写法一致,也印证了"追加 metadata.type 会收窄结果"的原因;
  • 全局模式使用 {"OR": [{"user_id": "*"}]} 且不含 app_id,即跨项目语义;
  • should_rerank()(第 18-33 行)说明:REST 搜索端点在省略 rerank不会重排,此时结果按原始向量相似度排序,最相关记忆可能掉出 top_k 窗口,因此 hook 注入路径默认开启 rerank,并可用 MEM0_RERANK=0/false/no/off 关闭。tour 文档中每个 search_memories 调用都显式写 rerank=true,正是为了在类别展示前拿到可靠的相关性排序;
  • 该助手还带有 5 秒超时与失败静默(返回空列表并打 stderr 日志),这是 hook 场景的容错设计;tour 本身走 MCP 工具调用,但该文件说明了平台搜索端点的行为前提。

类别体系:tour 分组的供给侧

tour 的显示名映射表(第三节)对应插件自动安装的"编码优化类别体系"。scripts/setup_coding_categories.py 定义了 17 个编码类别——architecture_decisionsanti_patternstask_learningstooling_setupbug_fixescoding_conventionsuser_preferencesdependency_decisionsperformance_findingssecurity_constraintstesting_patternsdata_modelapi_contractsdeployment_runbookteam_normsdomain_glossaryexperiment_results——每个类别附一段描述文本,供平台在自动归类时参照。脚本行为:python setup_coding_categories.py 干跑对比现状与提案,--apply 才真正调用 client.project.update(custom_categories=[...]),且 project.update 总是整体替换类别列表;幂等性由 _categories_match() 的键集比对保证。该配置在会话启动时由生命周期钩子后台执行一次并缓存于 ~/.mem0/categories_setup.json

这解释了 tour 分组表的来源:hook/agent 显式写入的 metadata.type 用的是这套蛇形命名(如 architecture_decisions),而平台自动分配的 categories 可能是自然语言风格(如 architecture decisions),tour 的映射表同时覆盖两套命名,保证两侧记忆都落入正确的显示分组;project_profilesession_statecompact_summary 等则对应 hooks.json 中会话启动、Stop、PreCompact 等生命周期钩子自动写入的记忆类型。

与生命周期钩子的关系

hooks.json 声明了 SessionStart(加载既有记忆作为引导上下文)、UserPromptSubmit(注入相关记忆)、PreToolUse(阻止直接写 MEMORY.md、对 mcp__mem0__* 工具调用强制 user_id/app_id 元数据、读文件时扫描相关记忆)、Stop(提醒代理在回合结束前持久化学习)、PostToolUse(统计与 bash 错误扫描)等事件处理器。其中 PreToolUsemem0-enforce-metadata 钩子(scripts/enforce_metadata_defaults.sh)正是 tour Step 3 中 metadata.type 回退来源的写入方:它保证记忆写入时带上类型元数据,让 tour 的三级分组规则有稳定的回退层可用。

六、实战要点与边界

  1. 验证记忆落库的首选动作:README 推荐的验证链是 /mem0:remember 写入 → /mem0:tour 查看,配合 /mem0:health 检查连通性、/mem0:stats 看计数。tour 输出为空时,按空态提示先跑 /mem0:onboard
  2. 作用域可预测:tour 看到什么,取决于 user_id × app_id 两级作用域;怀疑"看不到某些记忆"时,先确认 MEM0_USER_IDMEM0_PROJECT_ID 覆写与 ~/.mem0/project_map.json 映射,而不是怀疑检索本身。
  3. 全量漫游禁用 metadata.type 过滤:这是 tour 文档明确写出的平台行为差异(自动 categories vs 显式 metadata.type),在自定义任何 tour 变体时都应当保留这一约束。
  4. rerank 的代价与收益:每个 search_memories 都开 rerank=true,换取类别展示内的相关性排序;hook 注入路径的默认实现与 MEM0_RERANK 开关说明平台侧对重排延迟有明确预算意识,tour 的三路并行检索把这部分延迟摊薄了。
  5. 跨项目模式的容量参数:跨项目 get_memoriespage_size=200(单项目为 100)、检索 top_k=20(peek 为 10/5),分组先按 app_id 再按类别,当前项目以 ← (current) 标记。

七、参考文件索引

内容 路径
tour 技能定义(本文主体文档) integrations/mem0-plugin/skills/tour/SKILL.md
peek 技能(紧凑检索对照) integrations/mem0-plugin/skills/peek/SKILL.md
插件总览、MCP 工具表、17 技能列表 integrations/mem0-plugin/README.md
MCP 服务器连接配置 integrations/mem0-plugin/mcp_config.json
生命周期钩子声明 integrations/mem0-plugin/hooks.json
身份(API key / user_id)解析 integrations/mem0-plugin/scripts/_identity.py
项目 ID / 分支解析 integrations/mem0-plugin/scripts/_project.py
共享检索助手(filters / rerank) integrations/mem0-plugin/scripts/_search.py
编码类别体系(17 类) integrations/mem0-plugin/scripts/setup_coding_categories.py
元数据强制钩子脚本 integrations/mem0-plugin/scripts/enforce_metadata_defaults.sh
插件清单(版本/描述) integrations/mem0-plugin/plugin.json

需要说明的适用前提:tour 依赖已安装 Mem0 插件并连通远端 MCP 服务器、MEM0_API_KEY 已配置(见 README 的安装步骤);类别自动归类的效果依赖插件的编码类别体系是否已随会话启动脚本应用。除技能文档明确给出的 page_size/top_k 参数外,本文所有行为结论均来自上述仓库文件,未引入外部数据。

登录后查看全文
热门项目推荐
相关项目推荐

项目优选

收起
kernelkernel
deepin linux kernel
C
33
18
ops-transformerops-transformer
本项目是CANN提供的transformer类大模型算子库,实现网络在NPU上加速计算。
C++
1.12 K
2.72 K
kernelkernel
openEuler内核是openEuler操作系统的核心,既是系统性能与稳定性的基石,也是连接处理器、设备与服务的桥梁。
C
527
590
ops-nnops-nn
本项目是CANN提供的神经网络类计算算子库,实现网络在NPU上加速计算。
C++
904
1.82 K
pytorchpytorch
作为 Ascend for PyTorch 社区的核心组件,TorchNPU 是昇腾专为 PyTorch 打造的深度学习适配插件,使 PyTorch 框架能够直接调用昇腾 NPU,为开发者提供昇腾 AI 处理器的超强算力。
Python
854
1.34 K
docsdocs
暂无描述
Markdown
889
5.78 K
jiuwenswarmjiuwenswarm
JiuwenSwarm 是一款基于openJiuwen开发的智能AI Agent,它能够将大语言模型的强大能力,通过你日常使用的各类通讯应用,直接延伸至你的指尖。
Python
3.52 K
1.01 K
ops-mathops-math
本项目是CANN提供的数学类基础计算算子库,实现网络在NPU上加速计算。
C++
1.33 K
1.45 K
cann-learning-hubcann-learning-hub
CANN 学习中心仓,支持在线互动运行、边学边练,提供教程、示例与优化方案,一站式助力昇腾开发者快速上手。
Jupyter Notebook
981
502
AscendNPU-IRAscendNPU-IR
AscendNPU-IR是基于MLIR(Multi-Level Intermediate Representation)构建的,面向昇腾亲和算子编译时使用的中间表示,提供昇腾完备表达能力,通过编译优化提升昇腾AI处理器计算效率,支持通过生态框架使能昇腾AI处理器与深度调优
C++
540
384