AD2V: Agentic Development to Visualization

See what your agents built, against what you specified.

Coding agents merge code faster than people can understand it. ad2v reads your repository and its spec-driven development (SDD) specs, pairs them up, and writes one SQLite file you can explore as a zoomable map, diff on every pull request, and ask questions about from Claude, ChatGPT or VS Code.

Apache-2.0 open format v0.7 Python ≥ 3.11 no LLM needed pip install ad2v v0.7.0 · early release
The ad2v map: an isometric view of the payments-recon system, with spec files above and the api and worker containers below, colored by status The ad2v map in the light theme
The problem

Comprehension debt

Specs say one thing. Agents write another. Tests cover a third. Nobody reads every diff, so the gap grows quietly until an audit, an incident or a new hire exposes it. ad2v makes that gap visible and measurable, per requirement, per endpoint, per container, per commit.

Specified but missing

A requirement or endpoint with no code behind it, shown as missing, with the exact spec line.

Built but drifting

Code that exists but no longer matches its spec (path, method, shape): drift. Or the spec changed after the code: stale.

Built but unasked

Routes, jobs and tools nobody specified: orphan. Often debug endpoints an agent left behind.

How it works

Read. Pair. Explore.

Extraction is deterministic and makes no LLM calls: the same code, specs and test results give the same file on any OS. ad2v only reads; it never imports or runs your code or tests.

01 · READ

Code, specs, tests, infra

Tree-sitter reads Python (FastAPI, Flask, Starlette routes, workers, env vars). Specs come from OpenAPI, Gherkin, Markdown (spec-kit, Kiro, requirement tables, user stories, EARS; English and Spanish). JUnit results and Terraform plans are optional.

02 · PAIR

One graph, one file

Spec items and code nodes are linked by ids, routes, test names and your manifest. Each node gets a status and a reason. Git history becomes epochs you can diff, with renames followed through lineage.

03 · EXPLORE

Map, PR diff, MCP

ad2v view opens a local 2.5D map. ad2v diff --format md fits a PR comment. ad2v mcp lets any MCP host find and explain components, and draws the map inline.

ad2v on the bundled fixture
$ ad2v extract --repo fixtures/payments-recon --spec fixtures/payments-recon/specs \
    --test-results fixtures/payments-recon/test-results/junit.xml --out recon.ad2v
20 code files (417 lines), 4 spec files, 127 nodes, 226 edges, 16 workflows in 0.24s

$ ad2v status recon.ad2v --side spec
status        kind           qualified_name                           reasons
drift         spec_endpoint  GET /reconciliations/{run_id}/unmatched  link:drift(http:api:GET /v1/…/unmatched)
implemented   requirement    REQ-004                                  link:implemented(test_req_004_…)
missing       spec_endpoint  POST /reconciliations/{run_id}/approve   link:missing
needs_review  spec_endpoint  GET /reconciliations/{run_id}/audit      link:needs_review(http:api:GET /{run_id}/audit)
specified     requirement    REQ-007                                  link:specified

$ ad2v view recon.ad2v      # opens the map on 127.0.0.1, read-only
The status vocabulary

Every node says where it stands, and why

Line style carries the status on the map, so you read the state of a system at a glance, in dark and light themes. Every status comes with machine-readable reasons.

specifiedIn the spec, no code paired yet. Dotted.
implementedPaired with code. Solid.
verifiedImplemented and a passing test covers it. Glows.
driftPaired, but the code no longer matches the spec. Warning badge.
missingThe spec expects code that is not there.
orphanCode no spec asks for. Dashed.
staleThe spec changed after the code it pairs with.
needs_reviewAn ambiguous pairing a human should confirm.
not_evaluableBuilt in a language no active extractor reads (TS, Go, Java…). “∅” badge.
Features

One file, many readers

ad2v is an open format plus reference implementations. The .ad2v file is plain SQLite, validated against a published schema, so you can build your own readers too.

An isometric map with more levels than C4

System → containers → modules → functions, plus spec files floating above. Glyph shape is the node kind; line style is the status. Zoom with the wheel, double-click to enter, / to search, Esc to go up. A deterministic layout keeps boxes in place across epochs.

Served on 127.0.0.1 only, GET/HEAD only, strict CSP. The viewer never writes the file.

ad2v map, api container enteredad2v map, light theme
Design principles

Built to be trusted in audits and CI

Deterministic

Same inputs, same normative dump, byte for byte, on Linux, macOS and Windows (LF vs CRLF+BOM is tested in CI).

Read-only

Never imports or runs repository code, tests or Terraform. Plug-ins are opt-in per repository.

Local-first

The viewer and the MCP server bind to 127.0.0.1 and make no outbound calls. Your code stays on your machine.

AI as advisor

LLM rows carry full provenance and never change an epoch id. Repository content is sent as fenced, untrusted data.

Open format

Versioned spec, SQLite DDL, IR JSON Schema, glyph grammar and visual tokens. ad2v validate checks any file.

Extensible

Stable plug-in API (ad2v.api 1.0) for language extractors and framework packs, with a conformance kit.

Use cases

Who uses ad2v, and for what

Teams shipping with coding agents

Review what the agent actually did

  • Post an ad2v diff on every PR: new orphans, new drift, requirements that lost their tests.
  • Catch debug endpoints and unrequested features before merge.
ad2v diff pr.ad2v --from parent --to head --format md
Spec-driven teams

