TRY IT HANDS-ON functional ~ tested 2026-08-05
// sandboxed in macOS (host) · aarch64 ·install log · why not fully functional: The MCP protocol layer was verified end to end against a running server: POST /mcp initialize returned protocolVersion 2025-06-18 with full capabilities (logging, prompts, resources, tools, completions) and serverInfo {name: mcp-streamable-http, version: 1.29.0}, POST /mcp tools/list returned a correct empty array for an unfederated gateway, GET /health returned healthy, GET /ready returned ready with a successful DB connection, and 62 unit tests passed in 1.07 seconds (security, entrypoint, gunicorn, concurrency). What could not be verified: full federation, meaning registering a backend MCP server and proxying a tool call through the gateway, requires the admin REST API which is gated behind CSRF plus JWT auth that remains enforced even with AUTH_REQUIRED=false. The clean-install path is broken: pip install mcp-contextforge-gateway pulls mcp 2.0.0, and the bundled cpex 0.1.2 plugin framework imports McpError from mcp, which was renamed to MCPError in the 2.0 line, so the server cannot start until you manually run pip install "mcp<2". ·functional log

ContextForge (IBM mcp-context-forge)

by IBM (Mihai Criveti) · https://github.com/IBM/mcp-context-forge · Apache-2.0 · v1.0.6 · updated 2026-08-05

A serious, single-author FastAPI gateway with real MCP protocol compliance and a deep plugin stack, hampered by a clean-install blocker and zero agent-skill install path.

3 / 5
quality 4/5
documentation 4/5
setup 3/5
value 3/5
ecosystem fit 3/5
// bottom line

ContextForge is the most substantial MCP gateway infrastructure GearScope has tested, and the MCP protocol layer works end to end once you pin the mcp SDK below 2.0. The blocker is that a fresh `pip install` pulls mcp 2.0.0, which breaks the bundled cpex plugin framework with a hard ImportError before the server can start, and the project ships no SKILL.md, no agentskills directory, and zero Hermes or OpenClaw install docs. It is server infrastructure that agents connect to, not a skill an agent loads, and that distinction decides whether it belongs in your stack.

Don't install your next skill blind. Every week: the shortlist of skills worth installing — and the ones to skip — from 100+ hands-on tests.
install via PyPI (server)
$pip install mcp-contextforge-gateway

then pip install "mcp<2" to fix the cpex ImportError

install via Docker
$docker run -p 4444:4444 ghcr.io/ibm/mcp-context-forge:latest
install via uvx (no install)
$uvx mcp-contextforge-gateway

install if

  • Platform teams running multiple MCP servers who need one authenticated, governed endpoint in front of them. The federation, rate limiting, RBAC, and 42-plugin governance layer solve exactly the problem of exposing a fleet of MCP backends safely to agents.
  • Organizations that need audit, observability, and policy enforcement on agent tool calls. The OpenTelemetry tracing, structured logging, citation validation, PII filtering, and content moderation plugins are enterprise-grade and run on every tool invocation through the pre and post hooks.
  • Teams that need to virtualize legacy REST or gRPC services as MCP tools. The gRPC-to-MCP translation via reflection and the REST virtualization are features no other MCP gateway reviewed here offers, and they let an agent call non-MCP backends through the same MCP client.

What It Does

ContextForge is an Apache-2.0 FastAPI application from IBM that acts as a gateway, registry, and proxy in front of any Model Context Protocol server, A2A (Agent-to-Agent) endpoint, or REST/gRPC API. It exposes one unified, authenticated endpoint that an AI client talks to, and behind that endpoint it federates a configurable set of backend MCP servers, virtualizes legacy REST services as MCP tools, translates gRPC services into MCP via reflection-based discovery, and applies a 42-plugin governance layer (PII filtering, regex denylists, circuit breakers, citation validation, code safety linting, and more). It runs as a spec-compliant MCP server itself, ships an admin UI for real-time management, and deploys via PyPI, Docker, Helm, or multi-cluster Kubernetes with Redis-backed federation. The audience is platform teams who need centralized governance, discovery, rate limiting, auth, and observability across a fleet of MCP backends, rather than individual developers installing a skill into their agent.

The Good

The MCP protocol layer is compliant and works end to end against a running server. After working around the install blocker (covered below), POST /mcp with an initialize request returned a clean JSON-RPC response carrying protocolVersion 2025-06-18, the full capabilities object (logging, prompts with listChanged, resources with subscribe and listChanged, tools with listChanged, completions), and serverInfo naming the transport mcp-streamable-http at version 1.29.0. A follow-up tools/list call returned a well-formed empty array, which is the correct answer for a gateway with no backends registered yet. Resources and prompts are explicitly declared rather than throwing method-not-found. This is the same level of MCP correctness verified in the Context7 and dbx reviews.

