MCP Audit
Security regression CI for MCP servers.
MCP Audit tells you when a pull request makes an MCP server more dangerous.
MCP Audit understands whether a change makes your MCP server safer, riskier, or simply different.
Blocking regression detected
Filesystem scope widened from allowlisted to unrestricted.
No security regression
A new read-only tool was added; MCP Audit warns but does not block.
Security improvement
Filesystem access was narrowed and previous findings were resolved.
Add it to a pull-request workflow:
permissions:
actions: read
contents: read
security-events: write
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- uses: actions/setup-python@v5
with:
python-version: "3.12"
- uses: robbyfa/MCP-Audit@v0.2.1
with:
path: .
baseline: origin/main
The Action writes a security-diff summary to the workflow run, uploads new source findings to GitHub Code Scanning, and fails only when the change introduces a blocking regression.
See the Action on three real pull requests:
- Filesystem access widens and CI fails
- Filesystem access narrows and CI passes
- A harmless read-only tool is added and CI passes
Install the CLI
pipx install mcp-capdiff
mcp-audit scan .
The product and CLI are named MCP Audit; the PyPI distribution is named mcp-capdiff.
Version 0.2 focuses on Python/FastMCP projects and one CI question: did this change make the MCP server more dangerous?
Develop locally
uv sync
Run project commands through uv run, or activate the virtual environment with
source .venv/bin/activate before using bare commands.
The package also supports isolated CLI installation directly from a checkout:
pipx install .
mcp-audit --version
mcp-audit scan .
Scan a server
uv run mcp-audit scan .
Scans fail closed when source cannot be read or when no MCP tools are discovered. Use --allow-empty only when an empty result is intentional.
Useful output formats:
uv run mcp-audit scan . --format json
uv run mcp-audit scan . --format sarif --output mcp-audit.sarif
Generate a capability manifest
uv run mcp-audit manifest .
Compare against a Git baseline
uv run mcp-audit diff --baseline origin/main .
uv run mcp-audit diff origin/main HEAD
The diff compares tools by registration context and name, classifies capability and finding changes as regressions, improvements, or neutral changes, and exits 1 only for blocking regressions. Operational and baseline errors exit 2.
Machine and CI outputs use the same structured change model:
uv run mcp-audit diff --baseline origin/main . --format json
uv run mcp-audit diff --baseline origin/main . --format markdown
uv run mcp-audit diff --baseline origin/main . \
--sarif-output mcp-audit.sarif \
--summary-output mcp-audit-summary.md
Run tests
uv run pytest
The corpus contains positive, negative, and edge cases under fixtures/, including host allowlisting, path-root validation, approval gating, and cross-tool sensitive-data paths.
GitHub Action options
The repository includes a composite action that runs the security diff, uploads SARIF to GitHub Code Scanning, and fails the check when policy thresholds are crossed:
permissions:
actions: read
contents: read
security-events: write
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- uses: actions/setup-python@v5
with:
python-version: "3.12"
- uses: robbyfa/MCP-Audit@v0.2.1
with:
path: .
baseline: origin/main
Add policy: mcp-audit.yaml when the repository needs custom blocking rules or reviewed suppressions.
JSON reports and manifests use the versioned schema documented in docs/report-schema.md.
The copyable vulnerable FastMCP demo includes four before/after pull-request scenarios and its own Action workflow.
Rules
MCP001arbitrary shell execution.MCP002unrestricted filesystem access.MCP003arbitrary URL or SSRF surface.MCP004high-impact side effect without approval.MCP005sensitive read to external write path.MCP007unbounded security-sensitive input.MCP010destructive tool exposed.
Capability widening and approval removal are first-class semantic diff changes in v0.2 rather than synthetic source findings. SARIF therefore remains focused on newly introduced MCP001-MCP010 findings, while the job summary reports capability and policy changes.
MCP005 is the capability-graph rule: it identifies when one tool returns classified data and another tool in the same MCP registration context can send it to an external destination. Findings include the source, data classification, sink, destination, path, source evidence, impact, and remediation.
Each rule's detection behavior, examples, remediation, and limitations are documented in docs/rules.
Demo fixtures
uv run mcp-audit scan fixtures/safe_server
uv run mcp-audit scan fixtures/vulnerable_server
The vulnerable fixture includes a sensitive file read tool, an unrestricted URL fetcher, shell execution, and a destructive operation. MCP Audit should flag the individual findings and the cross-tool path:
read_customer_file -> agent_context -> fetch_url
Policy
The default policy fails on high and critical findings. A minimal policy file can set a risk threshold and suppress reviewed findings:
policy:
ci:
fail_on:
- critical
- high
max_risk_score: 60
fail_on_changes:
- filesystem_widened
- network_widened
- shell_execution_added
- side_effect_widened
- approval_removed
- destructive_capability_added
warn_on_changes:
- tool_added
- input_became_unbounded
suppress:
- rule: MCP003
tool: internal_fetch
reason: "Network egress is enforced by service mesh"
expires: 2027-01-31
Suppression reasons are required. Expired suppressions no longer hide findings, and mcp-audit policy check reports them. See policy documentation.
Version contracts
CLI, ruleset, report schema, and manifest schema versions evolve independently. See versioning and report schema.
Passing MCP Audit is technical security evidence, not a legal compliance determination.
Metadata
Release files for mcp-capdiff 0.2.1
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| mcp_capdiff-0.2.1.tar.gz | 61.1 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| mcp_capdiff-0.2.1-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 98.4 kB
Release files / mcp_capdiff-0.2.1.tar.gz
| Download URL | mcp_capdiff-0.2.1.tar.gz |
|---|---|
| Size | 61.1 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
aea5b6aec000185e131cdd5fc5cb5b6c9ed9e403ec71e5a19a8edce62c42c349
|
|
BLAKE2b-256 checksum How to use checksums |
acc755c26dc77756681ca04ebe134274be7176435b1db9aea2f4640d3c17b79c
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 1, 2026.
Transparency logRelease files / mcp_capdiff-0.2.1-py3-none-any.whl
| Download URL | mcp_capdiff-0.2.1-py3-none-any.whl |
|---|---|
| Size | 37.4 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
3868b78aa991d8e5103586c946b15349c1fd90e6c1e7ac2b0039e68223c9c641
|
|
BLAKE2b-256 checksum How to use checksums |
62dc9c0689b51171295b1a918ed8157dc6e436d0519fcbf564ceb6c2dc8a4844
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/7.0.0 CPython/3.13.14
|
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
PyPI Publish Attestation
PyPI verified that this artifact, at this checksum, originated from the publisher listed below.
Signed by GitHub Actions, verified by PyPI on Oct 1, 2026.
Transparency log