Extending BMAD: the open-source tool ecosystem
BMAD supplies a method and its own memory (the memlog, project-context.md, and
the artifact chain from page 7). It does not supply
precise code navigation, cross-session agent memory, up-to-date library
knowledge, context compression, or corpus-scale research. Those come from a
thriving open-source ecosystem, most of it exposed over MCP, that you wire into a
BMAD agent using the mechanisms from the extending page.
This page is the catalog and the decision matrix: what each tool is, how it pairs with BMAD, and where it overlaps (or conflicts with) BMAD's own memory. Facts below (stars, versions, licenses) are dated to mid-2026; treat them as a snapshot. Vendor benchmark claims are flagged as such.
On this page
- Code and context tools
- Memory tools
- The overlap question: what to add vs what BMAD already has
- Wiring and pitfalls
- Hands-on: wire Serena and do a symbol-level rename
- Under Claude Code: how these tools attach and route
Code and context tools
Serena, symbol-level code tools (the one to reach for first)
Serena (oraios/serena, MIT, ~27k stars, v1.6.x) is an MCP server that gives a coding agent IDE-grade semantic tools backed by the Language Server Protocol, so it edits code by symbol instead of by reading and patching whole files. Its own tagline is "the IDE for your agent." This is the single highest-value tool to pair with BMAD's implementation phase, because dev-story's cost and error rate both come largely from shoveling whole files through the context window.
What it exposes (several dozen tools across categories):
- Symbol tools (the point):
find_symbol,find_referencing_symbols,find_declaration,find_implementations,get_symbols_overview,replace_symbol_body,insert_after_symbol,insert_before_symbol,rename_symbol,safe_delete_symbol, plusget_diagnostics_for_file/_for_symbol. An agent can rename a symbol across a codebase, or replace one function body, as a single atomic call rather than a read-edit-write cycle per file. - File utilities:
search_for_pattern,replace_content(regex/literal),list_dir,find_file,read_file,create_text_file, and friends. Inside Claude Code or Codex these are "typically disabled by default, since the surrounding harness already provides overlapping file, search, and shell capabilities," so you keep the symbol tools and let the host own plain file ops. - Memory:
write_memory,read_memory,list_memories,delete_memory,edit_memory,rename_memory, backed by markdown files in.serena/memories/. An onboarding flow runs on first use of a project and seeds memories describing the project's conventions. - Meta/config:
onboarding,activate_project,get_current_config,open_dashboard, and so on.
Under the hood the LSP layer is solidlsp, a synchronous client library
derived from Microsoft's multilspy, giving direct support for 40+ (docs say
60+) languages via their real language servers (Pyright, typescript-language-server,
Eclipse JDT, rust-analyzer, gopls, clangd, and so on). Configuration is a
per-project .serena/project.yml (which languages, which modes, which tools to
disable) and a global ~/.serena/serena_config.yml; behavior is shaped by an
immutable context (claude-code, codex, ide, ...) and composable
modes (planning, editing, no-onboarding, no-memories, ...).
Run it (current canonical commands; ignore older marketplace snippets):
uv tool install -p 3.13 serena-agent
# register it with Claude Code (verified command):
claude mcp add --scope user serena -- \
serena start-mcp-server --context claude-code --project-from-cwd
# or run the MCP server yourself and point any MCP client at it:
serena start-mcp-server --context claude-code --project-from-cwd
One caveat matters specifically for a Claude-based BMAD stack: Serena's own docs
warn that recent Claude Code and Opus-line updates cut the model's adherence to
its tool instructions, and recommend launching with a system-prompt override
(claude --system-prompt="$(serena prompts print-cc-system-prompt-override)")
plus hooks to keep the agent reaching for the symbol tools. Serena's own token
claim (that a cross-file rename which would otherwise cost many careful steps
collapses into one atomic call) is a vendor quote, not a measured percentage; the
direction is real (symbol edits are far leaner than whole-file rewrites) and the
number is marketing.
How it pairs with BMAD. Add Serena over MCP and reference its symbol tools
from Amelia's bmad-agent-dev.toml persistent_facts ("For code navigation and
edits, prefer Serena's find_symbol / replace_symbol_body over reading whole
files"). dev-story then edits precisely and cheaply. One overlap to manage
deliberately: Serena's .serena/memories/ and BMAD's project-context.md both
store durable project knowledge. Pick one as the source of truth (BMAD's
project-context.md is the better choice, since every BMAD workflow already loads
it) and let Serena's memories hold LSP-flavored specifics, or disable Serena's
memory with its no-memories mode to avoid two drifting copies.
The rest of the code/context toolbox
| Tool | What it is | MCP | Pairs with BMAD by |
|---|---|---|---|
| ast-grep (ast-grep/ast-grep, MIT, ~15k) | AST structural search and rewrite (tree-sitter, 25+ langs); YAML rules | official ast-grep-mcp (4 tools) | deterministic, codebase-wide transforms an agent applies by pattern, not fuzzy text |
| repomix (yamadashy/repomix, MIT, ~27k) | packs a repo into one AI-friendly file (XML/MD/JSON), --compress for signatures | --mcp (6 tools) | brownfield onboarding: a compact whole-repo snapshot to seed document-project |
| Context7 (upstash/context7, MIT, ~60k) | up-to-date, version-specific library docs on demand | remote + local MCP (2 tools) | stops dev-story guessing a stale API; add "use context7" or wire the MCP |
| GitMCP (idosal/git-mcp, Apache, ~8k) | remote "any GitHub repo → docs/code context" | it is a remote MCP server | research and reference against an external repo's real docs |
| mcp-server-git (modelcontextprotocol/servers, MIT) | local git operations (status/diff/commit/branch) | reference MCP (12 tools) | gives an agent git actions when the host doesn't; distinct from GitMCP |
| aider's repo map (Aider-AI/aider, Apache) | tree-sitter + PageRank map of a repo (concept, not a server) | no (aider is an MCP client) | the idea behind why symbol/structure beats raw file dumps; use Serena for the MCP version |
| LSP MCP servers (e.g. isaacphi/mcp-language-server, BSD, ~1.5k) | thin LSP bridges (definition/references/rename/diagnostics) | yes | a lighter alternative to Serena when you want raw LSP without the memory/onboarding layer |
Headroom, context/token compression
Headroom (headroomlabs-ai/headroom,
Apache-2.0, ~62k stars as of mid-2026, v0.32.x) is what "headroom" refers to in
this space: a context-optimization layer that compresses what flows into the
window (tool outputs, logs, files, RAG chunks, JSON, code) before it reaches the
model. It ships three ways, a library, a proxy, and an MCP server
(tools headroom_compress, headroom_retrieve, headroom_stats), so you can
route Claude Code, Cursor, or any MCP client through it. Its "CCR" mode is
reversible: originals are cached locally and the model calls headroom_retrieve
to pull full content back on demand, and its "SharedContext" carries compressed
context across a multi-agent workflow.
Headroom is also a memory tool, which is why it belongs in this chapter: it
keeps categorized memories (preferences, facts, decisions, entities) with
embeddings and timestamps in a local project database (.headroom/memory.db:
SQLite plus a vector index plus full-text search, no external service), and it can
share that memory across agents through the proxy with provenance (which agent
and provider wrote each fact), so a Claude session and a Codex session can see
each other's memories. Where it fits BMAD: a research or dev run that drags large
tool outputs and logs through context is exactly what it targets; route the host
through its proxy or point the agent at its MCP. Its headline numbers ("20% fewer
tokens for coding agents, 60 to 95% for JSON," equivalent answers on public QA
sets) are vendor benchmarks, the README itself hedges output-token savings as
hard to guarantee, and the star count climbed unusually fast, so re-verify both
before you quote them. Mind the naming trap: the old chopratejas/headroom path
redirects to headroomlabs-ai/headroom, and unrelated repos share the name; the
LLM-context one is headroomlabs-ai.
Memory tools
BMAD's memory is per-run (memlog) plus per-project (project-context.md) plus
per-phase (artifacts). It has no cross-session, cross-tool agent memory ("the
model remembers me and my preferences across every session and tool"). That is
what this category adds.
| Tool | Model of memory | MCP | License / scale (mid-2026) |
|---|---|---|---|
| mem0 (mem0ai/mem0) | extract facts, semantic + BM25 + entity retrieval; v3 (Apr 2026) is single-pass ADD-only (append, no overwrite); built-in entity linking | mem0-mcp / plugin (9 tools) | Apache-2.0, ~62k stars |
| Letta (formerly MemGPT, letta-ai/letta) | the "LLM OS": in-context memory blocks the agent self-edits, plus recall + archival tiers; sleep-time background consolidation; .af agent-file format | MCP client (attach external servers) | Apache-2.0, ~24k stars |
| OpenMemory MCP (by mem0) | 100% local, private, cross-tool shared memory | yes (4 tools: add_memories, search_memory, list_memories, delete_all_memories) | Apache-2.0 |
| MCP knowledge-graph memory (server-memory) | entities + relations + observations in a local JSONL graph | reference MCP (9 tools) | MIT, Anthropic reference server |
Anthropic memory tool (memory_20250818) | client-side files under /memories; you own the store; pairs with context editing | not MCP; a Messages-API tool (GA) | proprietary API feature |
| Zep / Graphiti (getzep/graphiti) | bi-temporal knowledge graph: facts carry validity windows and are invalidated on contradiction; hybrid semantic + BM25 + graph search | official Graphiti MCP (~13 tools) | Graphiti Apache-2.0 (~29k stars); Zep is now cloud-only |
| GraphRAG (microsoft/graphrag) | LLM-built entity graph over a private corpus; Leiden community summaries; global / local / DRIFT query | community wrappers only (no first-party MCP) | MIT, v3.x |
A few notes an expert will want:
- mem0's 2026 pivot is real: v3 replaced the older ADD/UPDATE/DELETE/NOOP reconciliation with a single-pass append-only extraction, and moved external graph DBs out of the OSS SDK (built-in entity linking now; graph + time-decay are Platform-only). Every mem0 benchmark number is vendor-authored.
- Letta's sleep-time compute (background agents that consolidate memory while
the main agent is idle) and its
.afformat (serialize a whole stateful agent, secrets nulled, for checkpoint/version-control) are the two ideas worth stealing even if you do not adopt Letta. - Zep's bi-temporal model (event time vs ingestion time, with automatic fact invalidation on contradiction) is the most sophisticated "facts that change over time" story; its benchmark numbers are self-reported.
- GraphRAG is corpus research, not agent memory. It answers "what are the
themes across this whole corpus?" via community summaries, the same shape as Deep
Recon's coverage query at corpus scale. Its own README warns indexing is
expensive; LazyGraphRAG defers the cost to query time. Use it when the sweep is
too big to hold in one run, and contrast it with
bmad-deep-reconfor external-source, cited research. - The Cline / Cursor "memory bank" is not a tool at all; it is a pattern, a
set of markdown files (
projectbrief.md,activeContext.md,progress.md, ...) the agent reads at session start. It is essentially what BMAD already gives you withproject-context.mdplus the artifact chain, so if you run BMAD you do not also need a memory bank; the concepts are the same.
The overlap question: what to add vs what BMAD already has
The most common mistake is stacking redundant memory layers. Map each need to the right layer before adding anything:
| The need | BMAD already has it? | If not, reach for |
|---|---|---|
| durable project rules and conventions | yes (project-context.md) | nothing; don't duplicate it in Serena/mem0 |
| per-run process memory (decisions, claims) | yes (memlog) | nothing |
| reviewed handoffs between phases | yes (artifact chain) | nothing |
| precise, token-cheap code edits | no | Serena (symbol tools) |
| up-to-date library/API docs | no | Context7 |
| deterministic codebase-wide rewrites | no | ast-grep |
| cross-session "remember me and my preferences" | no | mem0 / Letta / OpenMemory |
| facts that change over time (validity windows) | no | Zep / Graphiti |
| corpus-scale "themes across everything" research | partial (Deep Recon per-decision) | GraphRAG |
| cutting tokens on huge tool outputs/logs | no | Headroom |
Start here: for almost every BMAD team, the highest-value single addition is
Serena (precise, cheap dev edits) plus Context7 (stop the agent guessing
APIs). Add a cross-session memory tool (mem0 or Letta) only if you genuinely need
the agent to remember a user across projects, which is a different need from
remembering a project (that is project-context.md). Add GraphRAG only when a
research sweep is too large for a Deep Recon run. Add Headroom when tool-output
bloat is a measured cost.
Wiring and pitfalls
Wire any of these over MCP using the mechanics on the extending page:
connect the server in your host, then reference its tools by exact name in the
relevant BMAD agent's customize.toml (persistent_facts for standing routing,
external_sources for on-demand lookups). Serena is the exception that also
registers itself, via the claude mcp add ... serena ... command shown above.
The pitfalls are consistent:
- Redundant memory layers. Two systems both claiming to hold "project knowledge" drift apart and confuse the agent. Pick one source of truth per kind of memory (the matrix above).
- Too many chatty MCP surfaces. Every connected server adds tool schemas to context and a decision the model must make. Add the ones that remove work (Serena replaces file reads; Context7 replaces guessing) and skip the ones that just add another thing to consider.
- Believing the marketing. The token-savings and accuracy numbers on Headroom, mem0, Zep, and GraphRAG are almost all vendor-authored and often not apples-to-apples. Adopt for the mechanism, then measure the effect yourself with the scorecard from page 7 and the benchmark harness on the next page.
- Sending secrets or PII into memory tools. Cross-session memory persists and is replayed into future contexts; never store credentials there, and check data regulations before persisting user data.
Hands-on: wire Serena and do a symbol-level rename
This turns "Serena helps" into a rename you can run today. Install the server and register it with Claude Code:
uv tool install -p 3.13 serena-agent
claude mcp add --scope user serena -- \
serena start-mcp-server --context claude-code --project-from-cwd
Index the project once so the language server answers symbol queries without a cold scan on every call (worth it on any non-trivial repo):
cd ~/src/your-project
serena project index
Point dev-story at the symbol tools by adding one standing fact to Amelia's dev
agent. Append to bmad-agent-dev's customize.toml:
persistent_facts = "For code navigation and edits, prefer Serena's mcp__serena__find_symbol, mcp__serena__find_referencing_symbols, and mcp__serena__rename_symbol over reading and patching whole files."
Now the session. Say a fetch helper normalize_url should become
canonicalize_url across the codebase. Locate it, list its callers, then rename
in one atomic edit:
Illustrative (run it in your own repo; not machine-verified here).
mcp__serena__find_symbol {"name_path": "normalize_url"}
-> src/fetch/url.py:42 def normalize_url(raw: str) -> str
mcp__serena__find_referencing_symbols
{"name_path": "normalize_url", "relative_path": "src/fetch/url.py"}
-> src/fetch/client.py:88 normalize_url(resp.url)
-> src/crawl/frontier.py:15 from ..fetch.url import normalize_url
-> tests/test_url.py:7 normalize_url("HTTP://A/b")
mcp__serena__rename_symbol
{"name_path": "normalize_url", "relative_path": "src/fetch/url.py",
"new_name": "canonicalize_url"}
-> updated 4 files, 6 occurrences, one change set
Three calls: one to find the definition, one to see exactly who calls it, one to
rename the symbol and every reference to it together. The LSP resolves references
by binding, so it skips a same-named local in another module and never touches the
string "normalize_url" sitting in a log line.
Contrast the whole-file path this replaces: grep the name, read each hit's full
file into context, edit each one, write it back, then re-read to confirm nothing
else matched by accident. That is one read-edit-write cycle per file, several
thousand tokens of file bodies through the window, and a real chance of a missed
caller or a clobbered look-alike. The symbol rename moves only the definition and
its true references, so it is both cheaper and safer. Wire it once; every
subsequent dev-story edit rides the same path.
Under Claude Code: how these tools attach and route
Every server in this chapter attaches the same way: as an MCP server the host
connects to. claude mcp add at project scope writes a committed .mcp.json at
the repo root (an mcpServers map of command / args for stdio, or url for
http), so the whole team gets the same servers on clone. /mcp lists connection
status and runs the OAuth sign-in for servers that need it (tokens land in
~/.claude.json, not in the repo). Once connected, each tool is exposed under a
fixed name, mcp__<server>__<tool>, so Serena's find_symbol is
mcp__serena__find_symbol, and that exact string is what you reference in a BMAD
agent's persistent_facts and in permission rules.
A big server does not have to crowd out the rest of the context. Schemas are
deferred by default: only tool names load, and full schemas are pulled on demand
through ToolSearch. ENABLE_TOOL_SEARCH governs the choice:
| Value | Behavior |
|---|---|
auto (default) | load all schemas upfront only if they fit in about 10% of the window, else defer |
true | always load all schemas upfront |
false | always defer; wait via WaitForMcpServers if a server is still connecting |
Since Serena exposes dozens of tools, auto usually defers them, so one large
server stays cheap until its tools are actually needed.
Route the agent toward the right tool two ways. First, disable the host's
overlapping built-in file tools (Read, Grep, Glob, via a disallowedTools
entry or a deny rule) so it stops reaching for a whole-file read when a symbol
tool is better. Second, add a PreToolUse hook to nudge or block a choice, or a
permission rule (mcp__serena__* in allow / deny) that scopes a server's
tools exactly like any built-in. The chapter's "wire it in over MCP" is,
concretely, those three pieces: .mcp.json, deferred schemas, and a routing hook
or rule.
That completes the toolbox. But should you trust these tools' numbers, or BMAD's own? The next page is how you benchmark the method and everything you bolt onto it, across every dimension, so the answer is a measurement rather than a hunch. 👉