Model or dataset
arabold/docs-mcp-server avatar
arabold/docs-mcp-server

Grounded Docs MCP Server: a local documentation index your AI client can query by version

Grounded Docs MCP Server: Open-Source Alternative to Context7, Nia, and Ref.Tools

1,725 stars182 forksTypeScriptMIT

At a glance

What is it?
Grounded Docs MCP Server (arabold/docs-mcp-server) is a TypeScript, MIT-licensed tool that crawls official documentation into a local index and exposes it to MCP clients over SSE or through a CLI. It is aimed at developers who want version-pinned answers from their own machine, and its main cost is that you own the index, the embedding provider and the refresh schedule.
Who is it for?
Adopt Grounded Docs MCP Server if you want documentation retrieval to stay on your own machine, if you need to index private repositories or local folders that a hosted service cannot see, or if you are pinning answers to a specific library version. Do not adopt it if you want a zero-maintenance hosted endpoint, if you cannot run Node.js 22 or a container, or if you have no way to supply an embedding provider and are unwilling to accept keyword-only search quality.
Can I use it commercially?
Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 17 days ago.
What is it written in?
Mainly TypeScript, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on September 15, 2026, and from our analysis. They are not legal advice.

DEEP OPEN-SOURCE ANALYSIS

The problem: your assistant answers from training data, not from the version you installed

An AI coding assistant that has never seen the current release notes will answer questions about an API from whatever was in its training data. The README frames the project as a fix for exactly that: it "solves the problem of AI hallucinations and outdated knowledge by providing a personal, always-current documentation index for your AI coding assistant." The intended user is someone whose assistant already speaks MCP, which the README describes as "any MCP-compatible client (Claude, Cline, etc.)", and who wants the retrieval layer to point at an exact library version rather than at a general web answer. The repository topics list copilot, cursor, vscode and windsurf, so the assumed audience is people wiring documentation into an editor-integrated agent rather than into a chat window. It is also explicitly positioned as the open-source option against Context7, Nia and Ref.Tools, which is a statement about deployment model as much as about features: the README says it "runs entirely on your machine; your code never leaves your network."

What actually gets indexed, and the formats that decide whether it is worth trying

The ingestion surface is wider than a typical docs scraper. The README lists documents (PDF, Word, Excel, PowerPoint, OpenDocument, RTF, EPUB, FictionBook, Jupyter Notebooks), archives (ZIP, TAR, gzipped TAR, with contents "extracted and processed individually"), web pages (HTML, XHTML), markup (Markdown, MDX, reStructuredText, AsciiDoc, Org Mode, Textile, R Markdown), source code across what the README calls "90+ source code languages", data formats (JSON, YAML, TOML, CSV, XML, SQL, GraphQL, Protocol Buffers) and config files (Dockerfile, Makefile, Terraform/HCL, INI, dotenv, Bazel). The practical effect is that you can point it at a vendor's PDF spec, a GitHub repository, an npm or PyPI package, a local folder or a zip archive, and get one query surface over all of them. That breadth is the strongest argument for the project over a hosted docs service, because most hosted services index public websites only. The counter-argument is that breadth here means a large number of parsers, and the README itself defers the detail to docs/concepts/supported-formats.md "for the complete reference including MIME types and processing details", which is where you should look before assuming a specific format in your corpus is handled well.

Two ways to run it: a short-lived CLI and a long-running MCP endpoint on port 6280

The README presents the CLI as the simpler path "for agents and scripts", and it requires Node.js 22 or newer. Indexing a site looks like this: npx @arabold/docs-mcp-server@latest scrape react https://react.dev/reference/react. Querying the resulting index is a separate command: npx @arabold/docs-mcp-server@latest search react "useEffect cleanup" --output yaml. There is also a single-page mode, fetch-url, which returns one page as Markdown and, per the README, keeps its text payload on stdout while other commands emit structured output. The output contract is worth reading closely if you are scripting against it: structured commands default to clean JSON on stdout in non-interactive runs, --output json|yaml|toon selects a format, diagnostics go through a shared logger and stay off stdout, and --quiet or --verbose control diagnostic volume. That separation is what makes the CLI usable from an agent without the agent parsing log noise. For a persistent endpoint you run the server with no arguments, open the Web UI at http://localhost:6280 to add documentation, and register an SSE server in your client config under mcpServers with "type": "sse" and "url": "http://localhost:6280/sse". A Docker alternative is documented with named volumes for /data and /config and the flags --protocol http --host 0.0.0.0 --port 6280.

Markdown negotiation and llms.txt probing, the two scraping behaviours that change results most