Measure spec coverage, not just test coverage

  • spec-kit, Kiro, OpenAPI, Gherkin or your own Markdown, side by side.
  • See which requirements are specified, implemented, verified, or gone stale.
ad2v status app.ad2v --side spec --status stale
Tech leads & new hires

Onboard onto a brownfield codebase

  • Zoom from the system down to a function, replay request flows.
  • Ask an MCP host “where is reconciliation approved?” and get node ids back.
ad2v init --repo . && ad2v view app.ad2v
Platform & architecture

Keep code and infrastructure honest

  • Env vars the code reads that no deployment provides, per environment.
  • Unused resources, and a C4 view you can export to Structurizr.
ad2v extract … --infra-plan prod=plan.json && ad2v c4 app.ad2v --env prod
Governance, risk & audit

Traceability you can re-derive

  • Requirement → code → test links with reasons, in one SQLite file per release.
  • A deterministic, canonical JSONL dump as evidence; pin epochs to release labels.
ad2v pin app.ad2v head --label v1.2 && ad2v dump app.ad2v --normative-only
Tool builders

Build on an open format

  • Read .ad2v with any SQLite client, or write an extractor for your language.
  • Use the read-only MCP tools from your own agents.
ad2v extractor check my-lang --fixture tests/fixture
Install

Up and running in five minutes

One command, from PyPI. You need Python ≥ 3.11. The wheel includes the map viewer and the MCP App, so there is nothing to build.

python3 -m venv .venv
source .venv/bin/activate
pip install ad2v
ad2v --version

Prefer isolated CLIs? pipx install ad2v or uv tool install ad2v.

Then map the bundled example

git clone --depth 1 https://github.com/shanglai/ad2v.git
ad2v extract --repo ad2v/fixtures/payments-recon \
  --spec ad2v/fixtures/payments-recon/specs \
  --test-results ad2v/fixtures/payments-recon/test-results/junit.xml \
  --out recon.ad2v
ad2v status recon.ad2v --side spec
ad2v view recon.ad2v

The clone is only for the example project. On your own repository, start with ad2v init --repo .

Read the full guide →

Inputs

Works with the specs you already have

InputFormatsNotes
CodePython (built-in extractor, tree-sitter)FastAPI, Flask, Starlette routes; workers; env reads. Other languages show as not_evaluable; annotate with // ad2v: REQ-001, or add a plug-in.
API specsOpenAPIPaired with routes by method and path; x-ad2v-refs ties endpoints to requirements.
BehaviourGherkin (EN, # language: es)Scenarios tagged @REQ-001.
Markdownad2v convention, spec-kit, Kiro, requirement tables, user stories, EARS (EN/ES), custom regexesAuto-detected in specs/, spec/, docs/specs/, .kiro/specs/, sdd/…
Prose docsAny MarkdownOptional LLM extraction into a proposal you approve (ad2v specs bootstrap).
TestsJUnit XMLTurns implemented into verified. Tests are never run by ad2v.
InfrastructureTerraform / OpenTofu plan JSON, static .tfGCP and AWS core types; only allowlisted attributes and env var names are stored.
Status

Where ad2v is today

Built in public, phase by phase, with a report and ADRs for every decision (81 so far).

PhaseScope
P1–P2Format spec, SQLite schema, deterministic extractors, spec↔code pairing, statuses, drift, visual tokens
P3Multi-epoch storage, parse cache, git history, epoch diff, lineage, stale
P4Bring-your-own-model LLM layer: judge, suggestions, summaries, prose extraction, budgets
P5three.js viewer: deterministic layout, LOD map, replay, epoch diff
P6–P7MCP server + MCP App, retrieval, real-repo readiness, viewer chat
P8–P8.1Plug-in API, blind eval, packaging, CI, security review, not_evaluable
P9Brownfield onboarding: ad2v init, Spanish and English team formats
P10Infrastructure layer, env-var bridge, deterministic C4 view (format v0.7)
0.7.0First release on PyPI
NextTypeScript extractor, more language extractors
FAQ

Questions

Does ad2v need an LLM or an API key?

No. Extraction, pairing, statuses, diff, the viewer and the MCP server are fully deterministic and offline. The LLM layer is optional and you bring your own model (Vertex AI, an OpenAI-compatible server, or the offline fake provider).

Does it run my code or my tests?

Never. It parses source files, reads JUnit XML you produced, and exports history with git archive. It also never runs Terraform; you hand it a plan JSON.

Which languages does it read?

Python today, through the built-in extractor. Code in other languages is shown as not_evaluable instead of being reported as missing, and you can pair it with // ad2v: REQ-001 comments. The plug-in API lets anyone add an extractor.

How do I install it?

pip install ad2v (Python ≥ 3.11). The package includes the map viewer and the MCP App; Node is only needed if you build ad2v from source.

Should I commit the .ad2v file?

No. It contains code snippets and optional LLM outputs; treat it like source. Keep it outside the repo or in a gitignored .ad2v/. Commit your specs and ad2v.yaml instead.

Can I use it in CI?

Yes. An example GitHub Actions workflow builds two epochs (merge base and PR head) and posts ad2v diff --format md as a single PR comment. See the CI guide.

What is the license?

Apache-2.0, for the format and the reference implementation. Dependencies are checked by license gates in CI.

Pay down your comprehension debt

Try the demo in your browser, then point ad2v at your own repository.