A Go MCP broker & the Python harness that grades it
Grades any MCP server against the spec, clause by clause, and says plainly what it cannot see.
On 28 July 2026 the Model Context Protocol became stateless: sessions, the
initialize handshake and server-initiated requests were removed, and
server/discover became mandatory. Sentinel is a harness that
scans any endpoint over the wire and grades it rule by rule, each with the clause it comes
from. It also lists the deprecated features the server still uses and when each can be removed.
The broker is a Go server built natively on the new revision, and it is
graded by that same harness.
Everything below is rendered from JSON that sentinel wrote, scanned
. Nothing is typed in by hand.
How it was generated.
The same 52-rule catalog, three servers, both directions
A gate that can only pass proves nothing. CI scans an unmigrated server that
must fail, and two correct ones that must pass. The exit code is part of the
contract: 0 means the target passed, 1 means the target failed the gate, and
2 means the scanner itself broke.
Loading scan output…
Report viewer
Each row is one finding from a real scan. Open a row to see what was observed, what to change, and the specification clause it is graded against.
No finding matches these filters.
Five MUSTs a scan cannot settle, and does not pretend to
Some requirements are invisible from the client side. Sentinel reports them as Indeterminate, never as passes. It excludes them from the gate and reprints them on every scan, so a green build can never be read as covering them. The same five appear, with the same wording, on all three scans above.
Deprecated-feature inventory, against the removal clock
sentinel deprecations probes for each deprecated feature and records how
it knows: observed on the wire, or advertised in
server/discover. This inventory never fails a gate. A deprecated feature
that still works is a migration to plan, not a defect.
Sizing the migration from the same evidence
sentinel migrate maps failing rules onto the revision's breaking changes.
Changes the wire cannot reveal are listed as not checkable from here rather than
marked done. The hours are the harness's planning estimates, not measurements.
A rule ID never changes meaning
A report from six months ago names rules by ID and nothing else, so redefining a rule
would silently rewrite what that report said. When a rule turns out to be wrong it is
deprecated, and a successor is published under a new ID.
Retired rules are skipped by default and never deleted. Re-running with
--include-deprecated-rules reproduces an old report.
All three corrections in 0.2.0 went the same way: sentinel had been demanding more than the specification does. Reasons are quoted from the README. Outcomes are from a replay scan of the unmigrated fixture.
Two products, one wire between them
The harness never imports server internals and runs against any endpoint URL. Its probe is
a deliberately literal client, with no MCP SDK. An SDK that helpfully adds
Mcp-Method would make the rule that requires Mcp-Method
untestable.
harness/ · Python
sentinel
- probehand-built JSON-RPC over HTTP, no SDK
- catalog52 live rules: MUST · SHOULD · SENTINEL/ beyond-spec, each with a citation or a rationale
- gradePASS · FAIL · INDETERMINATE · N/A, then the gate
- reporttext · JSON · SARIF for GitHub code scanning
any endpoint URL
broker Go · 2026-07-28 native
- Envoy routes and authorizes on
Mcp-Method/Mcp-Name, with no body-parsing filter - Stateless: cross-call state is a principal-bound handle, re-verified on every use
- MRTR with exactly-once effects: a duplicate retry replays the recorded result
- Exact-audience tokens; hash-chained, append-only audit log in Postgres
oracle fixtures Python
- non-conformant: tags each seeded violation in its own source
- conformant: a minimal correct server. Any FAIL against it is a false positive
Run it yourself
Requires Go 1.23+, Python 3.12, uv ≥ 0.5 and Docker. No model API key is needed anywhere. The broker serves tools and never calls a model.
The whole stack
make up # postgres + broker + envoy + smokescreen + otel-collector
make check # golangci-lint, go test -race, ruff, mypy, pytest
make scan-broker # grade the broker against its own harness
make scan-fixture # grade an unmigrated server; expected to exit 1
make demo # the nine-step demo
Scanning your own server
uv run sentinel scan --endpoint https://your-server.example/mcp --gate must \
--token "$TOKEN" --format sarif --out scan.sarif
uv run sentinel deprecations --endpoint https://your-server.example/mcp
Regenerating this page's data
bash site/data/regenerate.sh 2026-09-29
The script header lists the prerequisites: the broker, both fixtures, and a dev token from broker mint-token.
Commands quoted from the repository README.