feat: add plugin manifest and update README

Add .claude-plugin/plugin.json and .mcp.json for plugin marketplace
distribution. Update README with plugin install instructions and
include plugin files in npm package.
This commit is contained in:
Mert Koseoglu
2026-02-23 09:15:05 +03:00
parent 60a1a2543d
commit d114a1924c
4 changed files with 265 additions and 102 deletions
+29
View File
@@ -0,0 +1,29 @@
{
"name": "context-mode",
"version": "0.4.0",
"description": "Claude Code MCP plugin that saves 94% of your context window. Sandboxed code execution in 10 languages, FTS5 knowledge base with BM25 ranking, and smart truncation.",
"author": {
"name": "Mert Koseoğlu",
"url": "https://github.com/mksglu"
},
"homepage": "https://github.com/mksglu/claude-context-mode#readme",
"repository": "https://github.com/mksglu/claude-context-mode",
"license": "MIT",
"keywords": [
"mcp",
"context-window",
"sandbox",
"code-execution",
"fts5",
"bm25",
"playwright",
"context7"
],
"mcpServers": {
"context-mode": {
"command": "node",
"args": ["${CLAUDE_PLUGIN_ROOT}/build/server.js"]
}
},
"skills": "./skills/"
}
+8
View File
@@ -0,0 +1,8 @@
{
"mcpServers": {
"context-mode": {
"command": "node",
"args": ["${CLAUDE_PLUGIN_ROOT}/build/server.js"]
}
}
}
+226 -102
View File
@@ -2,146 +2,277 @@
**Claude Code MCP plugin that saves 94% of your context window.**
Every MCP tool call, every `cat` of a log file, every documentation lookup eats into your 200K token context. Context Mode intercepts these operations, processes them in isolated subprocesses, and returns only what matters — keeping your context window clean for actual problem-solving.
Every tool call in Claude Code consumes context tokens. A single Playwright snapshot is 5-50KB. A Context7 docs lookup is 5-60KB. A `gh pr list` dumps 2-20KB. After 30 minutes of real debugging, you've burned 150K+ tokens and responses slow to a crawl.
## The Problem
Context Mode intercepts these operations, processes data in isolated subprocesses, and returns only what matters.
A typical Claude Code debugging session burns through context fast:
## Before / After
| Operation | Without Context Mode | With Context Mode |
|-----------|---------------------|-------------------|
| Read access.log (500 req) | **45.1 KB** into context | **71 B** summary |
| Fetch React useEffect docs | **60.3 KB** raw HTML | **285 B** search result |
| `npm test` output (30 suites) | **6.0 KB** raw output | **37 B** pass/fail |
| Git log (153 commits) | **11.6 KB** raw log | **18 B** summary |
| **Total** | **123 KB** (~31K tokens) | **411 B** (~100 tokens) |
| What you're doing | Without Context Mode | With Context Mode | Savings |
|---|---|---|---|
| Playwright `browser_snapshot` | 12 KB snapshot into context | 50 B element summary | **99%** |
| Context7 `query-docs` (React) | 60 KB raw documentation | 285 B search result | **99%** |
| `gh pr list` / `gh api` | 8 KB JSON response | 40 B formatted summary | **99%** |
| Read `access.log` (500 req) | 45 KB raw log | 71 B status breakdown | **99%** |
| `npm test` (30 suites) | 6 KB raw output | 37 B pass/fail count | **99%** |
| Git log (153 commits) | 12 KB raw log | 18 B summary | **99%** |
| Supabase Edge Functions docs | 4 KB raw docs | 123 B code example | **97%** |
After 30 minutes, sessions hit context limits and degrade to 60s+ responses. Context Mode prevents this.
**Real aggregate across 13 scenarios: 194 KB raw → 12.6 KB context (94% savings)**
## Quick Start
### Option 1: Claude Code Plugin (Recommended)
```bash
claude mcp add-json context-mode '{"type":"stdio","command":"npx","args":["-y","context-mode"]}'
/plugin install context-mode@claude-plugin-directory
```
Restart Claude Code. Done. 5 tools are now available.
Installs as a Claude Code plugin with skills and MCP server bundled together.
### Per-Project Setup (team-shared)
### Option 2: MCP Server Only
Add `.mcp.json` to your project root:
```json
{
"mcpServers": {
"context-mode": {
"command": "npx",
"args": ["-y", "context-mode"]
}
}
}
```bash
claude mcp add context-mode -- npx -y context-mode
```
Restart Claude Code. 5 tools are now available.
## What Problems Does It Solve?
### Problem 1: MCP tools flood your context
Popular MCP servers return large payloads that eat tokens:
| MCP Server | Tool | Typical Output |
|---|---|---|
| **Playwright** | `browser_snapshot` | 5-50 KB per page |
| **Context7** | `query-docs` | 5-60 KB per query |
| **GitHub** | `gh api`, `gh pr view` | 2-20 KB per call |
| **Supabase** | schema/RLS queries | 3-15 KB per query |
| **Memory** | `search_nodes` | 1-10 KB per search |
Context Mode gives you `fetch_and_index` and `index` → `search` to keep raw data out of context.
### Problem 2: File operations are wasteful
Reading a 500-line log file with `cat` puts 45KB into context. You only needed "how many 500 errors?"
Context Mode's `execute_file` reads the file in a subprocess — only your printed summary enters context.
### Problem 3: Command output is too large
`npm test`, `git log`, `docker ps`, `kubectl get pods` — all produce output that's mostly noise.
Context Mode's `execute` runs commands in a sandbox. You write the filtering code, only the result enters context.
## Tools
### `execute` — Run Code in Sandbox
Runs code in an isolated subprocess. Only `stdout` enters context.
10 languages: JavaScript, TypeScript, Python, Shell, Ruby, Go, Rust, PHP, Perl, R
**10 languages:** JavaScript, TypeScript, Python, Shell, Ruby, Go, Rust, PHP, Perl, R
```
Claude calls: execute({ language: "shell", code: "gh pr list --json title,state | jq length" })
Returns: "3" ← 2 bytes instead of 8KB JSON
```
Authenticated CLI tools (`gh`, `aws`, `gcloud`, `kubectl`, `docker`) work out of the box — auth credentials are passed through securely.
When Bun is installed, JS/TS runs 3-5x faster automatically.
Authenticated CLIs work out of the box — `gh`, `aws`, `gcloud`, `kubectl`, `docker` credentials are passed through securely. Bun auto-detected for 3-5x faster JS/TS.
### `execute_file` — Process Files Without Loading
Reads a file into a `FILE_CONTENT` variable inside the sandbox. The file contents never enter context — only your printed summary does.
File contents never enter context. Loaded into `FILE_CONTENT` variable in the sandbox.
**Use for:** Log analysis, CSV aggregation, JSON inspection, test output parsing.
```
Claude calls: execute_file({ path: "access.log", language: "python", code: "..." })
Returns: "200: 312 | 404: 89 | 500: 14" ← 30 bytes instead of 45KB
```
### `index` — Build a Knowledge Base
### `index` — Build Searchable Knowledge Base
Indexes content into a searchable BM25 knowledge base. Chunks markdown by headings, keeps code blocks intact, stores in ephemeral FTS5 database.
Chunks markdown by headings. Keeps code blocks intact. Stores in ephemeral FTS5 database with BM25 ranking.
**Use for:** API docs, framework guides, README files, any content with code examples.
```
Claude calls: index({ content: <60KB React docs>, source: "React useEffect" })
Returns: "Indexed 33 sections (15 with code)" ← 40 bytes
```
### `search` — Retrieve Exact Content
BM25 full-text search across indexed content. Returns exact code blocks and documentation — not summaries.
BM25 full-text search with Porter stemming. Returns exact code blocks — not summaries.
```
Claude calls: search({ query: "useEffect cleanup function" })
Returns: exact code example with heading context ← 500 bytes instead of 60KB
```
### `fetch_and_index` — Fetch & Index URLs
Fetches a URL, converts HTML to markdown, and indexes into the knowledge base. Raw content never enters context.
Fetches URL in subprocess, converts HTML to markdown, indexes into FTS5. Raw content never enters context.
**Use for:** Documentation lookups without burning context. Replaces WebFetch for docs you'll reference multiple times.
```
Claude calls: fetch_and_index({ url: "https://react.dev/reference/react/useEffect" })
Returns: "Indexed 33 sections (15 with code)" ← 40 bytes instead of 60KB
```
Use instead of WebFetch or Context7 when you need documentation — index once, search many times.
## How It Works
```
Without Context Mode:
Claude Code → WebFetch docs → 60KB raw HTML → context fills up
Claude Code → Bash npm test → 50KB raw output → context fills up
Claude Code → gh pr list → 20KB JSON → context fills up
┌──────────────────────────────────────────────────────────────────┐
│ Without Context Mode │
│ │
│ Claude Code → Playwright snapshot → 12KB into context │
│ Claude Code → Context7 docs → 60KB into context │
│ Claude Code → gh pr list → 8KB into context │
│ Claude Code → cat access.log → 45KB into context │
│ │
│ Total: 125KB consumed = ~32,000 tokens = 16% of context gone │
└──────────────────────────────────────────────────────────────────┘
With Context Mode:
Claude Code → fetch_and_index(url) → "Indexed 8 sections" (50B)
Claude Code → execute("npm test") → "132 pass, 8 fail" (30B)
Claude Code → execute("gh pr list") → "3 open PRs: #42, #38, #35" (40B)
Claude Code → search("useEffect") → exact code block (500B)
┌──────────────────────────────────────────────────────────────────┐
│ With Context Mode │
│ │
│ Claude Code → fetch_and_index(url) → "Indexed 8 sections" (50B)│
│ Claude Code → search("snapshot") → exact element (500B) │
│ Claude Code → execute("gh pr list") → "3 open PRs" (40B)│
│ Claude Code → execute_file(log) → "500:14, 404:89" (30B)│
│ │
│ Total: 620B consumed = ~160 tokens = 0.08% of context │
└──────────────────────────────────────────────────────────────────┘
```
Data processing happens in subprocesses, not in the context window.
## Architecture
```
┌─────────────┐ stdio / JSON-RPC ┌──────────────────────────────┐
│ │ ◄──────────────────────► │ Context Mode MCP Server │
│ Claude Code │ tool calls/results │ │
│ │ │ ┌────────────────────────┐ │
└─────────────┘ │ │ PolyglotExecutor │ │
│ │ • 10 language runtimes │ │
│ │ • Sandboxed subprocess │ │
│ │ • Auth passthrough │ │
│ │ • Smart truncation │ │
│ └────────────────────────┘ │
│ │
│ ┌────────────────────────┐ │
│ │ ContentStore │ │
│ │ • SQLite FTS5 │ │
│ │ • BM25 ranking │ │
│ │ • Porter stemming │ │
│ │ • Heading-aware chunks │ │
│ └────────────────────────┘ │
└──────────────────────────────┘
```
### Sandbox Isolation
Each `execute` call spawns an isolated subprocess with:
- **Isolated temp directory** per execution — scripts can't access each other
- **Real HOME** — so `gh`, `aws`, `gcloud` find their auth configs
- **Auth passthrough** — GH_TOKEN, AWS credentials, KUBECONFIG, Docker, npm tokens, XDG paths
- **Clean environment** — PATH, LANG, NO_COLOR, Python unbuffered mode
### FTS5 Knowledge Base
The `index` and `search` tools use SQLite FTS5 with BM25 ranking:
```sql
-- Schema
CREATE VIRTUAL TABLE chunks USING fts5(
title, -- heading hierarchy, weighted 2x
content, -- section text + code blocks
source_id UNINDEXED,
content_type UNINDEXED, -- "code" or "prose"
tokenize='porter unicode61' -- stemming + unicode support
);
-- Search query
SELECT title, content, bm25(chunks, 2.0, 1.0) AS rank
FROM chunks
WHERE chunks MATCH ?
ORDER BY rank LIMIT 3;
```
**Chunking algorithm:**
- Splits on H1-H4 headings and `---` separators
- Tracks heading hierarchy: `"React > Hooks > useEffect > Cleanup"`
- Keeps code blocks intact — never splits mid-block
- Marks chunks as `code` or `prose` for content-type filtering
- Porter stemming: "connecting" matches "connect", "connection", "connected"
**Lazy singleton:** Database created only when `index` or `search` is first called — zero overhead for sessions that don't use it.
### Smart Truncation
When subprocess output exceeds the 100KB buffer, Context Mode preserves both head and tail:
```
Head (60%): Initial output with context
... [47 lines / 3.2KB truncated — showing first 12 + last 8 lines] ...
Tail (40%): Final output with errors/results
```
Line-boundary snapping — never cuts mid-line. Error messages at the bottom are always preserved.
### HTML to Markdown Conversion
`fetch_and_index` converts HTML in a subprocess (raw HTML never enters context):
1. Strip `<script>`, `<style>`, `<nav>`, `<header>`, `<footer>`
2. Convert `<h1>`-`<h4>` to `#`-`####` markdown headings
3. Convert `<pre><code>` to fenced code blocks with language detection
4. Convert `<a>`, `<li>`, `<p>`, `<br>`, `<hr>` to markdown
5. Decode HTML entities (`&amp;`, `&lt;`, `&nbsp;`, etc.)
6. Collapse excessive whitespace
## Benchmarks
Measured across 13 real-world scenarios:
### Real MCP Ecosystem Comparison
| Tool | Use Case | Raw | Context | Savings |
|------|----------|-----|---------|---------|
| `fetch_and_index` | API documentation | 9.4 KB | 50 B | **99%** |
| `execute` | Git log (153 commits) | 11.6 KB | 18 B | **100%** |
| `execute_file` | Access log (500 requests) | 45.1 KB | 71 B | **100%** |
| `execute_file` | Analytics CSV (500 rows) | 85.5 KB | 11.5 KB | **87%** |
| `execute_file` | MCP tools manifest (40 tools) | 17.0 KB | 78 B | **100%** |
| `index + search` | React docs → useEffect | 5.9 KB | 285 B | **95%** |
| `index + search` | Supabase Edge Functions | 3.9 KB | 123 B | **97%** |
| `index + search` | Next.js docs → routing | 6.5 KB | 273 B | **96%** |
Tested with tools from popular MCP servers and Claude Code workflows:
**Aggregate: 194 KB raw → 12.6 KB context = 94% savings**
| Scenario | Tool | Raw | Context | Savings |
|---|---|---|---|---|
| Playwright page snapshot | `execute_file` | 50+ KB | 78 B | **99%** |
| Context7 React docs | `index + search` | 5.9 KB | 285 B | **95%** |
| Context7 Supabase docs | `index + search` | 3.9 KB | 123 B | **97%** |
| Context7 Next.js docs | `index + search` | 6.5 KB | 273 B | **96%** |
| httpbin.org API docs | `fetch_and_index` | 9.4 KB | 50 B | **99%** |
| GitHub API response | `execute` | 8+ KB | 40 B | **99%** |
| Access log (500 req) | `execute_file` | 45.1 KB | 71 B | **100%** |
| Analytics CSV (500 rows) | `execute_file` | 85.5 KB | 11.5 KB | **87%** |
| MCP tools manifest (40 tools) | `execute_file` | 17.0 KB | 78 B | **100%** |
| npm test (30 suites) | `execute_file` | 6.0 KB | 37 B | **99%** |
| Git log (153 commits) | `execute` | 11.6 KB | 18 B | **100%** |
### Session Impact
Typical 45-minute debugging session:
| Metric | Without | With | Delta |
|--------|---------|------|-------|
|---|---|---|---|
| Context consumed | 177 KB | 10 KB | **-94%** |
| Estimated tokens | ~45,300 | ~2,600 | **-94%** |
| Window remaining | 77% | 95% | **+18pp** |
## Smart Truncation
When output exceeds the buffer, Context Mode keeps both the head (initial context) and tail (errors/results):
```
First 12 lines of output...
... [47 lines / 3.2KB truncated — showing first 12 + last 8 lines] ...
Last 8 lines with error messages
```
60% head + 40% tail, snapped to line boundaries.
| Tokens used | ~45,300 | ~2,600 | **-94%** |
| Context remaining | 77% | 95% | **+18pp** |
| Time before slowdown | ~30 min | ~3 hours | **+6x** |
## Tool Decision Matrix
| Data Type | Best Tool | Why |
|-----------|-----------|-----|
| Web documentation | `fetch_and_index` | Raw HTML never enters context |
| API references | `fetch_and_index` → `search` | Index once, search many times |
|---|---|---|
| Web documentation | `fetch_and_index` → `search` | Index once, search many times |
| MCP tool output (large) | `index` → `search` | Keep raw output out of context |
| Log files | `execute_file` | Aggregate stats |
| Test output | `execute_file` | Pass/fail summary |
| CSV / JSON data | `execute_file` | Computed metrics |
| Git operations | `execute` | `gh`, `git` commands work natively |
| Build output | `execute` | Error counts and warnings |
| Git / GitHub operations | `execute` | `gh`, `git` commands with auth |
| Cloud CLI | `execute` | `aws`, `gcloud`, `kubectl` with auth |
| Source code to edit | Plain `Read` tool | Need full content |
| Build output | `execute` | Error counts and warnings |
| Source code to edit | Plain `Read` tool | Need full content for edits |
| Small files (<20 lines) | Plain `Read` tool | Minimal overhead |
## Requirements
@@ -149,30 +280,23 @@ Last 8 lines with error messages
- **Node.js 18+**
- **Claude Code** with MCP support
### Optional Runtimes (auto-detected)
### Auto-Detected Runtimes
Bun (3-5x faster JS/TS), Python 3, Ruby, Go, Rust, PHP, Perl, R
| Runtime | Used For | Speed |
|---|---|---|
| Bun (optional) | JS/TS execution | 3-5x faster than Node |
| Python 3 | Python code | Standard |
| Ruby, Go, Rust, PHP, Perl, R | Respective languages | Standard |
## Architecture
## Test Suite
```
┌─────────────┐ stdio / JSON-RPC ┌──────────────────┐
│ │ ◄──────────────────────► │ Context Mode │
│ Claude Code │ tool calls/results │ MCP Server │
│ │ │ │
└─────────────┘ │ ┌────────────┐ │
│ │ Executor │ │
│ │ 10 langs │ │
│ │ sandboxed │ │
│ └────────────┘ │
│ │
│ ┌────────────┐ │
│ │ ContentStore│ │
│ │ SQLite FTS5│ │
│ │ BM25 search│ │
│ └────────────┘ │
└──────────────────┘
```
113 tests across 3 suites:
| Suite | Tests | Coverage |
|---|---|---|
| Executor | 55 | 10 languages, sandbox, truncation, concurrency, timeouts |
| ContentStore | 34 | FTS5 schema, BM25 ranking, chunking, stemming, fixtures |
| MCP Integration | 24 | JSON-RPC protocol, all 5 tools, fetch_and_index, errors |
## Development
+2
View File
@@ -28,6 +28,8 @@
"files": [
"build",
"skills",
".claude-plugin",
".mcp.json",
"README.md",
"LICENSE"
],