mcp-injector
Health Warn
- License — License: MIT
- Description — Repository has a description
- Active repo — Last push 0 days ago
- Low visibility — Only 5 GitHub stars
Code Pass
- Code scan — Scanned 5 files during light audit, no dangerous patterns found
Permissions Pass
- Permissions — No dangerous permissions requested
No AI report is available for this listing yet.
HTTP shim for injecting MCP tools into OpenAI-compatible chat completions
mcp-injector
Resilient LLM gateway shim with virtual models, provider fallbacks, and secure MCP tool injection
mcp-injector sits between an agent (like OpenClaw) and LLM gateways. It provides automatic failover, error translation, and a secure governance framework for MCP tool execution.
Key Features
- ✅ Progressive MCP Tool Discovery — Discover and inject only the tools your agent needs. Fight MCP bloat by loading schemas on-demand instead of dumping hundreds of tools into every prompt.
- ✅ PII Scanning & Smart Restoration — Automatic redaction of sensitive data in prompts. Trusted tools receive original values via a per-request vault with deterministic hashing.
- ✅ Virtual model chains — Define fallback providers with cooldowns. Automatic failover when providers rate-limit or go down.
- ✅ Transparent Loop Preservation — Accumulates all internal turns (reasoning, tool calls, results) and synchronizes them with clients via signed footers.
- ✅ Session Re-hydration — Automatically restores conversation context from durable storage when a
session-idis provided. - ✅ Provider-Level Observability — Granular tracking of tokens, requests, and rate-limits per provider. Usage stats via
/api/v1/stats. - ✅ Multi-transport MCP — Support for HTTP and STDIO (local process) MCP servers.
- ✅ Error translation — Converts cryptic provider errors into actionable messages.
PII Scanning & Restoration
The PII scanner uses a multi-layered approach to minimize false positives while catching real secrets:
- Whitelisting: Local file paths (Windows/POSIX), URLs, IP addresses, and UUIDs are automatically ignored.
- Character Diversity: Tokens must contain at least 4 character classes (lower, upper, digit, special) OR 3 classes with at least 20 characters. This prevents descriptive strings like
mcp__stripe__retrieve_customerfrom being flagged. - Proximity Check: By default, general high-entropy strings are only redacted if they follow assignment-like keywords (e.g.,
api_key:,token =). Explicit regex patterns (AWS, Anthropic, etc.) bypass this check for maximum safety.
PII Restoration (Smart Vault)
For tools that need access to original PII data (e.g., a Stripe integration that must see real email addresses), configure trust levels:
:servers
{:stripe
{:url "http://localhost:3001/mcp"
:trust :restore ; :none (default), :read, or :restore
:tools [{:name "retrieve_customer" :trust :restore}]}}
:none(default): Tool receives redacted tokens like[EMAIL_ADDRESS_a35e2662]:restore: Tool receives original values (e.g.,[email protected])
The vault uses deterministic SHA-256 hashing with a per-request salt, ensuring tokens are consistent within a request but not leakable across requests.
Observability & Tracing
Action Receipts — When tools run during a request, mcp-injector prepends a clean markdown receipt to the response content:
Action Receipt: trace_id=abc123 | 2 tools (165ms total)
- stripe.get_customer: 45ms
- postgres.query: ERROR: timeout
---
Receipts are:
- Prepended (not appended) — better for Telegram/Slack UX
- PII-masked — sensitive values replaced with tokens
- Controllable via config/env var
Response Headers — Every response includes W3C trace headers for distributed tracing:
X-Injector-Traceparent: 00-<trace-id>-<parent-id>-00
Configure observability:
{:receipt-mode :on} ;; :on, :off, or :errors-only
{:receipt-style :emoji} ;; :emoji (future) or :ascii
{:footer-mode :off} ;; :off (default) or :legacy
Or via environment variables:
MCP_INJECTOR_RECEIPT_MODE=on|off|errors-only
MCP_INJECTOR_RECEIPT_STYLE=emoji|ascii
MCP_INJECTOR_FOOTER_MODE=off|legacy
Per-request override: extra_body: {:receipt false} suppresses the receipt for that request.
Quick Start
Prerequisites
Installation
nix develop
bb test
bb run
Configuration
Copy the example config and customize:
cp mcp-servers.example.edn mcp-servers.edn
Environment Variables
| Variable | Description | Default |
|---|---|---|
INJECTOR_AUDIT_SECRET |
32-byte secret for signing audit log entries. | (auto-generated) |
MCP_INJECTOR_AUDIT_LOG_PATH |
Path for NDJSON audit log. | logs/audit.log.ndjson |
MCP_INJECTOR_PORT |
Server port. | 8080 |
MCP_INJECTOR_LLM_URL |
LLM gateway endpoint. | http://localhost:11434 |
MCP_INJECTOR_MAX_ITERATIONS |
Agent loop iteration limit. | 10 |
MCP_INJECTOR_LOG_LEVEL |
Log verbosity. | debug |
MCP_INJECTOR_TIMEOUT_MS |
LLM request timeout. | 1800000 |
MCP_INJECTOR_RECEIPT_MODE |
When to show action receipts: on, off, or errors-only. |
on |
MCP_INJECTOR_RECEIPT_STYLE |
Receipt style: emoji or ascii. |
emoji |
MCP_INJECTOR_FOOTER_MODE |
Legacy HTML footer: off or legacy. |
off |
Edit mcp-servers.edn:
{:servers
{:stripe
{:url "http://localhost:3001/mcp"
:tools ["retrieve_customer" "list_charges"]}}
:llm-gateway
{:url "http://localhost:8080"
:virtual-models
{:brain
{:chain ["provider1/model1" "provider2/model2"]
:cooldown-minutes 5}}}}
Virtual Models & Retry Behavior
Provider Chains
Virtual models define a chain of providers with automatic failover:
:virtual-models
{:brain
{:chain ["zen/kimi-k2.5-free" "nvidia/moonshotai/kimi-k2.5" "openrouter/claude-sonnet-4"]
:cooldown-minutes 5
:retry-on [429 500]
:on-context-overflow :fail-fast}}
Retry-on Codes
When a provider fails, mcp-injector checks :retry-on to decide whether to try the next provider:
| Code | Meaning | Retry? | Notes |
|---|---|---|---|
| 429 | Rate limit | ✅ Yes | Provider is throttling, try elsewhere |
| 500 | Server error | ✅ Yes | Provider is broken, try elsewhere |
| 503 | Service unavailable | ⚠️ Depends | Context overflow = don't retry (same window). Other 503 = retry |
| 400-404 | Client errors | ⚠️ Depends | Context overflow = don't retry. Auth errors (401-403) = retry with different provider |
Context Overflow Handling
The :on-context-overflow key controls behavior when the prompt exceeds the model's context window:
:fail-fast(default) — Return 503 immediately. Don't retry other providers (they likely have the same window). Let upstream handle compaction.:retry— Advance through the chain. Useful for tiered chains with progressively larger context windows.:alert— Retry but addX-Injector-Context-Overflow-Fallbackheader when falling back to a paid provider.
Cooldowns
When a provider fails with a retriable error, it's placed on cooldown for :cooldown-minutes (default: 5). Cooldowns prevent wasting quota on temporarily unavailable providers.
Governance & Security
mcp-injector includes a robust governance layer configured via the :governance key in mcp-servers.edn (copy from mcp-servers.example.edn).
Governance Modes
:permissive(Default): All tools are allowed unless explicitly denied.:strict: All tools are denied unless explicitly allowed in the policy.
Privileged Tools
Certain high-risk tools (like clojure-eval) are marked as Privileged. These tools are always blocked by default, even in permissive mode, unless explicitly listed in an :allow rule.
Example Policy
:governance
{:mode :permissive
:policy
{:mode :permissive ; Fallback mode for this policy (overrides global)
:allow ["mcp__stripe__*"]
:deny ["mcp__danger-server__*"]
:rules [{:model "gpt-4o-mini" :deny ["clojure-eval"]}]
:sampling {:trusted-servers ["stripe" "postgres"]}}
:audit
{:enabled true :path "logs/audit.log.ndjson"}
:pii
{:enabled true :mode :replace :proximity-check-enabled true}}
⚠️ Security Notice: clojure-eval Escape Hatch
The clojure-eval tool is a privileged escape hatch that allows the LLM to execute arbitrary Clojure code on the host JVM. This is Remote Code Execution (RCE) by design.
- Default State: Disabled. You must explicitly allow
clojure-evalin your policy's:allowlist. - Risk: If enabled, a compromised, hallucinating, or prompt-injected LLM gains full system access—including files, environment variables, network, and process control.
- Mitigation: Only enable
clojure-evalfor highly trusted models in isolated environments. Treat it as root-level access. - Startup Warning: When enabled, mcp-injector logs a
CRITICALaudit event at startup.
Signed Audit Trail
Tamper-proof NDJSON logs with ULID and HMAC chaining. Verify integrity with GET /api/v1/audit/verify.
Control API
GET /api/v1/status: Health and version.GET /api/v1/mcp/tools: List discovered tools.GET /api/v1/stats: Usage statistics broken down by model and provider.GET /api/v1/llm/state: Cooldown and usage state.POST /api/v1/session/reset: Reset session history (fixes corrupted state).POST /api/v1/llm/cooldowns/reset: Clear all provider cooldowns.POST /api/v1/mcp/reset: Clear caches and restart processes.GET /api/v1/audit/verify: Cryptographically verify the audit log integrity.
NixOS Deployment
services.mcp-injector = {
enable = true;
mcpServers = { ... };
governance = {
mode = "permissive";
policy = {
allow = [ "mcp__stripe__*" ];
};
};
};
Status: Production-ready | Tests: 150 passing | Built with: Babashka + http-kit + Cheshire
Reviews (0)
Sign in to leave a review.
Leave a reviewNo results found