Skip to content

SrulyRosenblat/agent_memory_mcp

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 

Repository files navigation

acp-memory-server

An MCP server that gives a single, searchable view of your past coding-agent transcripts across every locally-installed ACP-compatible agent (Claude Code, Codex, Goose, …).

How it works. On startup, the server fetches the ACP registry, detects which registered agents are launchable on this machine (binary on PATH, or npx/uvx available), and starts a background poller. Every 5 minutes it pulls each agent's session history into a local SQLite + FTS5 database. MCP tools query that index.

Two backends ship today:

  • Filesystem (default wherever a parser exists). Reads the agent's on-disk session store directly. Bundled parsers cover Claude Code, Codex CLI, Goose, Cursor, Cline, Roo Code, Kilo Code, Zed, Gemini CLI, Qwen Code, Continue, and Aider. Captures 100% of local history, fast, no subprocess churn. Incremental scans are mtime- or updated_at-gated depending on the store shape. Filesystem-only agents (Cursor, Cline-in-VS-Code, Zed, Continue) are auto-detected even when their CLI isn't installed — we just read their state files.
  • ACP (fallback for agents without a filesystem parser). Lazy-spawns each agent as an ACP subprocess, calls session/list + session/load, drains the replayed session/update notifications. For agents whose ACP adapter filters session/list by spawning cwd, cwd discovery iterates known project roots.

You can override the backend per agent in config.toml — see Configuration below. The filesystem backend is the reason indexed coverage is ~16× higher than ACP-only would deliver: most agent ACP adapters expose only a small recent slice of session/list, while the filesystem store is complete.

Where each agent stores its data

Agent Storage Format
Claude Code ~/.claude/projects/*/<uuid>.jsonl per-session JSONL
Codex CLI ~/.codex/sessions/<y>/<m>/<d>/rollout-*.jsonl per-session JSONL
Goose ~/.local/share/goose/sessions/sessions.db SQLite
Cursor ~/Library/Application Support/Cursor/User/globalStorage/state.vscdb SQLite (composer headers + per-bubble blobs; orphan composers also recovered)
Cline / Roo / Kilo …/Code/User/globalStorage/<publisher>/tasks/<id>/api_conversation_history.json JSON (Anthropic-format)
Zed ~/Library/Application Support/Zed/threads/threads.db SQLite (payloads may be Zstd)
Gemini CLI / Qwen Code ~/.{gemini,qwen}/tmp/<projectHash>/chats/*.{json,jsonl} JSON / JSONL
Continue ~/.continue/sessions/<id>.json JSON
Aider <repo>/.aider.chat.history.md (per repo; needs project_roots in config) Markdown

Install

git clone <this-repo>
cd acp-memory-server
uv pip install -e .          # or: pip install -e .

First run

acp-memory doctor

That prints the database path, the registry fetch result, the agents detected locally, and per-agent indexed status. Filesystem-backed agents (the ones in the table above) show ok as soon as their on-disk store is found — no subprocess launch required. ACP-only agents may also show unsupported if their adapter lacks loadSession, or needs_auth if session/list returns 401. For needs_auth, run that agent's normal login flow (e.g. claude login) and call the refresh MCP tool or wait for the next poll.

Wire into Claude Code

Add to ~/.claude.json:

{
  "mcpServers": {
    "acp-memory": {
      "command": "acp-memory",
      "args": ["serve"]
    }
  }
}

Restart Claude Code. Then ask it: "search my past sessions for 'database migration'" — it will call search_memory and return hits across every agent it indexed.

MCP tools

Tool Purpose
search_memory(query, agent?, since?, limit?) FTS5 search across all indexed turns. since accepts 7d, 24h, 30m, or ISO-8601.
list_agents() Detected agents and per-agent status.
list_sessions(agent?, limit?) Recent sessions, sorted by latest turn time.
get_session(agent, session_id, offset?, limit?, only_human?, roles?) Paginated transcript. only_human=true keeps just user turns; roles=["user","agent"] for human + assistant only. Returns total and has_more for paging.
refresh(agent?) Force a poll cycle now.
refresh_agents() Re-run discovery (registry + PATH).

Configuration

~/.config/acp-memory/config.toml (all keys optional):

poll_interval_seconds = 300
auto_discover = true
registry_url = "https://cdn.agentclientprotocol.com/registry/v1/latest/registry.json"

# Define a custom agent the registry doesn't know about
[agents.my-custom-agent]
enabled = true
launch_cmd = "/usr/local/bin/my-acp-agent"
launch_args = ["--mode", "acp"]
launch_env = { FOO = "bar" }

# Force ACP polling instead of the default filesystem reader
[agents.claude-acp]
backend = "acp"

# Disable a registry agent without uninstalling it
[agents.codex-acp]
enabled = false

# ACP-only agent that needs cwd hints (override auto-discovery)
[agents.gemini]
cwds = ["/Users/me/code/foo", "/Users/me/code/bar"]

# Aider has no central session store — chat history lives next to each repo.
# Configure the project roots you want indexed.
[agents.aider]
project_roots = ["/Users/me/code/foo", "/Users/me/code/bar"]

Backend selection

Per-agent backend values:

  • "filesystem" — read the agent's local session store. Bundled parsers exist for claude-acp, codex-acp, goose, cursor, cline, roo-code, kilo, zed, gemini, qwen-code, continue, and aider.
  • "acp" — lazy-spawn the agent as an ACP subprocess and use session/list + session/load.
  • omitted — auto: filesystem if a parser exists, else ACP.

Storage

  • Database: ~/.local/share/acp-memory/db.sqlite (or $XDG_DATA_HOME/acp-memory)
  • Registry cache: ~/.cache/acp-memory/registry.json
  • Config: ~/.config/acp-memory/config.toml

The database is plain SQLite with FTS5; you can sqlite3 into it directly to debug or run ad-hoc queries.

Known caveats

  • ACP session/load is optional in the protocol spec. Agents that don't advertise the loadSession capability are flagged unsupported and skipped. Codex and Goose are partial today; their indexed coverage will grow as upstream support matures.
  • Some agents only expose process-local sessions over ACP (i.e. not the user's CLI history). For those, session/list may return little or nothing — acp-memory doctor will surface the empty result.
  • The poller is headless: it cannot drive interactive auth flows. Agents that require claude login / equivalent must be authenticated manually first.

Recursion guard

When the server spawns an agent, it sets ACP_MEMORY_DISABLE_RECURSION=1 in the agent's environment. If that variable is set when the server itself starts, the server runs in a degraded "no-poll" mode (still serves search queries from the existing index) so a chain of nested ACP launches never fans out.

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages