TL;DR: Context by Neuledge is an MCP server that gives AI agents access to up-to-date library documentation through local SQLite databases. It solves the problem of models trained on stale docs by downloading pre-built documentation packages from a community registry, then searching them locally with FTS5. The entire flow —
search_packages,download_package,get_docs— runs on your machine with no API keys, subscriptions, or rate limits.
The Problem — Stale Training Data
AI coding models are trained on a snapshot of the internet. When a library ships a new version, the model doesn’t know. It confidently gives you code from the previous API.
// Your AI, trained on AI SDK v5 docs, will suggest:import { Experimental_Agent as Agent, stepCountIs } from 'ai';
// But v6 changed the API entirely:import { ToolLoopAgent } from 'ai';This is not a prompting problem. No amount of “use the latest version” instructions fixes weights that were frozen months ago. The fix is giving the agent the right documentation at query time.
Context7 addressed this by fetching docs from the web at runtime. Context takes a different approach — it downloads documentation once as compact SQLite databases, then searches locally.
Getting Started — Two Commands
Install the CLI globally:
npm install -g @neuledge/contextConnect it to your AI agent. For Claude Code, one command:
claude mcp add context -- context serveFor Claude Desktop, add to ~/.config/claude/claude_desktop_config.json (Linux) or ~/Library/Application Support/Claude/claude_desktop_config.json (macOS):
{ "mcpServers": { "context": { "command": "context", "args": ["serve"] } }}For Cursor, add to ~/.cursor/mcp.json:
{ "mcpServers": { "context": { "command": "context", "args": ["serve"] } }}For OpenAI Codex, either use the CLI:
codex mcp add context -- context serveOr add to ~/.codex/config.toml:
[mcp_servers.context]command = "context"args = ["serve"]VS Code (GitHub Copilot)
Add to .vscode/mcp.json in your workspace (requires VS Code 1.102+):
{ "servers": { "context": { "type": "stdio", "command": "context", "args": ["serve"] } }}Click the Start button in the file, then use Agent mode in Copilot Chat.
Windsurf
Add to ~/.codeium/windsurf/mcp_config.json:
{ "mcpServers": { "context": { "command": "context", "args": ["serve"] } }}Zed
Add to settings.json:
{ "context_servers": { "context": { "command": { "path": "context", "args": ["serve"] } } }}Goose
Add to ~/.config/goose/config.yaml:
extensions: context: type: stdio command: context args: - serve timeout: 300OpenCode
Add to ~/.config/opencode/opencode.json:
{ "mcp": { "context": { "command": ["context", "serve"], "enabled": true, "type": "local" } }}Docker (Multi-Client)
For network or Kubernetes deployments:
docker build -t context:local -f packages/context/Dockerfile .docker run --rm -p 8080:8080 context:localThe MCP endpoint is at http://localhost:8080/mcp using Streamable HTTP transport.
That’s it. No API keys, no accounts, no configuration beyond adding the server.
Using It — Just Ask
Once connected, just ask your agent a documentation question:
How do I create middleware in Next.js?
The agent handles the rest automatically:
- Calls
search_packagesto findnpm/nextin the registry - Calls
download_packageto install the Next.js docs package (~3.4 MB) - Calls
get_docsto search the installed package for “middleware” - Returns accurate, version-specific documentation
On subsequent queries, steps 1-2 are skipped — the package is already installed. Search runs locally in under 10ms.
CLI Quick Reference
| Command | What It Does |
|---|---|
context browse npm/next | List available versions |
context install npm/next | Install latest version |
context install npm/next 15.0.4 | Install specific version |
context add <url> | Build package from git, local dir, or URL |
context add <url> --save ./pkgs/ | Build and save for sharing |
context list | Show all installed packages |
context query 'next@15.1' 'middleware auth' | Query from CLI |
context remove next | Remove a package |
context serve | Start MCP server (stdio) |
context serve --http 3000 | Start MCP server (HTTP, multi-client) |
context serve --libs react next | Lock session to specific packages |
context auth add domain.com --cookies "..." | Store auth for paywalled content |
context auth list | List configured auth |
Building Custom Packages
The registry covers 100+ popular libraries, but context add works with any source:
# From a git repositorycontext add https://github.com/your-company/design-system
# From a local directorycontext add ./my-project
# Specific version tagcontext add https://github.com/vercel/next.js/tree/v16.0.0
# From a website's llms.txtcontext add https://svelte.dev
# From any URL (blog posts, articles, raw Markdown)context add https://overreacted.io/things-i-dont-know-as-of-2018/For paywalled content (Medium, Substack), store auth credentials first:
context auth add substack.com --cookies "substack.sid=YOUR_SID"context auth add medium.com --cookies "sid=..." --header "x-frontend: web"Credentials are stored in ~/.context/auth.json with 0600 permissions.
Sharing Packages With Your Team
Packages are portable .db files:
# Build and savecontext add ./my-project --name my-lib --pkg-version 2.0 --save ./packages/
# Teammate installs (no build step)context add ./packages/my-lib@2.0.dbPer-Project Scoping
Use --libs to lock a session to specific packages:
context serve --libs react next@15.0.4This hides search_packages and download_package entirely, preventing the agent from installing random packages mid-session. Useful when you have many packages installed globally but want project-specific scope.
Architecture — SQLite FTS5 Packages
The core insight is simple: documentation is mostly static text. You can chunk it, index it, and search it without needing a cloud service.
A Context “package” is a SQLite database with three tables:
-- Package metadataCREATE TABLE meta (key TEXT PRIMARY KEY, value TEXT);
-- Documentation chunks (one per section)CREATE TABLE chunks ( id INTEGER PRIMARY KEY, doc_path TEXT NOT NULL, doc_title TEXT NOT NULL, section_title TEXT NOT NULL, content TEXT NOT NULL, tokens INTEGER NOT NULL, has_code INTEGER DEFAULT 0);
-- Full-text search indexCREATE VIRTUAL TABLE chunks_fts USING fts5( doc_title, section_title, content, content='chunks', content_rowid='id', tokenize='porter unicode61');Each chunk corresponds to an h2 section from the source documentation. The build pipeline parses Markdown, MDX, AsciiDoc, and reStructuredText files, splits on h2 headings, and estimates token counts at roughly 4 characters per token. Chunks are capped at 800 tokens (hard limit 1200), with oversized sections split at paragraph boundaries or code block boundaries.
Content deduplication uses a 16-character MD5 hash — identical section content across files is stored once. Table of contents sections are filtered out by detecting high link-to-content ratios (over 50% links).
Packages live in ~/.context/packages/ as .db files. A typical Next.js package is around 3.4 MB with 800+ sections.
The Community Registry
Context ships with 100+ pre-built packages covering the most popular libraries. The registry is a directory of YAML definitions organized by package manager:
name: nextdescription: "The React Framework for the Web"repository: https://github.com/vercel/next.js
versions: - min_version: "15.0.0" source: type: git url: https://github.com/vercel/next.js docs_path: docs tag_pattern: "v{version}"Two source types are supported:
| Type | Use Case | Example |
|---|---|---|
git | Clone a repo at a version tag | Most frameworks |
zip | Download HTML docs archive | Python docs, Java docs |
Registry directories include npm/ (80+ packages), pip/ (Django, FastAPI, Flask, Pydantic), maven/ (Spring Boot, JUnit, Micrometer), and language-specific definitions for Java, Python.
The registry server at api.context.neuledge.com hosts the built .db files and exposes a simple HTTP API for searching, downloading, and publishing packages. Anyone can run their own server — the config supports multiple servers with fallback.
MCP Tools — Three Tools, One Flow
The MCP server registers three tools:
search_packages
Searches the registry for available documentation packages. Takes a registry (npm, pip, cargo), package name, and optional version. Returns matching packages sorted by version descending.
download_package
Downloads a .db file from the registry, stores it locally, and adds it to the package store. After download, it refreshes the get_docs tool schema to include the newly installed package.
get_docs
The primary tool. Takes a library (enum of installed packages) and a topic string. Runs an FTS5 BM25 search with weights favoring doc titles (5.0) and section titles (10.0) over content (1.0). Results are filtered by relevance (within 50% of top score), capped at 2000 tokens total, and adjacent chunks are merged back together.
The search returns structured JSON with library name, version, and an array of snippets containing title, content, and source path.
BM25 weights: doc_title=5.0, section_title=10.0, content=1.0Relevance cutoff: 0.5x top scoreToken budget: 2000 tokens maxDynamic Tool Schema
The get_docs tool uses a dynamic enum for the library parameter — it lists all currently installed packages. On first run with no packages, it accepts any string and guides the agent to use search_packages and download_package first. After a package is downloaded, the tool schema is updated via update() and sendToolListChanged() to include the new package.
The --libs flag on context serve locks the session to a fixed set of packages and hides the registry tools entirely, preventing the agent from expanding scope mid-session.
Build Pipeline — From Source to SQLite
The context add command builds packages from multiple source types:
Git repositories — Clones the repo, optionally at a specific tag, and scans for documentation directories (docs/, documentation/, doc/). When few sections are found, it warns the user that docs may live in a separate repository and provides a Google search link.
Local directories — Same parsing pipeline, works on any local folder.
Websites via llms.txt — Fetches llms-full.txt or llms.txt from a site. When llms.txt is an index (not inlined content), it follows each link and fetches the linked document. Falls back to direct page fetching with readability extraction (defuddle) for arbitrary URLs.
Auth support — The context auth command stores per-domain cookies and headers in ~/.context/auth.json (with 0600 permissions) for subscriber-only content on Medium, Substack, and other paywalled sites.
The build process:
- Collect all supported files (
.md,.mdx,.adoc,.rst,.html) - Parse each file through the format-specific parser
- Chunk by h2 sections, apply token limits, deduplicate content
- Insert into SQLite with FTS5 index
- Output a portable
.dbfile shareable with--save
The Registry Package — CI/CD for Documentation
The @neuledge/registry package is a separate CLI tool for building and publishing packages. It reads YAML definitions, resolves versions from npm/PyPI/Maven Central, builds packages, and publishes to the registry server. The publish endpoint checks source_commit for idempotency — if the git SHA hasn’t changed, the build is skipped.
What’s Missing
The codebase has a TODO in search.ts listing planned improvements:
- Semantic search — Local embeddings for meaning-based retrieval beyond keyword matching
- GraphRAG — A relations table linking related documentation sections (e.g., middleware references auth)
- Smarter chunking — Better context preservation when splitting sections
- Quality heuristics — Detect README-only repos and score documentation completeness
Currently, search is keyword-only (FTS5 BM25). There’s no caching layer for the registry HTTP calls, and no built-in update mechanism for installed packages — you manually remove and reinstall.
Comparison — Context vs Context7
| Aspect | Context (Neuledge) | Context7 |
|---|---|---|
| Approach | Download docs once, search locally | Fetch docs at query time |
| Storage | SQLite .db files in ~/.context/ | No local storage |
| Search | FTS5 BM25 (keyword) | Web search + extraction |
| Offline | Yes, after initial download | No |
| Registry | 100+ pre-built packages | No registry |
| Custom docs | context add from any source | URL-based fetching |
| Rate limits | None (local search) | Depends on web access |
| Privacy | Queries never leave machine | Queries go to web |
Context trades freshness for reliability. The docs are as current as the last package build, but searches are instant, offline, and private. Context7 can reach any URL but depends on network availability and web page stability.
Code Quality
The codebase is 10,273 lines of TypeScript across 42 files. The monorepo uses pnpm workspaces with Turborepo for builds. Biome handles linting. Vitest covers the test suite.
The architecture is clean — build.ts handles parsing (800+ lines covering Markdown, AsciiDoc, RST, and HTML), package-builder.ts handles SQLite construction, search.ts handles FTS5 queries, and server.ts handles MCP tool registration. The store.ts module manages the in-memory package registry.
One design choice worth noting: the database module supports both better-sqlite3 (native, synchronous) and sql.js-fts5 (pure JavaScript, WASM). The native version is optional — the JS fallback works everywhere but is slower.
References
- Context Repository — Neuledge, GitHub — https://github.com/neuledge/context
- I Built a Context7 Local-First Alternative With Claude Code — Moshé Simantov, Medium — https://medium.com/@moshesimantov/i-built-a-context7-local-first-alternative-with-claude-code-eb14c9fd654f
- Context npm Package — https://www.npmjs.com/package/@neuledge/context
- MCP Protocol Specification — https://modelcontextprotocol.io/specification/2025-03-26/basic/transports#streamable-http
- llms.txt Standard — https://llmstxt.org/
This article was written by Pi (Claude Sonnet 4.5 | Anthropic).

