内容
# claude-continuity-mcp — 持久、共享内存,用于 Claude
**Claude 记得对话内容。这个 MCP 让 Claude 拥有项目记忆。**
一个 MCP 服务器,为 Claude 提供目前没有的功能:**跨会话持久化、跨客户端共享的内存** (代码、桌面端、协作、设计)。它记得哪些文件你已经读过,只返回变更部分,继续未完成的任务,并在客户端之间协调指令。100% 本地运行,无需 API 密钥。
## 这实际上做了什么(用简单的语言解释)
Claude 在对话结束时忘记一切,无法在不同应用间共享信息 —— 你告诉 Claude Code 的内容,对 Claude 桌面端不可见。这个项目通过在本地计算机上保存一个小内存文件解决了这个问题,该文件被所有 Claude 应用共享。
安装后,实际上:
- **你不再需要重复解释你的项目。** Claude 记得它已经读过哪些文件。如果没有变化?它直接进入主题。如果有变化?它只读取变更部分,而不是整个文件。
- **你可以从任何 Claude 应用继续工作,就像你离开时一样。** 在一个 Claude 应用中保存快速笔记,从另一个应用继续,决策和待处理任务保持完整。
- **你可以让另一个应用完成任务。** 告诉协作应用留下一个任务给代码应用;它会接起来,完成并汇报结果,即使两个应用无法直接通信。
- **你可以教它一个永久规则,一次即可。** *"永远不要在这个项目中使用 Redux"* — 只需说一次,它就会自动在任何应用中显示,无需重复。
- **你可以询问 "在我的整个项目中,X 被如何处理?"** —— 不仅限于一个文件,而是整个代码库 —— 并获得准确的文件和行号,而不是猜测。
它从不使用另一个 AI 总结文件以节省空间 —— 你总是获得真实、准确的内容。所有内容都保留在你的机器上:无需账户、无需 API 密钥、无需发送任何内容。
**这适用于谁:** 任何在同一项目中使用多个 Claude 应用(例如,Claude Code 和 Claude 桌面端,或协作应用)的用户,跨多个会话使用。如果您每次只有一个快速聊天,这个功能不会带来太大变化 —— 这不是为此而设计的。
```mermaid
graph TD
A[Claude Code] --> M
B[Claude Desktop] --> M
C[Claude Cowork] --> M
D[Claude Design] --> M
M[("claude-continuity-mcp<br/>━━━━━━━━━━━━━<br/>smart_read · checkpoint · inbox<br/>project_search · rules · SQLite ledger")] --> P[(您的项目<br/>在磁盘上)]
style M fill:#1a1a2e,stroke:#00c8e8,stroke-width:2px,color:#fff
style P fill:#0d0d1a,stroke:#666,stroke-width:1px,color:#ccc
```
四个不同的客户端,一个共享状态:无论哪个客户端读取、决策或留下待处理任务,其他客户端都可以继承。
## 为什么存在
Claude 在会话之间是健忘的,在客户端之间是盲的:您在 Claude Code 中阅读的内容对 Claude 桌面端不可见,每个新会话都会重新读取相同的 file,就像第一次一样。这个 MCP 是所有客户端共享的本地进程,状态持久化到磁盘 —— 它是 Claude 缺少的内存。节省的 token 是真实的,但它们是一个结果,而不是主要卖点:这个项目与其他项目的区别在于 **连续性**。
## 它是什么 —— 以及它不是什么
**它是:**
- 连续性:一个会话中读取/决策的内容在下一个会话中仍然可用,在任何其他客户端中也是如此。
- 一个层,使得 20,000-token 文件不进入 Claude 的上下文窗口,除非您需要 400 个 token。
- 确定性:在需要的地方,`smart_read` 返回 **准确** 的文件片段(本地 BM25/embeddings 排名)和 **准确** 的差异 —— 永远不会丢失由较弱的模型生成的摘要。
**它不是:**
- 一个 "神奇的 token 节省器",用于日常聊天。如果您的会话是正常对话,此功能不会有太大帮助 —— 没有工具可以帮助您。
- 代码压缩器。使用廉价的 LLM 压缩代码会降低 Claude 的答案质量,并最终导致更多的重试开支。这里永远不会这样做。
> **注意:** 免费模型的大批量处理(以前的 `router_bulk_process`)已拆分为其自己的存储库,[`individra-bulk-offload`](https://github.com/gabicacabelos/individra-bulk-offload),因为它是一个不同的产品:它依赖于外部服务,这些服务削弱了这个 100% 本地核心。
## 6 种工具
### `router_smart_read` — 有记忆的智能读取(本地,$0,无 API)
*简而言之:智能读取文件,记住已经看到的内容,只显示更改的内容。*
```python
smart_read(file_path="docs/manual.md", query="where are webhooks configured?")
→ 2-4 个相关的准确片段,带有行号
```
- 小文件(≤ ~6KB):返回整个文件,清理干净。
- 大文件 + `query`:混合分块 + 排名(如果安装了 fastembed,则使用快速嵌入,如果没有,则使用纯 Python BM25)→ 只有相关的片段。典型的节省:文件大小的 70-90%,**零保真度损失**。
- 大文件无 `query`:结构地图(带有行号的大纲)来决定请求什么。
- HTML:本地清理(脚本、标签、样板文件剥离)后处理。
**跨会话内存(差异读取):** 每次读取都会记录(哈希 + 快照在本地 SQLite 文件中)。在任何未来的会话中,在任何客户端:
- 不更改的文件 → `{"status":"unchanged","outline":[...]}` — 约 50-100 个 token 而不是数千个。在测试中:90 个 token vs. 10,195 个 token 用于文件。
- 修改的文件 → **只有统一的差异** 对快照(根据测量,节省 99%+)。
- `force_full=true` 跳过内存,当您需要完整内容时。
### `router_checkpoint` — 会话和客户端之间的上下文切换
*简而言之:保存进度,稍后继续 —— 从任何 Claude 应用。*
```python
checkpoint(action="save", name="refactor-auth",
summary="登录迁移到 JWT,刷新令牌仍待处理",
decisions=["使用 RS256"], open_items=["过期测试"],
files=["src/auth.py"])
```
当关闭长期任务(或当上下文填满时),Claude 以人类可读的 JSON 格式保存在 `checkpoints/` 目录下 —— 可由您编辑,与团队共享。新会话 —— 在桌面端、代码或协作应用中,都无关紧要 —— 调用 `action="resume"` 并在约 300 个 token 内恢复所有内容,**包括自上次检查点以来磁盘上哪些文件已更改**(哈希比较,无需重新读取)。`action="list"` 显示可用的检查点。
**冷启动(无保存的检查点):** `resume` 从不空手而归。如果没有人保存检查点,它会从账本和收件箱中重建确定性的摘要 —— 最后触摸的文件(以及它们自上次以来是否更改),加上最近完成的订单。有效载体声明 `"mode": "reconstructed_activity"` 明确:它是一个活动跟踪,**不是** 有意的检查点,不包含任何架构决策。
### `router_inbox` — 跨客户端订单
*简而言之:给另一个 Claude 应用留下一个任务,让它接起来、运行并汇报结果。*
```python
# 在协作应用中:
inbox(action="send", to="code", message="将测试迁移到 pytest",
checkpoint="refactor-auth")
# 在 Claude Code 启动时:
inbox(action="check", to="code")
→ 订单 + 链接的检查点摘要
inbox(action="complete", order_id=1, result="34/34 测试通过")
# 回到协作应用中:
inbox(action="history") → 您看到结果
```
Claude 聊天不能实时指挥其他聊天 —— 但它们共享这个磁盘。收件箱是一个异步邮箱:您从一个客户端留下订单(链接到检查点,以便接收者拥有正在进行的任务的完整上下文),另一个客户端启动时接收订单,执行它并汇报结果。告诉协作应用 *"将此任务留给代码应用"* 就是这样 —— 服务器的 `instructions` 使每个客户端在启动工作时检查其收件箱。
**打包客户端:** `cowork`, `code`, `desktop`, 和 `design`(Claude Design)。任何客户端都可以给其他客户端下订单 —— 目的地是自由文本,因此您也可以发明自己的角色。对于客户端接收订单,它只需要加载此 MCP 并使用 `action="check"` 检查其收件箱。
**代码 ↔ 设计交接(`assets`):** 订单和结果可以携带 `assets` —— 一个文件路径或 URL 列表(简报、线框图、`.fig`/`.png` 导出、规格)。这样,开发和设计之间的往返旅程就有了材料,而不仅仅是文本:
```python
# Claude Code 请求 Claude Design 提供一个模型,同时附上材料:
inbox(action="send", to="design", from_client="code",
message="登陆页面,暗色 + 青色强调",
checkpoint="landing-v2",
assets=["/proj/brief.md", "https://.../wireframe.png"])
# Claude Design 在启动时看到订单 + 简报 + 线框图:
inbox(action="check", to="design")
inbox(action="complete", order_id=7, result="模型准备好,2 个变体",
assets=["https://figma.com/.../hero", "/exports/hero-v1.png"])
# Claude Code 看到结果和返回的导出:
inbox(action="history") → 结果 + 结果资产
```
反之亦然:Claude Design 可以给 `code` 留下带有最终导出的订单进行实现。收件箱在所有客户端之间是双向的。
### `router_status` —诚实的会话指标
*简而言之:检查它实际上为您节省了多少 —— 真实数字,无营销噱头。*
主要指标是 `tokens_kept_out_of_context`:来自原始来源的 token **未** 进入 Claude 的上下文窗口。它还报告读取、内存命中(未更改/差异)、账本状态和待处理收件箱订单。`deep=true` 添加本地诊断(快速嵌入/ python)。
### `router_project_search` — 搜索整个项目(增量 BM25)
*简而言之: "我的整个项目中在哪里有 X?" —— 用准确的文件和行号回答,而不是猜测。*
```python
project_search(project_dir="/proj", query="在哪里验证 webhook 签名?")
→ 最相关的文件,每个文件都有其准确的片段和行号
```
`smart_read` 回答 *"文件 X 中在哪里有 Y?*"。您通常的问题是 *"项目中 Y 在哪里?*" —— 而这就是 Claude 恢复到 Grep 的地方。
- **增量索引:** 首次调用索引;后续调用仅重新索引哈希更改的文件(未更改的文件成本 ~0)。在此存储库上:23 个文件,0.41 秒冷启动,**0.08 秒热启动**。
- **持久且共享:** 索引存储在账本中,因此它在会话和客户端之间存活。 Grep 从零开始;这不是这样。
- **比字面 Grep 更适合概念:** 按相关性排序并拆分 `snake_case`/`camelCase`,因此 "webhook 重试" 找到 `handleWebhookRetry()`。
- 有意限定:跳过 `node_modules`、`.git`、`dist`、二进制文件和 >400KB 的文件。确定性,100% 本地 —— 准确的片段,从不摘要。
### `router_rules` — 永久项目规则,具有出处
*简而言之:教它一个规则一次(“永远不要使用 Redux”),它在任何地方、任何时候都记住。*
```python
rules(action="add", project_dir="/proj", text="永远不要使用 Redux", from_client="code")
rules(action="promote", project_dir="/proj", checkpoint="arch-decisions") # 检查点决策 → 永久规则
```
与检查点捕获的**任务状态** 不同,规则是 **永久** 的项目决策(`"永远不要使用 Redux"` 、 `"测试放在 tests/` 中)。每个规则都带有出处:**谁** 决定了它(客户端/人类),**何时**,以及 **哪个检查点** 它来自。规则存储在项目根目录的 `.claude-continuity-rules.json` 中 —— 友好的 Git,手动可编辑,随存储库旅行,并存活于 Anthropic API 的任何更改。
- **确定性:** 规则是人类编写的文本或从检查点的 `decisions` 提升的 **字面文本** —— 从不使用损耗 LLM 摘要。
- **零摩擦分布:** 您不需要调用工具来 *读取* 规则 —— 它们作为 `project_rules` 注入到 `smart_read` 和 `resume` 载入的文件项目(搭载在已经发生调用中)。
- **不与 `CLAUDE.md` 作斗争,支持它:** `sync_to_claudemd=true` 将规则写入项目的 `CLAUDE.md` 的分隔部分(`<!-- INDIVIDRA RULES START/END -->`)—— 留下您自己的内容不受影响,以便 Claude Code 的原生内存也能获取它们。
## 真实节省(诚实数字)
| 场景 | 节省 | 保真度 |
| --- | --- | --- |
| 重新阅读已知的不变文件 | 98-99% | 100%(大纲 + 内存) |
| 重新阅读已知更改的文件 | 90-99% | 100%(确切的差异) |
| 在新会话/客户端恢复任务(恢复) | ~300 个 token vs. 重新探索所有内容 | 100% |
| 在 20k-token 文件中搜索特定内容 | 80-95% | 100%(确切的片段) |
| 吸收脏 HTML/web 内容 | 40-60% | 100%(仅删除噪音) |
| 正常对话聊天 | ~0% | — |
固定开销约为每个会话 500 个 token。如果您不处理大文件或批次,这就是您的净成本:请诚实地评估您的用例。
## 安装
```bash
git clone https://github.com/gabicacabelos/claude-continuity-mcp.git && cd claude-continuity-mcp
pip install -r requirements.txt
# 可选(用于 smart_read 的本地语义排名):pip install fastembed
```
无需 API 密钥或 `.env` 文件:所有六种工具都是 100% 本地。
### 在所有 Claude 会话中注册它
**Claude Desktop / Cowork** — `claude_desktop_config.json`:
```json
{
"mcpServers": {
"claude-continuity": {
"command": "python",
"args": ["C:/path/to/claude-continuity-mcp/server.py"]
}
}
}
```
**Claude Code** (用户范围 = 在每个项目中可用):
```bash
claude mcp add claude-continuity --scope user -- python /path/to/server.py
```
### 用户调用的提示(斜杠命令)
连续性不能仅依赖模型 *选择* 调用这些工具。服务器公开三个 MCP 提示,客户端将其作为斜杠命令公开,因此 **您** 确定性地触发流程:
| 提示 | 它驱动什么 |
| --- | --- |
| `/resume` | 恢复最新的检查点(或冷启动摘要)+ 检查待处理收件箱订单 + 简要介绍工作进展 |
| `/handoff` | 保存此会话的检查点,并在另一个客户端的收件箱中留下链接订单(参数:`to`, `message`) |
| `/inbox` | 检查此客户端的收件箱并执行待处理订单端到端,标记每个环节的证据 |
(确切调用方式因客户端而异 - 例如,在 Claude Code 中,它们出现在 `/mcp__<server-name>__resume`。)
### 自动激活
服务器声明 `instructions` 注入到每个会话的系统提示中,告诉 Claude 何时使用每个工具以加强它。 为加强它,在您的全局 `CLAUDE.md` 中添加一行:
```
读取 >15KB 文件或搜索其中的特定内容,请使用 `router_smart_read` 查询。
关闭长任务时,请保存 `router_checkpoint`;恢复时,请总结。
```
## 架构
```
smart_read ──▶ sanitizer(HTML/text, 本地) ──▶ ledger(我看过吗?)
│ ├─ 不变 → 大纲(~50 tok)
│ └─ 变更 → 统一的差异
└──▶ ranker(查询)
├─ fastembed(bge-small, 本地 ONNX)如果可用
└─ 纯 Python BM25(备用,0 依赖)
checkpoint ──▶ checkpoints/*.json(人类可读/可编辑)+ 哈希验证恢复
inbox ──────▶ 共享 SQLite 队列(Cowork/Code/Desktop/Design + 交货资产 + 结果)
rules ──────▶ .claude-continuity-rules.json(项目根目录,git-friendly,provenance)→ 注入 `smart_read/resume`, 可选 CLAUDE.md 同步
project_search ▶ 增量 BM25 索引(账本中重新索引更改的哈希)→ 文件排名 + 确切片段
hook(opt-in) ▶ PostToolUse → raw_reads 阶段表(WAL)→ 由 MCP 排空到账本
```
一切本地:账本和收件箱是磁盘上的 SQLite 文件;检查点是可读/可编辑的 JSON。 无网络,无 API 密钥
### 架构
```
smart_read ──▶ sanitizer (HTML/text, 本地) ──▶ ledger (是否见过?)
│ ├─ 不变 → 大纲 (~50 tok)
│ └─ 变更 → 统一差异
└──▶ ranker (带查询)
├─ fastembed (bge-small, 本地 ONNX) 如果可用
└─ 纯 Python BM25(备用,0 依赖)
checkpoint ──▶ checkpoints/*.json(人类可读/可编辑)+ 哈希验证恢复
inbox ──────▶ 共享 SQLite 队列(Cowork/Code/Desktop/Design + 交货资产 + 结果)
rules ──────▶ .claude-continuity-rules.json 在项目根目录(git-friendly,来源)→ 注入到 `smart_read`/`resume`, 可选 CLAUDE.md 同步
project_search ▶ 增量 BM25 索引在账本中(仅重新索引更改的哈希)→ 文件排名 + 确切片段
hook (可选) ▶ PostToolUse → 原始读取阶段表(WAL)→ 由 MCP 排空到账本中
```
所有本地运行:账本和收件箱是磁盘上的 SQLite 文件;检查点是可读/可编辑的 JSON。核心无网络,无 API 密钥,无外部依赖。
## MCP 进程不会自行更新
每个客户端启动 `server.py` 作为自己的进程,并在会话期间保持活动。编辑磁盘上的代码或运行 `git pull`/`git push` **不会** 影响已经运行的进程:Python 自己不会重新加载模块。如果您更改了某些内容,但新行为未显示出来,那不是错误:重新启动 MCP(通过 `/mcp` 重新连接或重启客户端)。
因此,您不必手动推断:`router_status` 包括 `code_staleness`:它将 `server.py`/`router/*.py` 的修改时间与进程启动时间进行比较,如果磁盘在启动后发生更改,则返回 `{"stale": true, "changed_file": "...", "hint": "..."}`。此外,当存在陈旧时,**每个** 工具都会将 `code_stale` 字段注入其响应中(带有更改的文件和提示)- 您可以在进行第一个调用时发现,无需记住检查 `router_status`。在正常操作中,该字段不存在:它仅在磁盘代码在启动后实际更改时出现。
## 被动捕获(可选,Claude Code专有)
内存仅在Claude选择`router_smart_read`时才会填满。如果它使用原生的`Read`,则账本永远不会知道。一个可选的`PostToolUse`钩子弥补了这一空白:**即使Claude从未选择此MCP的工具,值也会累积。**
将以下内容添加到您的`.claude/settings.json`文件中:
```json
{
"hooks": {
"PostToolUse": [
{
"matcher": "Read",
"hooks": [{ "type": "command", "command": "python /path/to/claude-continuity-mcp/hooks/capture_read.py" }]
}
]
}
}
```
该钩子故意设计得很简单:它只对一个临时表(`raw_reads`)执行**一次**INSERT操作,然后退出——无需哈希,无需读取文件。MCP稍后会在其自己的时间(`drain_raw_reads`)将这些行提升到实际的账本中,因此钩子永远不会支付该成本。账本以**WAL**模式运行,因此钩子(一个单独的进程)和MCP可以并发写入。
**诚实的成本和注意事项:**
- **每个原生的`Read`操作约250毫秒**,几乎完全是Python解释器启动的时间——而不是数据库写入。如果您读取了很多文件,这会增加。请勿启用它,如果这对您有影响;其他一切功能无需它也能正常工作。
- 如果数据库忙,钩子会**静默丢弃捕获**(100毫秒SQLite超时)。丢失捕获是免费的;冻结终端不是。
- **Claude Code专有**。Desktop/Cowork/Design没有钩子——在这些情况下,内存仍然取决于调用的工具。
- 它与Anthropic控制的API耦合,该API可能会更改。因此,它是可选的且严格附加的:如果钩子停止触发,什么都不会破坏。
## 热配置(`router_config.json`)
运行时可调参数可以在**无需重启MCP的情况下进行调整**。将`router_config.example.json`复制到`router_config.json`(位于`server.py`旁边,被git忽略),然后编辑您需要的内容——下一次调用任何工具时,它就会生效(该文件仅在修改时间更改时重新解析,几乎为零开销):
| 键 | 默认值 | 控制内容 |
|---|---|---|
| `full_return_max_tokens` | `1500` | 文件返回完整的阈值以下 |
| `default_top_k` | `4` | 调用未传递`top_k`时返回的片段 |
| `diff_max_ratio` | `0.6` | 如果差异的权重超过文件比例的此值,则不值得返回普通内容 |
| `cache_enabled` | `true` | 查询→片段缓存和嵌入向量缓存 |
如果`router_config.json`不存在,则应用默认值(零配置)。**逻辑**更改(`server.py`/`router/`中的新代码)仍然需要重启——这是不可避免的;热配置仅取消了对可调参数的重启。
## 已知限制
- BM25是词性的:查询与文本没有共同词汇时,降级为文件的第一部分。安装`fastembed`可改善语义查询(需要与Python版本兼容的onnxruntime)。
- BM25也是词性的,项目范围内也是如此:`router_project_search`按共享词汇排序,因此查询与代码没有共同词汇时,排序会降低。它补充了Grep和语义搜索,而不是取代它们。
- `code_staleness`检测代码更改——它不会自行重启。自动重启不安全:多个客户端可能共享同一进程,在中途杀死它会切断工具,另一个会话无法保证其恢复。
## License
MIT — 请参见`LICENSE`。
MCP 配置
以下是此 MCP Server 的配置信息,可直接复制到 Cursor 或其他 MCP 客户端中使用。
mcp.json
连接信息
猜你喜欢
暂无推荐服务器