mcp-eval-gate
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 12 files during light audit, no dangerous patterns found
Permissions Pass
- Permissions — No dangerous permissions requested
No AI report is available for this listing yet.
CI regression gate for MCP servers: run a golden set of tool calls, diff against a baseline, fail the build when outputs get worse
mcp-eval-gate
A CI regression gate for MCP servers. It calls your server's tools, compares the results to a saved baseline, and fails the build when the output gets worse, even if the schema did not change.
Read the write-up: MCP server testing in CI: the bug no schema check can see.
Why
An MCP server's tool names and input schemas can stay identical while what a tool returns
quietly gets worse: a refactor breaks a code path, a dependency bump changes behavior.
Nothing crashes, the agent using it just gets worse answers.
Other tools cover parts of this. The official Inspector's CLI runs scripted single-run
assertions. mcp-server-diff compares declared schemas and says it does not test output
correctness. A few other early tools record golden outputs and diff them too, for example
vexyo and
cisco-open/mcptoolkit-test.mcp-eval-gate is another take on golden-output regression.
How it works
- You describe how to reach your server and list the tool calls that matter, with the output
you expect from each, in agolden_set.yaml. run --update-baselinecalls every tool and records the results as the baseline, once,
while everything is known to be good.runcalls the same tools again and compares against the baseline. It prints a table and a
diff, and exits1if anything failed or got worse, so any CI job can gate on it.
Install
Requires Python 3.12+.
pip install mcp-eval-gate
# only if you use match_type: judge
pip install "mcp-eval-gate[judge]"
# or run it without installing
uvx mcp-eval-gate --help
Quickstart
mcp-eval-gate init # scaffolds golden_set.yaml, which runs as is against the
# official MCP reference server (needs Node.js)
mcp-eval-gate run --update-baseline # first run: record the baseline
mcp-eval-gate run # later runs: gate on regressions
Then point server at your own server and replace the cases. --update-baseline refuses to
record while any case fails, since a baseline should hold known-good output.
Golden set
server:
command: node
args: ["dist/index.js"]
# or, for an HTTP server instead of stdio:
# url: http://localhost:3000/mcp
cases:
# substring match
- id: get-weather-nyc
tool_name: get_weather
tool_args:
city: "New York"
match_type: contains
expected_output: "New York"
# exact match
- id: cancel-subscription
tool_name: cancel_subscription
tool_args:
immediate: true
match_type: exact
expected_output: "cancelled"
# scored by an LLM against a rubric (needs ANTHROPIC_API_KEY)
- id: retention-policy-answer
tool_name: search_docs
tool_args:
query: "data retention policy"
match_type: judge
judge_criteria: "Answer must state data is retained for 90 days"
min_judge_score: 0.8
examples/golden_set.yaml is a copy you can edit.
Case fields
| Field | Required | Default | Meaning |
|---|---|---|---|
id |
yes | Unique name for the case | |
tool_name |
yes | The MCP tool to call | |
tool_args |
no | {} |
Arguments passed to the tool |
match_type |
no | contains |
exact, contains, or judge |
expected_output |
for exact and contains |
The text to compare against | |
judge_criteria |
for judge |
The rubric the LLM scores against | |
min_judge_score |
no | 0.8 |
Lowest judge score that passes |
timeout_seconds |
no | 30 |
A case that takes longer fails on its own, so one hung tool does not stall the run |
A tool call that returns an error always fails its case.
Exit codes
| Code | Meaning |
|---|---|
0 |
Every case passed and nothing regressed against the baseline |
1 |
A case failed or regressed, or --update-baseline was refused because a case failed |
2 |
The golden set is invalid, or the server could not be started or reached |
Run as an MCP tool
The package also installs mcp-eval-gate-mcp, an MCP server over stdio with one tool,run_eval_gate(config_path, baseline_path, update_baseline). Add it to an MCP client's config:
{
"mcpServers": {
"mcp-eval-gate": { "command": "mcp-eval-gate-mcp" }
}
}
Without installing, use uvx:
{
"mcpServers": {
"mcp-eval-gate": { "command": "uvx", "args": ["--from", "mcp-eval-gate", "mcp-eval-gate-mcp"] }
}
}
Validation
validation/ has two runs against real servers, each with the actual command
output committed and steps to reproduce it. No paid API calls.
- A one-line regression planted in the official MCP reference server, caught with exit
code1and a real diff. - A real bug the official filesystem server shipped (garbled
text when a multi-byte character straddled a read boundary), caught by running the commit
before its upstream fix against a baseline from the fixed commit. The
write-up
walks through it.
Both are small. They show the gate works end to end on real code, not how often this class
of bug occurs.
Limitations
- Matching is exact, substring, or an LLM judge. There is no normalization for volatile
output such as timestamps or ids, so output that varies between runs can't be compared
reliably. - It checks tool outputs only, not schemas or protocol conformance.
match_type: judgehas only been tested against a stub client, not the live Anthropic API.
Feedback
If you maintain an MCP server, I'd like to know what you would want to test and what got in
the way. Open an issue with the
feedback form.
Development
uv sync --extra judge --dev
uv run pytest --cov=src --cov-report=term-missing
uv run ruff check src tests
License
MIT
Reviews (0)
Sign in to leave a review.
Leave a reviewNo results found