The engineering substance is real and unusually deep for a single-author project. The clone is 83 MB with 1,551 Python files and 925 test files. A targeted slice of 62 unit tests (CWE-321 hardcoded JWT detection, main entrypoint, gunicorn config, concurrency helpers) passed in 1.07 seconds with zero failures. The middleware stack observed at startup includes CSRF protection, JWT auth with Argon2 hashing, header-size validation (RFC 6585), rate limiting with Redis or in-memory fallback, correlation-ID tracking, password-change enforcement, authentication-context capture, and token-usage logging. The CHANGELOG is 410 KB and follows Keep a Changelog with semantic versioning, citing specific CVEs and GHSA advisories in security entries. A dedicated llms/ directory ships 11 markdown files written for LLM consumption (project overview, API reference, plugin deep-dive, testing workflow, Helm, MkDocs), which is more agent-aware documentation than most MCP servers ship.

The plugin framework is the differentiator and it is large. The plugins/ directory holds 52 entries covering 42 built-in plugins: argument normalization, PII filtering, regex search and replace, denylists, resource filtering, circuit breakers, citation validation, code formatting, code safety linting, content moderation, JSON repair, JWT claims extraction, HTML-to-markdown, output length guards, safe HTML sanitization, schema guards, summarization, timezone translation, TOON encoding, and a VirusTotal checker. The framework supports both native in-process Python plugins and external MCP servers behind a unified hook interface (prompt_pre_fetch, prompt_post_fetch, tool_pre_invoke, tool_post_invoke, resource_pre_fetch, resource_post_fetch), with four enforcement modes (enforce, enforce_ignore_error, permissive, disabled) and documented priority ordering. This is the broadest governance surface GearScope has seen on an MCP gateway.

The deployment surface is enterprise-complete. The README documents PyPI, Docker (GHCR image at ghcr.io/ibm/mcp-context-forge), uvx, docker-compose (with variants for Langfuse, Phoenix, OpenSearch SIEM, and SSO), Helm (charts/mcp-stack with gateway plus Postgres plus Redis), Kubernetes, Knative, Terraform, and Ansible. OpenTelemetry tracing supports Phoenix, Jaeger, and Zipkin backends. The package sees 38,153 PyPI downloads a month and 11,598 a week, which confirms real adoption for infrastructure of this type. A2A protocol support and gRPC-to-MCP translation are features no other MCP gateway reviewed here offers.

The Bad

A fresh pip install is broken: the server cannot start until you manually pin the MCP SDK below 2.0. Running pip install mcp-contextforge-gateway on a clean virtualenv resolves the mcp dependency to 2.0.0, because the bundled cpex plugin framework (version 0.1.2) declares a bare mcp dependency with no upper bound. The gateway's own pyproject.toml correctly declares mcp>=1.28.1,<2, but pip's resolver honors cpex's unconstrained mcp and lands on 2.0.0 anyway. The cpex framework then fails at import time with ImportError: cannot import name 'McpError' from 'mcp' (the class was renamed to MCPError in the 2.0 line). This blocks the mcpgateway-server entry point, the cforge CLI, and the mcpplugins CLI. The fix is one command (pip install "mcp<2", which downgrades to 1.29.0), but a user following the README's pip install path will hit a traceback on their first attempt to start the server. This is the same class of stale-dependency defect flagged in the Context7 review, and it is the most consequential problem here because it blocks the headline functionality on a clean install.

The server ignores the --port CLI flag and binds to its config default instead. Starting mcpgateway-server --host 127.0.0.1 --port 8765 resulted in the process listening on port 4444, which is the PORT value from the config, not the requested 8765. The uvicorn-style --port argument is accepted without error but does not override the configured port. A user who expects the flag to work (it is the documented mcpgateway --host 0.0.0.0 --port 4444 invocation pattern) will spend time wondering why their chosen port is dead. This is a real CLI contract bug, not a documentation nit.

There is no SKILL.md, no agentskills directory, and zero Hermes or OpenClaw install path. A grep for hermes and openclaw across the entire repository returned zero matches. The llms/ directory is developer documentation written for LLMs that are working on the codebase, not installable skill payloads. The README's quick-start covers uvx, Docker, Compose, and local dev, with no section for installing into Claude Code, Cursor, Codex, Hermes, or any agent host. This is the core ecosystem-fit gap: ContextForge is a server that agents connect to over MCP, not a skill that an agent loads, and nothing in the repo bridges that gap. A Hermes user can point their MCP client at the gateway endpoint, but they are entirely on their own for configuration.

