All notable changes to this project are documented here. The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.
1.7.0 - 2026-07-29
- Diff-aware blast-radius analysis.
codebase-index diff-impactand the MCPimpact_of_difftool aggregate graph impact for tracked working-tree changes relative to a verified Git commit, with a changed-file safety cap, unresolved file reporting, freshness, graph coverage, edge confidence, and exclusion of the tool's own derived cache. - Progressive skill references. The installed agent skill now keeps its always-loaded evidence protocol compact and moves detailed commands and response handling into on-demand reference files.
- Reproducible product identity. Added a graph-route mark and redesigned README/social assets around Find / Trace / Predict.
- Reworked the README, roadmap, product brief, package metadata, and plugin copy around the evidence-first product promise.
- Expanded the safe
cbxwrappers to allow the shipped read-onlyarchitecture,path,describe, anddiff-impactcommands. - Replaced broad skill shell permissions with an explicit command allowlist so
clean,init, andwatchcannot bypass the safe wrapper. - Hardened the release workflow with least-privilege defaults and immutable commit pins for every GitHub Action that receives release or PyPI credentials.
1.6.0 - 2026-06-24
- Snippet skeletonization & content-aware rendering.
search/explainsnippets are now focus skeletons — import/signature/class lines and the query-matching line are kept while function bodies collapse to a... N lines elided (read A-B)marker — so more ranked results fit the same token budget. Content-aware (code via tree-sitter, markdown headings, structured-config keys), reversible viarecommended_reads, and safe (raw fallback on any parse miss or non-win). Newskeletonized/elided_linesresult fields; newretrieval.compact_snippets/retrieval.compact_min_reductionconfig knobs (no reindex); disable per-call with--raw(CLI) orraw: true(MCPsearch_code/explain_code).
1.5.0 - 2026-06-24
- HTML graph is now legible at a glance: nodes are coloured by module
(community), sized by connectivity (god nodes are biggest), and edges are styled
by confidence — solid
extracted, dashedinferred, red-dottedambiguous— with a legend. Community/degree are computed on the displayed subgraph. codebase-index graph --format graphml|dot|neo4jexports the same enriched graph for external tools: GraphML (Gephi / yEd / NetworkX), DOT (Graphviz, edge style = confidence), and Cypher (Neo4j / FalkorDB). All pure-stdlib, zero new dependencies.--format html(default) is unchanged.
codebase-index path <A> <B>— shortest undirected dependency/call path between two symbols or files ("how is X connected to Y"). Renders the node chain annotated with each link's edge type and confidence;inferred/ambiguoushops are marked, so a path is only as trustworthy as its weakest edge.codebase-index describe <symbol>— a node card: definition(s), direct callers and callees (with confidence), in/out degree, the symbol's module, and its god-node rank if it has one. The graphifyexplain Symbolidea, nameddescribeso it doesn't collide with the existing how-it-worksexplain.path_betweenanddescribe_symbolMCP tools expose both to agents.
codebase-index architectureprints a high-level map of the codebase from the analytics cached at index time: detected modules (with auto-derived labels), god nodes (most-connected symbols/files), surprising cross-module connections, and suggested starting questions.--jsonfor the structured payload.architecture_overviewMCP tool exposes the same map to MCP clients, so an agent can orient itself before diving into specifics. Reportsavailable: false(rather than crashing) on an index built before the analytics existed; a reindex fixes it.
- Edge confidence audit trail. Every graph edge now carries a
confidence:extracted(exact — a same-file symbol or repo-unique name),inferred(a heuristic resolved it, e.g. an import path-suffix match), orambiguous(a named target we could not pin to a unique node).refsandimpactsurface it so an empty or short answer overambiguous/inferrededges reads as inconclusive, not as proof. Confidence is derived from how an edge resolved — never guessed by an LLM; the index stays fully local. BumpsSCHEMA_VERSION2 → 3. Older indexes stay readable;index/updatedetect the mismatch and rebuild. - Architecture analytics (
graph/analysis.py), zero new dependencies. A pure, deterministic pass over the resolved edge graph computes communities (greedy modularity / Louvain local-move — does not collapse cliques joined by one bridge), god nodes (most-connected symbols/files), surprising connections (edges bridging weakly-linked communities), auto-labelled modules, and suggested questions. The summary is cached inmeta['graph_analysis']at build time for instant reads. (Surfaced via thearchitecturecommand and HTML export in following changes.)
- RRF fusion rescaled and re-keyed. Fused scores were ~
w/k(≈0.017), an order of magnitude below the reranker's bounded bonuses, so rerank silently became the primary ranker. RRF is now scaled byk(a pure monotonic rescale — order is unchanged) so fused scores and rerank bonuses share an O(1) scale. Fusion also merges on a coarse(path, line-bucket)key instead of an exact(path, start, end)one: different retrievers report different ranges for the same place, so the exact key almost never coincided and cross-source agreement never fired.agreeing_sourcesis now counted at file granularity. - Confidence uses a scale-invariant relative gap instead of absolute thresholds.
- Per-file diversification: at most 3 hits per file stay on the page; the rest are pushed to the tail (nothing is dropped). Combined with bucketing this removes the "same small file returned six times at different line slivers" noise.
- FTS recall on natural-language queries: stopwords (
how,does,the, …) are dropped before building the FTSMATCH, so a query like "how does auth work" no longer AND-s in filler that code chunks never contain. - Symbol names are FTS-indexed.
chunksgained a denormalizedsymbol_namescolumn (mirrored verbatim by the FTS sync triggers, so external-content delete/ update stays consistent) — a query matching a symbol's name now hits even when the body text doesn't repeat it. BumpsSCHEMA_VERSION1 → 2. Older indexes are still readable;index/updatedetect the mismatch and rebuild from scratch. - Centrality fallback for ambiguous names: symbols whose name isn't globally
unique never get a resolved
in_degree; they now receive a damped, half-capped bonus from a name-reference count so common names (run,handle, …) aren't flatly zeroed. Precisein_degree, where present, still takes precedence. - Test-file demotion is word-boundary aware:
contest/,latest.py,testimonials.tsxare no longer mistaken for test files. - Language-aware import resolution:
import './base'from a.tsfile resolves tobase.tsrather than a same-namedbase.pyearlier in the fallback order. - Freshness is content-aware: a bare
touch(mtime change, identical bytes) is a no-op forupdate, so it no longer reports the index as stale — freshness now mirrors the sha-based incremental decision.
- Dead legacy lexical-search path in
retrieval/searchers.py(fts_response,fts_search, the secondCandidatedataclass and_confidence/_fallbacks/_trim) — the live path goes throughpipeline.search→fts_candidates.
1.4.0 - 2026-06-14
cleanis now implemented (it was a documented-but-stubbed_todosince M0).codebase-index cleanresets the index database (index.sqlite+ WAL/SHM sidecars);codebase-index clean --allwipes the whole per-project cache directory. It prompts before deleting (skip with--yes), supports--json, and never touches the installed skill. Locked in bytests/test_clean_cli.py.docs/PRODUCT_UPGRADE_PLAN.md: positioning, target users, competitor matrix, differentiators, current weaknesses, a ranked roadmap, and documentation / benchmark / distribution / technical task lists.docs/RELEASE_CHECKLIST.md: a repeatable release checklist (version sync, tests, benchmarks, doctor, install/plugin/MCP smoke, changelog) with signed checksums + SBOM tracked as future hardening.- MCP contract hardening (M11.5): every MCP tool payload — success and the
no-index/error path — is now wrapped in a stable envelope (
schema_version: 1,tool: ). Golden snapshots lock every tool's output (tests/golden/mcp_*.jsonviatests/test_mcp_golden.py), and the contract values are asserted explicitly so a golden can't freeze a wrong version. Closes the long-standingdocs/MCP.mdfollow-ups and makes theschema_versionclaim indocs/ARCHITECTURE.md§8 true. - Config / IaC language labeling: Dockerfile, Containerfile,
*.tf/*.tfvars(terraform),*.hcl,*.ini/*.cfg/*.conf/*.properties(ini), and Makefiles now get a real language label. These files were already FTS-indexed as unknown text; labeling surfaces infra files instatsand lets agents scope searches to config. They stay on the line/FTS floor (no tree-sitter spec). - Typed framework edges — design doc
(
docs/superpowers/specs/2026-06-14-typed-framework-edges-design.md): the documented-first deliverable for the M13 code-intelligence graph (route→handler→service→model, test→impl, config→consumer, …) with a schema, confidence/provenance model, resolver architecture, and a benchmark gate. - "Trust model in 60 seconds" callout, identical in
README.mdanddocs/SECURITY.md. tests/benchmark_public_RESULTS.md: a logged run of the public benchmark suite (Recall@k / MRR / nDCG / token economy / freshness / graph tasks) with the raw JSON and honest scope notes, per thedocs/BENCHMARKS.mdno-overclaim rule.
-
Reranker: dampened the god-class
in_degreetiebreak (retrieval/rerank.py). The graph-centrality bonus is now logarithmic with a lower cap instead of linear (which saturated by in_degree 10, giving 100-caller "god classes" the full bonus and floating them above genuinely relevant low-degree matches on stray-term ties). Validated as no-regression on the public benchmark (Recall@k / MRR / nDCG unchanged) with a targeted regression test; the real-repo gain on the honest Java misses is tracked under M12.5. CLI/MCPsearchgoldens regenerated accordingly. -
docs/ROADMAP.md: M10 MCP bridge marked shipped (was "planned"); reconciled the technical-vs-product milestone numbering instead of claiming one is canonical. -
README: added "Who Is It For?" and a "How Is This Different?" section that answers why-not-grep / Cursor / Aider repo-map / Sourcegraph / Codebase-Memory MCP on the first screen, plus a proven-today-vs-roadmap table.
-
docs/COMPARISON.md: explicit rows and "choose them when / choose us when" guidance for Continue, Sourcegraph/Cody/Amp, and Codebase-Memory MCP. -
docs/BENCHMARKS.md: a status table separating proven / toy / honest surfaces, an explicit "claims that should NOT be made yet" list, and a TODO-friendly benchmark task checklist with a no-overclaim procedure.
- MCP server failed to import on
mcp>=1.27+pydantic>=2.10: newer FastMCP auto-built a structured-output schema from each tool's-> strreturn annotation and raisedPydanticUserErrorat import time, breaking the server and its test suite. Tools now register as unstructured (structured_output=Falsewhere the kwarg exists; oldermcpis detected and unaffected), preserving the existing text-content wire contract. docs/FAQ.md: removed a dangling/duplicated sentence in "Is it production-ready?" and documented the realclean/clean --allbehavior.
1.3.0 - 2026-06-09
- Content-addressed embedding cache: a new
vec_cachetable (keyed by(model, content_sha)) persists chunk embeddings across rebuilds. Because chunk ids churn on every full rebuild, the embedding pass now hashes chunk content and only calls the (potentially slow or paid) backend for text never embedded under the active model — unchanged content reuses its cached vector for free. - Shared CLI/MCP service layer (
codebase_index/service.py): both surfaces now resolve the index path, run search sessions, and build stats payloads through the same code, so they cannot drift. Two real drifts were closed: MCPsearch_code/explain_codenow blend in vector results when embeddings are enabled (previously the vector channel was CLI-only), and MCPindex_statsnow reports the per-languagegraph: full|partialtier the skill keys on. - Repo-wide graph tier in diagnostics:
statsnow tags each tree-sitter language withgraph: full|partial, anddoctoradds agraph_coveragefinding listing Tier-B languages present in the index. Surfaces upfront which languages have partialrefs/impact(symbols but no import/inheritance edges) instead of only signaling per-query. - Graph coverage signal:
refsandimpactnow report acoverageblock (partial,languages,reason). Import/inheritance edges are only extracted for the hand-tuned (Tier-A) languages, so a symbol or file in a Tier-B language (generic tree-sitter walk, e.g. Lua) can produce an empty/short result that is inconclusive rather than authoritative.coverage.partialflags this so agents fall back to Grep instead of reading "no references" as proof. Markdown output prints a matching warning; the skill documents the field. - Skill-copy sync tooling:
scripts/sync_skill_copies.pyregenerates every committed copy of the skill (.claude/,.codex/,.opencode/,skills/, sharedskill/files) plus all version stamps from the canonicalsrc/codebase_index/skill_template/; CI fails when copies drift (--check). The package version now lives in one place (src/codebase_index/__init__.py) via hatch dynamic versioning. CBX_NO_SKILL_AUTO_UPDATE=1disables the silent skill auto-update — used by the test suite, useful for CI and scripted environments.
- Graph build is batched: edge resolution now runs one query for globally-unique symbol names
and one pass over file paths (in-memory suffix map) instead of per-edge lookups and up to ~20
full-table
LIKEscans per import edge — 7–28× faster on a small repo with identical results, and the gap grows with repository size. Vector blobs are written with a single batchedexecutemany; a newedges(file_id)index removes full-table scans from incremental updates and file-deletion cascades. - Silent failure paths now report to stderr: the ProcessPool→sequential parsing fallback and skill
auto-update failures were previously invisible; vector helpers only swallow
sqlite3.OperationalError(missing vec tables) instead of every exception. - The embedding pass reports cache misses (vectors actually computed) as its "embedded" count.
prune_orphan_vectorsnow deletes stalevec_chunksrows in a single batchedexecutemany.- Skill: documented the
--mode vectorsemantic-search path, theintent/mode/paginationresponse fields, and clarified thatgraph --openrenders an HTML view for a human (useimpact/refsfor agent-readable dependency answers). - Skill: narrowed the skill's
allowed-toolsfromBash(python *)/Bash(python3 *)toBash(python -m codebase_index *)/Bash(python3 -m codebase_index *), so the skill can no longer run arbitrary Python.
searchnow exposes--offset, so the pagination contract is reachable from the CLI/skill. The retrieval pipeline and MCP already supported paging, but the CLI command never surfaced the flag — every call silently returned page one and the advertisedpagination.next_offsetwas a dead end. Markdown output now also notes when more results are available.--offsetrejects negative values.explainnow honors the index freshness contract: it passesroot/configinto the retrieval pipeline, soindex.stale/files_changed_since_buildreflect reality instead of a hardcoded "fresh" block. Previously the skill's freshness check silently never triggered for "how does X work" questions.explainalso blends in vector results when embeddings are enabled, matchingsearch --mode hybrid.- The
cbxwrapper whitelist (skill + pluginbin/) now includesdoctor, which the skill's fallback diagnostics already invoke; previouslycbx doctorwas refused. - The test suite is green on Windows again (
bootstrappath comparison) and no longer rewrites the committed.skill_versionstamps as a side effect of running the CLI inside the checkout. docs/ARCHITECTURE.mdno longer shows two contradictory repository layouts or claimsgraph/is a stub.
- Synced the version to
1.2.2across the package, plugin manifest, and lockfile. - Documentation cleanup: removed stale prompt files and screenshots, refreshed the README.
1.2.1 - 2026-06-05
- Skill auto-update: skills installed via
initnow silently self-update whenever the package version changes. On every CLI invocation the main callback compares the installed.skill_versionstamp against the running package and re-materializes the template, saving a backup first. skill-updatecommand:codebase-index skill-update [--target] [--force] [--no-backup] [--json]for manual skill updates with optional dry-run and JSON output.skill-rollbackcommand:codebase-index skill-rollback [--target] [--json]restores the last backed-up version of installed skill(s).scaffold.materialize_skill()now writes a.skill_versionstamp alongside copied template files so freshness is detectable without an extra network call.
1.2.0 - 2026-06-05
- Interactive graph export via
codebase-index graph [target], producing a local HTML graph of indexed files, symbols, and resolved edges, with optional--openbrowser launch. - Project skill installers now advertise and whitelist the
graphcommand for Claude, Codex, and OpenCode skill resources.
search,symbol,refs,impact, andexplainnow auto-build the local index when it is missing instead of failing with a manual "run index first" step.- Natural-language kind words such as
method,function,class,interface,enum, andtypenow constrain the symbol retriever insidesearch. - Skill wrappers prefer the importable local
python -m codebase_indexmodule before falling back to a potentially stalecodebase-indexexecutable onPATH.
stats --jsonanddoctor --jsonnow work as subcommand flags, matching the documented skill examples and the existing global--jsonbehavior.init --no-hooksis accepted as the explicit counterpart to--with-hooks, preserving the default no-hook install while keeping the CLI option pair discoverable.
1.1.0 - 2026-06-02
- MCP server (
codebase-index mcp): exposes the retrieval layer as MCP tools —search_code,find_symbol,find_refs,impact_of,explain_code, andindex_stats— so MCP-capable editors (Cursor, Claude Desktop, VS Code, Zed, Windsurf) can query the index directly. codebase-index-mcpstandalone entry point for use as a bare MCP server binary.- Multi-client
init:--targetnow accepts five MCP clients in addition to the three skill targets. Each writes the correct JSON config format and merges without overwriting other servers already present:cursor->.cursor/mcp.jsonwindsurf->.windsurf/mcp.jsonvscode->.vscode/mcp.json(withtype: stdio)zed->.zed/settings.json(withcontext_servers)claude-desktop-> platform-specificclaude_desktop_config.json
detect_mcp_targets()auto-detects installed MCP clients during--target auto.- New optional dependency group
mcp(pip install codebase-index[mcp]). tests/benchmark_public.py, a reproducible multi-language public benchmark suite with Recall@1/3/5, MRR, nDCG, answer-correctness proxy, token economy, language breakdown, freshness latency, graph tasks, and scale counters.docs/MCP.mdanddocs/BENCHMARKS.mdfor first-class MCP setup and benchmark usage.
recommended_readswas empty for queries where all results had short symbol-signature snippets (token_est < 40). Added a minimum useful-token threshold so snippets below it are still shown as previews and the result is also added torecommended_reads.
- Aligned README, FAQ, architecture, language support, comparison, installation, and roadmap docs
with the current
1.1.0implementation. - Replaced toy benchmark positioning with the honest benchmark summary and public benchmark suite.
- Corrected Aider repo-map comparison language to acknowledge graph-ranked, token-budgeted maps.
- Distribution is GitHub-only for now: docs and
requirements.lockinstall from the GitHub release tarball pinned tov1.1.0; PyPI/uvx/Homebrew remain distribution-hardening roadmap items.
1.0.2 - 2026-05-29
- Added
codebase-index init --target claude|codex|opencode|auto|all, with an interactive Rich target picker for terminal use. - Added project scaffolding for Codex CLI (
AGENTS.md+ resources) and OpenCode (command, agent, and resources), while preserving the Claude Code skill path.
- Refreshed README positioning and SEO structure around local codebase indexing for AI coding agents, including Claude Code, Codex CLI, and OpenCode.
- Updated quickstart and installation docs for multi-CLI initialization.
1.0.1 - 2026-05-29
- Pinned
tree-sitterandtree-sitter-language-packin package metadata and the plugin bootstrap lock so CI and local installs use the same grammars. - Regenerated CLI golden snapshots against the pinned grammar set.
1.0.0 - 2026-05-29
- Multi-language tree-sitter symbol extraction. Previously a repo of 303 Java files produced
0 symbols, silently disabling
symbol/refs/impact. Java now yields 3,543 symbols; Go/Rust/C/C++/C#/Ruby/PHP/Kotlin plus a Tier-B generic path are covered.
- Symbol-aware retrieval ranking: candidates are scored by how many query terms their camelCase/underscore-split name covers, so multi-word concepts land on multi-word symbols. recall@3 against objective ground truth improved 20% → 70% (vs 40% for a disciplined grep agent) while using ~13× fewer tokens to answer.
- Parse guardrails with
parse_failed/treesitter_zero_symbolscounters anddoctorreporting to lock symbol extraction against silent regression. - Multi-CLI installer for Claude Code / Codex / OpenCode.
- Honest benchmark harness (
tests/benchmark_honest.py) comparing the index against a no-skill grep agent on a real repository.
0.1.0 - 2026-05-29
- Local-first codebase index exposed as a Claude Code Skill +
codebase-indexCLI. index/update: discovery with layered ignore rules, secret/binary/size gates, and incremental re-index (M1, M8).search: FTS5 lexical + hybrid retrieval with RRF fusion, intent detection, token budgeting, confidence scoring, and fallback suggestions (M2, M4).symbol/refs: tree-sitter symbol extraction and reference lookup across supported languages with line-based fallback (M3).impact: dependency/call-graph blast-radius analysis (M5).- Optional, opt-in local embeddings /
sqlite-vecvector backend, gated behindembeddings.enabledand SECURITY.md rules (M6). init: materializes the bundled skill template, resolvedconfig.json, and.gitignorerules; end-to-end freshness contract so the skill triggersupdate/index(M7).- Hooks example +
watchmode for keeping the index fresh without blocking the edit loop (M8). doctor,stats,cleandiagnostics/maintenance commands.