{
  "markdown": "<!-- mcp-name: io.github.Karzone/TestAtlas.Mcp -->\n<h1 align=\"center\">\n  <img src=\"https://raw.githubusercontent.com/Karzone/TestAtlas/main/assets/logo-mark.svg\" width=\"40\" height=\"40\" alt=\"\" valign=\"middle\">\n  &nbsp;TestAtlas\n</h1>\n\n<p align=\"center\">\n  <strong>A queryable, semantic map of your .NET test-automation solution — in one SQLite file, served to your AI agent over MCP.</strong>\n</p>\n\n<p align=\"center\">\n  <em>Zero config&nbsp; ·&nbsp; No AI&nbsp; ·&nbsp; No network&nbsp; ·&nbsp; Deterministic</em>\n</p>\n\n<p align=\"center\">\n  <a href=\"https://www.nuget.org/packages/TestAtlas.Mcp\"><img alt=\"TestAtlas.Mcp on NuGet\" src=\"https://img.shields.io/nuget/v/TestAtlas.Mcp?logo=nuget&label=TestAtlas.Mcp&color=004880\"></a>\n  <a href=\"https://www.nuget.org/packages/TestAtlas.Cli\"><img alt=\"TestAtlas.Cli on NuGet\" src=\"https://img.shields.io/nuget/v/TestAtlas.Cli?logo=nuget&label=TestAtlas.Cli&color=004880\"></a>\n  <img alt=\"Model Context Protocol — listed\" src=\"https://img.shields.io/badge/MCP_Registry-listed-7C3AED\">\n  <a href=\"https://glama.ai/mcp/servers/Karzone/TestAtlas\"><img alt=\"Glama — listed\" src=\"https://img.shields.io/badge/Glama-listed-1B8F5A\"></a>\n  <img alt=\".NET 8.0\" src=\"https://img.shields.io/badge/.NET-8.0-512BD4?logo=dotnet&logoColor=white\">\n  <img alt=\"MIT license\" src=\"https://img.shields.io/badge/license-MIT-blue\">\n</p>\n\n<p align=\"center\">\n  <a href=\"https://glama.ai/mcp/servers/Karzone/TestAtlas\"><img width=\"380\" alt=\"TestAtlas on Glama: license, quality and maintenance grades\" src=\"https://glama.ai/mcp/servers/Karzone/TestAtlas/badge\"></a>\n</p>\n\n<p align=\"center\">\n  <sub><b>11 MCP tools</b></sub><br>\n  <sub><code>resolve_step</code> · <code>step_catalog</code> · <code>impact</code> · <code>search_steps</code> · <code>search_scenarios</code> · <code>get_scenario</code> · <code>get_step_definition</code> · <code>list_tags</code> · <code>list_endpoints</code> · <code>project_dependencies</code> · <code>stats</code></sub>\n</p>\n\n<p align=\"center\">\n  <a href=\"#the-problem\">The problem</a> ·\n  <a href=\"#see-it-in-action\">See it in action</a> ·\n  <a href=\"#-quick-start\">Quick start</a> ·\n  <a href=\"#-use-it-from-an-ai-agent-mcp\">MCP</a> ·\n  <a href=\"#-commands\">Commands</a> ·\n  <a href=\"#-keeping-the-map-fresh\">Fresh maps</a> ·\n  <a href=\"#-roadmap\">Roadmap</a>\n</p>\n\n---\n\n## The problem\n\nLarge test-automation solutions are hard to navigate — for humans *and* for AI agents. Asked to\nautomate a new story, an agent can't see which steps already exist, where similar code lives, or\nwhat conventions the solution follows — so it duplicates steps and misplaces code. TestAtlas\nindexes the solution once into a single SQLite map and answers those questions precisely:\ndeterministically, offline, without a model or a network call.\n\n---\n\n## See it in action\n\nIndex the bundled 8-project sample once — `testatlas index samples/SampleShop/SampleShop.sln` — then\nask it questions from the terminal. Every number below is real output from that run:\n\n```console\n$ testatlas stats sampleshop.db\nTestAtlas map: sampleshop.db (schema v5)\n\ntotals: 8 project(s), 15 class(es), 36 method(s), 14 step definition(s)\nclass kinds:\n  api_client     7\n  page_object    4\n  step_class     4\n\ngherkin: 4 feature(s), 5 scenario(s), 16 step(s)\nbound steps: 16 · unbound: 0 · ambiguous: 0\nendpoints: 3 (3 call site(s))\n```\n\n…or let your agent ask them over MCP. Here an agent checks whether a step it is about to write\nalready exists — `resolve_step` answers with the definitions that would bind it, or the closest\nnear-misses to reuse instead:\n\n```jsonc\n// agent → testatlas: resolve_step { \"text\": \"I add the product to my cart\" }\n{\n  \"status\": \"none\",            // nothing binds this exact text — don't invent it from scratch:\n  \"suggestions\": [             // these existing steps are the closest, ranked by shared terms\n    { \"expression\": \"product (.*) is added to the cart with quantity (.*)\",\n      \"keyword\": \"When\", \"location\": \"SampleShop.Tests.Api/Steps/CatalogApiSteps.cs:34\" },\n    { \"expression\": \"the cart is not empty\",\n      \"keyword\": \"Then\", \"location\": \"SampleShop.Tests.Api/Steps/CatalogApiSteps.cs:43\" }\n    // …8 more\n  ]\n}\n```\n\nLive sample outputs, committed from that same solution:\n**[HTML report](https://htmlpreview.github.io/?https://github.com/Karzone/TestAtlas/blob/main/docs/sample-report.html)** (features, scenarios, bindings, class kinds, endpoints) ·\n**[dependency map](https://htmlpreview.github.io/?https://github.com/Karzone/TestAtlas/blob/main/docs/sample-map.html)** (the eight projects and their edges).\n<sub>(GitHub serves `.html` as source, so the links route through htmlpreview.github.io — or download from [`docs/`](docs/) and open locally.)</sub>\n\n## What you get\n\nTestAtlas statically analyses the solution and emits `codemap.db` — projects and their dependency\nedges, Gherkin features/scenarios/steps, step definitions and their bindings (bound / unbound /\nambiguous), page objects, API clients, helpers, test classes, and the call/usage edges connecting\nthem — then turns that map into answers:\n\n| | Capability | What you get |\n|:--:|---|---|\n| 🧩 | **Reuse-first authoring** | `resolve_step` — would this phrase bind an existing definition? `step_catalog` — the reusable step vocabulary with placeholders + allowed values |\n| 💥 | **Impact** | Blast radius — the scenarios affected by changing a class, method, step, or endpoint |\n| 🔍 | **Search** | FTS5 over step definitions + scenarios — *\"does a step for this already exist?\"* |\n| 🔌 | **MCP** | All of it served to an AI agent over stdio — precise answers in a few hundred tokens, no context stuffing |\n| 📊 | **Report & map** | Self-contained HTML drill-down of the whole map + project-dependency graph |\n| 📈 | **Stats** | Entity counts, class-kind breakdown, binding coverage, diagnostics |\n\nAll of it **offline, deterministic, and reproducible** — same input, same map, every time.\n\n---\n\n## 🚀 Quick start\n\n> **Requires** the [.NET SDK 8.0+](https://dotnet.microsoft.com/download). On a corporate machine\n> where `dotnet tool install` fails with **401**, see\n> [docs/troubleshooting.md](docs/troubleshooting.md).\n\n**1 — Install** the CLI (and the MCP server, if you'll connect an agent):\n\n```bash\ndotnet tool install --global TestAtlas.Cli\ndotnet tool install --global TestAtlas.Mcp\n```\n\n**2 — Index** your solution. This produces the map (`./codemap.db`) that every query, report, and\nMCP answer reads — nothing works without it:\n\n```bash\ntestatlas index path/to/YourSolution.sln\n```\n\nNo need to build or restore the solution first — indexing is a syntax-only pass, so an unrestored\ncheckout maps fine. Point `index` at a folder (or nothing) and it auto-discovers a single\n`.sln`/`.csproj` there.\n\n**3 — Query it:**\n\n```bash\ntestatlas stats\ntestatlas search \"login\"\ntestatlas report        # writes codemap.html\ntestatlas map           # writes codemap-map.html\n```\n\n…and to serve it to your AI agent, continue to [MCP setup](#-use-it-from-an-ai-agent-mcp).\n\n<details>\n<summary><b>Or run from source</b> (no install)</summary>\n\n```bash\ngit clone https://github.com/Karzone/TestAtlas.git\ncd TestAtlas\ndotnet build TestAtlas.sln\ndotnet run --project src/CodeMap.Cli -- index path/to/YourSolution.sln\n```\n\n</details>\n\n---\n\n## 🔌 Use it from an AI agent (MCP)\n\nTestAtlas ships an MCP server — `testatlas-mcp` — that serves the map to any MCP-aware client\n(Visual Studio / VS Code Copilot, Claude Code, and others) over stdio JSON-RPC. The agent asks a\nprecise question and gets an exact, structured answer straight from the `.db` — instead of\nstuffing source files into its context window.\n\nPrerequisites: **both tools installed and a map built** — steps 1–2 of the\n[Quick start](#-quick-start). Then register the server:\n\n**Visual Studio / VS Code** (GitHub Copilot agent mode) — add to your `.mcp.json`\n(`%USERPROFILE%\\.mcp.json` or `<SolutionDir>\\.mcp.json`):\n\n```json\n{\n  \"servers\": {\n    \"testatlas\": {\n      \"type\": \"stdio\",\n      \"command\": \"testatlas-mcp\",\n      \"args\": [\"C:\\\\path\\\\to\\\\codemap.db\"]\n    }\n  }\n}\n```\n\n**Pass the map path explicitly** (as above, or via a `TESTATLAS_DB` env var) — most agents launch\nthe server from their own working directory, not your solution folder, so relying on auto-discovery\nmakes the server exit with `code 2`. In Visual Studio you can also use **Tools picker → `+` → Add\ncustom MCP server** to write this entry for you. On the .NET 10 SDK you can skip the install and\nuse `\"command\": \"dnx\", \"args\": [\"TestAtlas.Mcp\", \"--yes\", \"C:\\\\path\\\\to\\\\codemap.db\"]` — `dnx`\nfetches and runs the server on demand.\n\n**Claude Code:**\n\n```bash\nclaude mcp add testatlas -- testatlas-mcp path/to/codemap.db\nclaude mcp list        # the testatlas row should read: ✔ Connected\n```\n\nBy default the server is registered for the **current project** (`--scope local`). Add\n`--scope user` to make it available in every project on your machine, or `--scope project` to\nshare the registration with your team via a committed `.mcp.json`.\n\n> [!IMPORTANT]\n> MCP clients load servers **at session start** — if you register mid-session, restart your agent\n> session before the `testatlas` tools appear. To confirm it's actually being used (and not\n> silently ignored), run the checks in\n> [docs/troubleshooting.md](docs/troubleshooting.md#the-agent-doesnt-seem-to-use-testatlas).\n\n**Tools exposed:**\n\n- `resolve_step` — resolve a Gherkin phrase to the existing step definition(s) that would bind it (regex/cucumber, keyword-agnostic). `exact` / `ambiguous` / `none` (+ near-match suggestions ranked by shared terms). Reuse-first authoring: don't write a step that already exists.\n- `step_catalog` — the reusable step vocabulary with extracted placeholders and allowed values (cucumber `{type}`, regex `(a|b)` enums). Compose scenarios from what exists.\n- `impact` — blast radius of a change: the scenarios affected by a given class, method, step definition, or endpoint.\n- `search_steps` — full-text search over step definitions (expression text + method + class name).\n- `search_scenarios` — full-text search over scenarios (feature + scenario name + step text + tags).\n- `get_scenario` — full detail of scenario(s) by name: feature, tags, kind, example-row count, and the ordered steps.\n- `get_step_definition` — full detail of step definition(s) by expression: keyword, params, C# class/method/signature, and the scenarios that use it.\n- `list_tags` — the tag taxonomy with per-tag scenario counts, most-used first — tag new scenarios consistently.\n- `list_endpoints` — the HTTP endpoints the suite calls, each with verb, route, and scenario blast radius (highest-reach first).\n- `project_dependencies` — the implied project dependency graph (depends-on / depended-on-by), e.g. *\"what depends on the Party project?\"*.\n- `stats` — summary counts: projects, classes, methods, class-kind breakdown, endpoints, and edge tallies.\n\nRetrieval runs locally against the SQLite file — deterministic, offline, and a few hundred tokens\nper answer. Protocol details in [`specs/codemap-mcp.md`](specs/codemap-mcp.md); registration from\nsource and every failure mode in [docs/troubleshooting.md](docs/troubleshooting.md).\n\n---\n\n## 📖 Commands\n\n| Command | What it does |\n| --- | --- |\n| `index [<path>]` | Analyse a `.sln`/`.csproj` and write the map (default `./codemap.db`). |\n| `stats [<db>]` | Entity counts per project, unbound/ambiguous steps, diagnostics. |\n| `search [<db>] <query>` | FTS5 full-text search over step definitions and scenarios. |\n| `impact [<db>] --class\\|--method\\|--step\\|--endpoint <target>` | Blast radius: scenarios affected by changing an entity. |\n| `report [<db>]` | Write a self-contained HTML drill-down of the map. |\n| `map [<db>]` | Write a self-contained project dependency graph (HTML). |\n| `validate [<db>]` | Check a file is a supported TestAtlas map. |\n\n<details>\n<summary><strong>Options &amp; exit codes</strong></summary>\n\n<br>\n\n**`index`** &nbsp;`--output <file>` · `--config <file>` · `--include <glob>` (repeatable) · `--exclude <glob>` (repeatable) · `--verbose` · `--quiet`\n\n**`search`** &nbsp;`--steps` (step definitions only) · `--scenarios` (scenarios only)\n\n**Exit codes** &nbsp;`0` ok · `1` completed with warnings · `2` fatal · `3` bad arguments\n\nRun `testatlas --help` for the full usage text.\n\n</details>\n\n<details>\n<summary><strong>A typical session</strong></summary>\n\n<br>\n\n```bash\n# Index the solution (no build needed — the pass is syntax-only)\ntestatlas index YourSolution.sln --output atlas.db\n\n# Before writing a new step — does one already exist?\ntestatlas search atlas.db \"add a product to the cart\" --steps\n\n# About to change a shared client — what will it hit?\ntestatlas impact atlas.db --class ProductsApiClient\n\n# Share human-readable snapshots\ntestatlas report atlas.db --html atlas.html\ntestatlas map    atlas.db --html atlas-map.html\n```\n\n</details>\n\n<details>\n<summary><strong>About the bundled sample (SampleShop)</strong></summary>\n\n<br>\n\n[`samples/SampleShop`](samples/SampleShop) is a self-contained **8-project** solution mixing API\ntests and UI tests, so the map has plenty of connected nodes — real `HttpClient` API clients, real\nSelenium `IWebDriver` page objects, and Reqnroll suites driving both:\n\n```text\n                       ┌─▶ Api.Catalog  ──┐\nTests.Api  ────────────┼─▶ Api.Cart     ──┤\nTests.E2E  ──┬─────────┴─▶ Api.Identity ──┼─▶ Core   (ApiClientBase : HttpClient)\n             └─▶ Ui.Pages ─────────────────┘          (PageBase      : IWebDriver)\nTests.Ui   ────▶ Ui.Pages ──────────────────▶ Core\n```\n\nReproduce the committed sample outputs yourself:\n\n```bash\ntestatlas index  samples/SampleShop/SampleShop.sln --output sampleshop.db\ntestatlas report sampleshop.db --html docs/sample-report.html\ntestatlas map    sampleshop.db --html docs/sample-map.html\n```\n\n</details>\n\n---\n\n## 🔄 Keeping the map fresh\n\nAnswers are deterministic — but only as fresh as the map, so re-index on *change*, not on a timer.\nA full re-index is a single static pass (**seconds**), and its cost scales with solution size, not\nwith how much changed:\n\n- **Locally** — `python scripts/check-map-age.py` tells you when your map drifted; a\n  version-controlled `post-merge` git hook can warn automatically after every pull.\n- **In CI (team model)** — re-index on every merge to main and publish the `.db` to a shared feed\n  (never commit it — it's a build artifact). Then teammates and agents only need **`TestAtlas.Mcp`**\n  locally: download the shared map and point `TESTATLAS_DB` at it — no local `TestAtlas.Cli` or\n  indexing required. (Index locally only to include your own *uncommitted* branch work.)\n\nDetails — the staleness checker, the git hook, and copy-paste CI recipes (GitHub Actions +\nAzure DevOps with a Universal feed) — in **[docs/keeping-the-map-fresh.md](docs/keeping-the-map-fresh.md)**.\n\n---\n\n## 🧹 Uninstall\n\nTwo separate things — remove them in this order, so the editor isn't launching a server whose binary just vanished:\n\n1. **Remove the MCP registration** — delete the `testatlas` block from your `.mcp.json`\n   (`<SolutionDir>\\.mcp.json` or `%USERPROFILE%\\.mcp.json`), then restart Visual Studio / VS Code.\n   (Or just toggle it off in the agent's tools/wrench picker to keep it for later.)\n2. **Uninstall the tools** — they're .NET global tools, not editor add-ins:\n   ```bash\n   dotnet tool uninstall --global TestAtlas.Mcp\n   dotnet tool uninstall --global TestAtlas.Cli\n   dotnet tool list --global            # confirm they're gone\n   ```\n3. **(Optional)** delete the `codemap.db` map file — it's just data, nothing else references it.\n\n---\n\n## 🎯 Design tenets\n\n- **Zero config** — a useful map on an unseen solution, no config file required.\n- **Solution agnostic** — heuristic, overridable detection; no company-specific assumptions.\n- **Deterministic & offline** — same input ⇒ byte-equivalent logical content; no network, no AI.\n- **Graceful degradation** — solutions without Gherkin still yield a useful map.\n- **Public schema as contract** — a versioned SQLite schema, so downstream consumers keep working\n  even if a third party swaps in their own indexer.\n\n<sub>The project folders use the indexer's working name (**CodeMap**); the shipped tools and\npackages are **TestAtlas**. Full specs: [`specs/codemap-indexer.md`](specs/codemap-indexer.md) ·\n[`specs/codemap-mcp.md`](specs/codemap-mcp.md). Repo layout: [CONTRIBUTING.md](CONTRIBUTING.md#project-layout).</sub>\n\n---\n\n## 🗺 Roadmap\n\n- [x] **Indexer CLI** — C# indexer + documented, versioned SQLite schema\n- [x] **HTML visualization** — self-contained report + project map generated from the db\n- [x] **MCP server** — `testatlas-mcp` exposes the map to AI agents over stdio JSON-RPC (11 tools)\n- [ ] **Second-language indexer** — same schema, contract-tested\n\n**Deliberately not planned** (see [design tenets](#-design-tenets)): LLM-assisted analysis inside\nthe indexer, network calls at index/query time, running or generating tests, and semantic\n(compilation-based) analysis that would require a restored build. Releases and per-version notes\nlive on the [releases page](https://github.com/Karzone/TestAtlas/releases); current distribution\nchannels in [docs/DISTRIBUTION.md](docs/DISTRIBUTION.md).\n\n---\n\n## 📄 License\n\n[MIT](LICENSE) © 2026 Karthik Kalaiyarasu\n",
  "bytes": 17272,
  "sha": "277c88a21d877e9b19e185d00454795ea380e9d67110abccd6d053c469fac1e2",
  "repo_slug": "karzone/testatlas",
  "fonte": "repo",
  "truncated": false,
  "api": "https://agentalog.com/api/listings/mcp_io_github_karzone_testatlas_mcp_4f7d0624/readme"
}