Before it crawls normally, a web scrape or refresh probes for llms.txt at the documentation subpath and at the site root. When one is found, the README states that "the curated links become additional crawl seeds", and pages discovered through that path prefer .md URL variants such as /guide/index.html.md before falling back to the original page. Requests also send an Accept header of text/markdown, text/html;q=0.9, */*;q=0.8 by default, so servers that support Markdown content negotiation can return Markdown directly instead of HTML that has to be converted. This matters because it changes what the index contains: a site publishing an llms.txt will be seeded from a curated list rather than from link discovery, and a site that negotiates Markdown will produce cleaner text. It also means two runs against the same site can differ depending on whether the site publishes those affordances. If you are comparing retrieval quality between this tool and another, that difference is a confounder, not a bug. The hash-routing path is the other special case: --preserve-hashes, the MCP preserveHashes parameter, or the Web UI "Preserve Hash Routes" checkbox should be used only for sites that route with URLs like #/guide. The README warns that enabling it with scrapeMode=fetch causes the scraper to upgrade the job to Playwright, because plain fetch cannot evaluate client-side hash routes, and that refresh reuses the stored preserveHashes setting unless a CLI or Web refresh entrypoint overrides it.

Embeddings are optional, and that is the decision that sets your search quality

The README is direct about this: using an embedding model is "optional but dramatically improves search quality by enabling semantic vector search." The shortest path is to pass a key in the environment, as in OPENAI_API_KEY="sk-proj-..." npx @arabold/docs-mcp-server@latest, and docs/guides/embedding-models.md covers Ollama, Gemini, Azure and others. Two consequences follow. First, if you skip embeddings you are relying on lexical matching, and a query phrased differently from the documentation wording is more likely to miss. Second, if you enable embeddings you have chosen a provider, and with a hosted provider you have reintroduced an outbound network dependency into a tool whose selling point is that it runs locally, unless you point it at a local model such as Ollama. The project also ships a benchmark guide, docs/guides/benchmarking.md, described as measuring retrieval quality with IR metrics plus LLM-judged scores, including prerequisites, how to run it and how to interpret results. That is the honest way to settle the embedding question for your own corpus, because retrieval quality on React reference pages says little about retrieval quality on a vendor PDF set.

Where it stops being the right tool

The index is yours to maintain. Nothing in the README describes a hosted sync, a shared team index, or an automatic upstream refresh that runs without you; refresh is an operation you or your client trigger, and the preserveHashes behaviour on refresh is documented precisely because it is stateful. If your team expects documentation to be current without anyone running a scrape, this is the wrong shape of tool. The Node.js 22 floor is a second constraint for anyone on an older runtime, and the container path is the documented way around it. The third limitation is subtler: this is retrieval infrastructure, not an answer engine. It returns indexed documentation to a client that then reasons over it, so the quality of the final answer still depends on the model and on how the client uses the MCP tools. A team looking for a service that answers questions directly is buying a different product. Finally, the README's own format table pushes detail into docs/concepts/supported-formats.md, which is a reasonable documentation choice but also a signal that per-format behaviour is not something you can assume from the top-level list.

The real alternative is a hosted documentation service, and the difference is who holds the index

Context7, Nia and Ref.Tools are named in the README as the alternatives this project replaces. The architectural difference is not the feature list, it is custody. A hosted service indexes public documentation on its own schedule and serves it to your client over the network; you get currency without operating anything, and you accept that the corpus is what the vendor chose to index. Grounded Docs inverts that. You choose the sources, including sources a hosted service cannot reach, such as a private GitHub repository, a local folder, or a zip archive of vendor documentation. You run the process, on your machine or in a container on port 6280. You pay in operational work: scraping, refreshing, and deciding whether to configure embeddings. The README's privacy claim, that code never leaves your network, only holds if you also keep the embedding provider local, which is why the Ollama option in docs/guides/embedding-models.md is the configuration that actually delivers the promise. If you use a hosted embedding API, you have a hybrid: local index, remote vectors.

Licence and the cost of keeping it current

The repository is MIT licensed, which permits commercial and private use with the usual requirement to preserve the licence notice; this is a description of the licence text, not legal advice, so read the LICENSE file in the repository if the distinction matters to your organisation. On maintenance, the release history shows v3.0.0, v3.0.1 and v3.1.0 within roughly three weeks of each other in August 2026, so the project is moving quickly and you should expect to re-read configuration documentation across minor versions rather than treating a pinned version as final. The upgrade surface is small if you use npx with the @latest tag, because each invocation pulls the current build, but that also means you are upgrading every time you run it; pinning an explicit version in scripts is the alternative. The larger ongoing cost is not the software, it is the corpus. Every documentation source you add is a source you have to refresh, and the only refresh controls the README documents are the CLI and Web entrypoints plus the preserveHashes override. Budget for that before you index twenty libraries.

Editorial conclusion

Adopt Grounded Docs MCP Server if you want documentation retrieval to stay on your own machine, if you need to index private repositories or local folders that a hosted service cannot see, or if you are pinning answers to a specific library version. Do not adopt it if you want a zero-maintenance hosted endpoint, if you cannot run Node.js 22 or a container, or if you have no way to supply an embedding provider and are unwilling to accept keyword-only search quality. Before committing, run the CLI scrape and search pair against one library you actually use, then check the index with and without an embedding model configured, because the README states that embeddings are optional but that they dramatically improve search quality. Also read docs/guides/benchmarking.md and run the documented benchmark on your own corpus before you trust retrieval quality on a large documentation set.

Official sources

  1. arabold/docs-mcp-server on GitHub
  2. License: MIT
  3. Project website
  4. README
  5. Releases
Community notes

Community notes