mcp-server-shield
mcp-server-shield is a Python-first hardening library for MCP server authors. It is not
a scanner, gateway, proxy, or hosted security service. It protects the MCP tool function
boundary directly: validate arguments before execution, use safe wrappers for dangerous
operations, filter outputs before they reach the MCP client, lint tool descriptions, lock
tool manifests, and emit structured audit logs.
The project is built for the way FastMCP and the official Python MCP SDK expose tools: ordinary Python functions decorated as tools.
Install
pip install mcp-server-shield
For local development:
pip install -e ".[dev]"
Quickstart
from mcp_server_shield import ShieldPolicy, shield
from mcp_server_shield.output_filters import PromptInjectionFilter, SecretRedactor
from mcp_server_shield.validators import PathGuard, StringGuard, URLGuard
policy = ShieldPolicy.strict(
paths={"file_path": PathGuard(root="./workspace", read=True, write=False)},
urls={"url": URLGuard(allowed_schemes=["https"], allowed_hosts=["api.github.com"])},
strings={
"query": StringGuard(
max_len=5000,
deny_substrings=["ignore previous instructions"],
)
},
output_filters=[SecretRedactor(), PromptInjectionFilter()],
)
@shield(policy)
def read_file(file_path: str) -> str:
with open(file_path, encoding="utf-8") as handle:
return handle.read()
FastMCP Example
Use @shield(policy) closest to the function so FastMCP sees the preserved signature and
metadata after the wrapper is applied:
from fastmcp import FastMCP
from mcp_server_shield import ShieldPolicy, shield
from mcp_server_shield.validators import PathGuard
mcp = FastMCP("secure-files")
policy = ShieldPolicy.strict(
paths={"file_path": PathGuard(root="./workspace", read=True, write=False)},
)
@mcp.tool()
@shield(policy)
def read_file(file_path: str) -> str:
with open(file_path, encoding="utf-8") as handle:
return handle.read()
Policy File Example
policy_id: secure-fetch-v1
fail_closed: true
audit_log: logs/mcp-shield-audit.jsonl
paths:
file_path:
root: ./workspace
read: true
write: false
allowed_extensions: [".txt", ".md"]
urls:
url:
allowed_schemes: ["https"]
allowed_hosts: ["api.github.com"]
allow_localhost: false
allow_private_ips: false
strings:
query:
max_len: 5000
deny_substrings: ["ignore previous instructions"]
output_filters:
- type: secret_redactor
redact_pii: true
- type: prompt_injection
action: redact
waivers:
- id: WAIVER-001
reason: Temporary partner endpoint migration.
expires_on: 2026-06-30
applies_to: ["URLGuard:url"]
evidence:
ticket: SEC-1234
Load it with:
policy = ShieldPolicy.from_file("mcp-shield-policy.yaml")
CLI
Lint tool descriptions:
mcp-shield lint-descriptions tools.json --json
Generate and verify a descriptor lockfile:
mcp-shield manifest generate tools.json --output mcp-shield.lock.json
mcp-shield manifest verify tools.json --lockfile mcp-shield.lock.json
Validate a policy file:
mcp-shield policy check mcp-shield-policy.yaml
Check the local installation:
mcp-shield doctor
Threat Model
mcp-server-shield assumes MCP tool arguments, external URLs, filesystem paths, command
arguments, tool descriptions, and tool outputs may be attacker influenced. It focuses on
deterministic local controls for:
- Secret exposure and context over-sharing through output redaction.
- Command and argument injection through
safe_run. - Path traversal and symlink escape through
PathGuard. - SSRF, localhost access, and DNS rebinding risk through
URLGuard. - Tool poisoning through description linting and manifest locking.
- Audit gaps through JSONL audit events for allowed, denied, redacted, and errored calls.
What This Library Does Not Solve
This library does not replace authentication, authorization, sandboxing, container policy, dependency scanning, supply-chain review, network egress policy, or a full MCP gateway. It does not claim to detect every prompt-injection phrase or every possible secret format. It does not make unsafe business logic safe by itself. It gives MCP server authors reusable secure-by-default primitives at the point where tool code handles untrusted data.
Release files for mcp-server-shield 0.1.0
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_server_shield-0.1.0.tar.gz | 31.5 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| mcp_server_shield-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 60.6 kB
Release files / mcp_server_shield-0.1.0.tar.gz
| Download URL | mcp_server_shield-0.1.0.tar.gz |
|---|---|
| Size | 31.5 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
8e7c738e572c36abf1b73360972bd96bda2becd117b17a9c42c690661427651e
|
|
BLAKE2b-256 checksum How to use checksums |
7102f783008b227f47afcea39216b95534423d8d5c14a4cc17d32a7b72557c30
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.12
|
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 Apr 25, 2026.
Transparency logRelease files / mcp_server_shield-0.1.0-py3-none-any.whl
| Download URL | mcp_server_shield-0.1.0-py3-none-any.whl |
|---|---|
| Size | 29.1 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
90f2705cf52282eb6dc4fb8a8ab204d4c0cbc079e3a3a5927dfc27a626e7a902
|
|
BLAKE2b-256 checksum How to use checksums |
b039a6fa86d7c1736caa3e2d096b085e90621acc04f5fc897568f9ac7d43c63f
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.12
|
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 Apr 25, 2026.
Transparency log