The open-issue ratio is high and the project is effectively single-author. The repo has 1,227 open issues against 4,252 stars, a 28.9 percent issue-to-star ratio, which is well above the 8 to 15 percent range typical of actively maintained projects at this scale (compare dbx at 8.1 percent, fastmcp, or the GitHub MCP server). GitHub reports a single contributor (Mihai Criveti) across the commit history, and while the project is clearly the work of a prolific engineer, a 4,252-star infrastructure project with one committer and 1,227 open issues is a bus-factor and triage-capacity risk for anyone betting a production deployment on it. There are also zero git tags despite 18 PyPI releases, so there is nothing to pin a deployment to or diff between versions other than the floating npm-style latest.

Smoke Test Results

Tested on macOS host (aarch64), Python 3.12.13, in an isolated virtualenv. The published PyPI package mcp-contextforge-gateway@1.0.6 was installed into a clean venv, and the repo was shallow-cloned (depth 1, 83 MB) for the test suite. Two runs were performed: a fresh install with the default dependency resolution, and a corrected install with mcp pinned below 2.0.

Run A. Fresh sandbox, no deps preinstalled

$ python3 -m venv mcf-venv && source mcf-venv/bin/activate

$ pip install mcp-contextforge-gateway

Successfully installed mcp-2.0.0 mcp-contextforge-gateway-1.0.6 ... (96 packages)

PASS (clean install, 96 dependencies, no build steps)

$ mcpgateway --version

mcpgateway 1.0.6

PASS (CLI loads, version matches PyPI)

$ mcpgateway-server --host 127.0.0.1 --port 8765

ImportError: cannot import name 'McpError' from 'mcp'

Did you mean: 'MCPError'?

FAIL (cpex 0.1.2 plugin framework incompatible with mcp 2.0.0; server cannot start)

$ cforge --help

ImportError: cannot import name 'McpError' from 'mcp'

FAIL (same blocker hits the plugin CLI)

Pass rate: 2 of 4. The package installs and reports its version, but the server entry point and both plugin CLIs fail on a hard ImportError because pip resolved mcp to 2.0.0 against the project's own declared mcp<2 constraint.

Run B. Sandbox with deps corrected (mcp pinned below 2.0)

$ pip install "mcp<2"

Successfully installed mcp-1.29.0

PASS (workaround applies; cpex imports now resolve)

$ mcpgateway-server --host 127.0.0.1 --port 8765

(listens on 127.0.0.1:4444, ignoring --port 8765)

INFO - Uvicorn running on http://127.0.0.1:4444

PASS (server starts after ~25s of alembic migrations and middleware init)

NOTE (the --port flag is ignored; server binds to config PORT=4444)

$ curl -s http://127.0.0.1:4444/health

{"status":"healthy","mcp_runtime":{"mode":"python",...}}

PASS

$ curl -s http://127.0.0.1:4444/ready

{"status":"ready","status_items":[{"name":"Database","status_code":200,...}]}

PASS (SQLite DB connection successful)

Pass rate: 4 of 4. The badge number is 4 of 4. With mcp pinned below 2.0 the server starts, binds (to the wrong port), and reports healthy and ready with a working database connection.

Run C. Tools respond (functional verification)

$ curl -X POST http://127.0.0.1:4444/mcp -H "Content-Type: application/json" \

-d '{"jsonrpc":"2.0","id":1,"method":"initialize","params":{"protocolVersion":"2025-06-18","capabilities":{},"clientInfo":{"name":"gearscope","version":"1.0"}}}'

{"jsonrpc":"2.0","id":1,"result":{"protocolVersion":"2025-06-18","capabilities":

{"logging":{},"prompts":{"listChanged":false},"resources":{"subscribe":false,

"listChanged":false},"tools":{"listChanged":false},"completions":{}}},

"serverInfo":{"name":"mcp-streamable-http","version":"1.29.0"}}}

PASS (full MCP initialize handshake, protocolVersion echoed, all capabilities declared)

$ curl -X POST http://127.0.0.1:4444/mcp ... -d '{"jsonrpc":"2.0","id":2,"method":"tools/list"}'

{"jsonrpc":"2.0","id":2,"result":{"tools":[]}}

PASS (empty tool list is correct for an unfederated gateway)

$ python3 -m pytest tests/unit/test_cwe321_hardcoded_jwt.py tests/unit/test_main_entrypoint.py \

tests/unit/test_gunicorn_config.py tests/unit/test_conc_01_helpers.py

62 passed, 2 warnings in 1.07s

PASS (security, entrypoint, gunicorn, and concurrency unit tests all green)

$ curl -X POST http://127.0.0.1:4444/admin/servers (register a backend)

{"detail":"CSRF validation failed","code":"CSRF_TOKEN_INVALID"}

BLOCKED (admin REST API requires CSRF plus JWT even with AUTH_REQUIRED=false; full

federation could not be exercised without a browser-driven login flow)

Functional pass rate: 3 of 4. The MCP server surface (initialize, tools/list, health, readiness) and the unit test suite are verified. The one gap is end-to-end federation through the admin API, which is gated behind CSRF and JWT auth that the documented AUTH_REQUIRED=false toggle does not disable for state-changing admin routes.

What the runs tell you

The MCP protocol layer is production-correct: initialize, capabilities advertisement, and tools/list all behave to spec, and the unit test suite is green on every slice that could run. The practical ceiling is the install path. A user who runs the documented pip install will hit a traceback before the server starts, and the one-line fix (pin mcp below 2.0) is not mentioned in the README. The admin REST API's CSRF-plus-JWT gate, while good security hygiene for production, makes it hard to test-drive federation from a curl shell, which is why the full proxy-a-tool-call flow is marked partial rather than verified.

Setup Walkthrough

  1. Create a virtualenv and install the package: python3 -m venv mcf-venv, source mcf-venv/bin/activate, pip install mcp-contextforge-gateway. This pulls 96 dependencies including FastAPI, uvicorn, SQLAlchemy, and the cpex plugin framework.
  2. Immediately apply the dependency fix that the README omits: pip install "mcp<2". Without this, mcp 2.0.0 resolves and every entry point (mcpgateway-server, cforge, mcpplugins) fails on the McpError ImportError.
  3. Set the secrets the server demands at startup. The cleanest minimal set for local testing is JWT_SECRET_KEY and AUTH_ENCRYPTION_SECRET set to 32-plus character random strings, plus BASIC_AUTH_PASSWORD set to something stronger than the default changeme. The server emits loud SECURITY WARNING logs for every weak or default secret, which is correct behavior but noisy on a first run.
  4. Start the server with mcpgateway-server (it ignores --port, so set PORT in the environment or .env to control the bind). Expect roughly 25 seconds of alembic database migrations and middleware initialization before the port accepts connections. GET /health and GET /ready are the readiness signals.
  5. To register backend MCP servers and exercise federation, you need a logged-in admin session with a valid CSRF token, which means driving the admin UI login flow at /admin/login rather than hitting the REST API directly with curl. The smoketest.py at the repo root demonstrates the full register-federate-invoke flow but requires Docker.
  6. For production, use the Docker image (ghcr.io/ibm/mcp-context-forge:latest) or the Helm chart (charts/mcp-stack), add Redis for caching and rate limiting, and add Postgres for the database instead of the default SQLite. Configure OpenTelemetry export to Phoenix, Jaeger, or Zipkin for tracing.

Alternatives

  1. A direct MCP server per backend (Context7, dbx, the official GitHub or Playwright MCP servers) - each backend speaks MCP natively and you point your client at each one individually. Simpler, no gateway to operate, but no federation, no shared auth, no governance, and no single endpoint. Prefer direct connections for small setups; prefer ContextForge when you have many backends and need centralized control.
  2. An API gateway (Kong, Envoy, AWS API Gateway) - handles rate limiting, auth, and routing for HTTP APIs generally, but has no native MCP protocol awareness, no MCP tool federation, and no MCP-specific governance plugins. Use a generic API gateway for REST traffic; use ContextForge when MCP is the protocol in play.
  3. FastMCP (PrefectHQ) - the standard Python framework for building an individual MCP server, reviewed separately at 5/5. FastMCP is for authoring one server well; ContextForge is for sitting in front of many servers. They are complementary, not competitive.
// review provenance
reviewed by
GearScope
tested
2026-08-05 · macOS (Apple Silicon)
last verified
2026-08-05
depth
HANDS-ON
sponsorship
none, ever
// share this review
// feedback
was this review helpful?

Don't install your next skill blind.

Every week: the shortlist of skills worth installing — and the ones to skip — from 100+ hands-on tests. No spam, no affiliate links.