mcp-bastion-python 2.0.0__tar.gz → 2.0.1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (73) hide show
  1. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/PKG-INFO +118 -76
  2. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/README.md +117 -75
  3. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/dashboard/README.md +4 -4
  4. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/pyproject.toml +1 -1
  5. mcp_bastion_python-2.0.1/src/mcp_bastion/benchmarks/injection_efficacy.py +120 -0
  6. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/cli.py +107 -3
  7. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/config.py +45 -1
  8. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/errors.py +14 -0
  9. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/middleware.py +118 -2
  10. mcp_bastion_python-2.0.1/src/mcp_bastion/pillars/content_normalize.py +54 -0
  11. mcp_bastion_python-2.0.1/src/mcp_bastion/pillars/cost_policy.py +161 -0
  12. mcp_bastion_python-2.0.1/src/mcp_bastion/pillars/governance_attestation.py +99 -0
  13. mcp_bastion_python-2.0.1/src/mcp_bastion/pillars/identity_adapters.py +121 -0
  14. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/injection_heuristics.py +8 -2
  15. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/prompt_guard.py +4 -1
  16. mcp_bastion_python-2.0.1/src/mcp_bastion/pillars/secrets_resolver.py +120 -0
  17. mcp_bastion_python-2.0.1/src/mcp_bastion/pillars/session_governance.py +97 -0
  18. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/telemetry_sinks.py +27 -0
  19. mcp_bastion_python-2.0.1/src/mcp_bastion/proxy_server.py +228 -0
  20. mcp_bastion_python-2.0.0/src/mcp_bastion/pillars/content_normalize.py +0 -31
  21. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/.gitignore +0 -0
  22. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/LICENSE +0 -0
  23. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/NOTICE +0 -0
  24. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/dashboard/app.py +0 -0
  25. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/dashboard/static/chart.umd.min.js +0 -0
  26. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/dashboard/static/dashboard-app.js +0 -0
  27. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/dashboard/static/mcp-bastian.png +0 -0
  28. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/dashboard/static/mcp-bastian.svg +0 -0
  29. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/__init__.py +0 -0
  30. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/audit_jsonl.py +0 -0
  31. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/base.py +0 -0
  32. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/benchmarks/__init__.py +0 -0
  33. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/benchmarks/finops_rbac.py +0 -0
  34. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/demo_dashboard_metrics.py +0 -0
  35. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/demo_live_traffic.py +0 -0
  36. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/doctor.py +0 -0
  37. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/governance_beacon.py +0 -0
  38. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/otel.py +0 -0
  39. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/__init__.py +0 -0
  40. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/agent_iam.py +0 -0
  41. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/alerts.py +0 -0
  42. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/argument_guards.py +0 -0
  43. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/audit_hash_chain.py +0 -0
  44. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/audit_log.py +0 -0
  45. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/budget_principal.py +0 -0
  46. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/circuit_breaker.py +0 -0
  47. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/content_filter.py +0 -0
  48. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/cost_tracker.py +0 -0
  49. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/external_policy.py +0 -0
  50. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/grounding_guard.py +0 -0
  51. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/metrics.py +0 -0
  52. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/output_budget.py +0 -0
  53. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/pii_redaction.py +0 -0
  54. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/pricing.py +0 -0
  55. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/rate_limit.py +0 -0
  56. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/rbac.py +0 -0
  57. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/replay_guard.py +0 -0
  58. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/response_scanner.py +0 -0
  59. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/schema_validation.py +0 -0
  60. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/semantic_cache.py +0 -0
  61. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/semantic_firewall.py +0 -0
  62. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/sensitive_classifier.py +0 -0
  63. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/server_verification.py +0 -0
  64. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/session_offload.py +0 -0
  65. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/state_backend.py +0 -0
  66. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/stdio_guard.py +0 -0
  67. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/tokens.py +0 -0
  68. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/pillars/tool_metadata_fingerprint.py +0 -0
  69. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/policy_simulator.py +0 -0
  70. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/redteam.py +0 -0
  71. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/serve.py +0 -0
  72. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/tenant.py +0 -0
  73. {mcp_bastion_python-2.0.0 → mcp_bastion_python-2.0.1}/src/mcp_bastion/transport_hardening.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: mcp-bastion-python
3
- Version: 2.0.0
3
+ Version: 2.0.1
4
4
  Summary: Security middleware for MCP servers protecting LLM agents from prompt injection, resource exhaustion, and PII leakage
5
5
  Project-URL: Homepage, https://github.com/vaquarkhan/MCP-Bastion
6
6
  Project-URL: Repository, https://github.com/vaquarkhan/MCP-Bastion
@@ -101,30 +101,32 @@ Provides-Extra: redis
101
101
  Requires-Dist: redis>=5.0.0; extra == 'redis'
102
102
  Description-Content-Type: text/markdown
103
103
 
104
- # MCP-Bastion
104
+ # MCP-Bastion
105
105
 
106
106
  <!-- mcp-name: io.github.vaquarkhan/mcp-bastion -->
107
107
 
108
108
  <p align="center">
109
109
  <img
110
110
  src="images/mcp-bastian.png"
111
- alt="MCP-BastionFortifying the Model Context Protocol"
111
+ alt="MCP-Bastion - Fortifying the Model Context Protocol"
112
112
  width="720"
113
113
  style="max-width:100%; height:auto;"
114
114
  />
115
115
  </p>
116
116
 
117
- [![PyPI: mcp-bastion-python 2.0.0](https://img.shields.io/pypi/v/mcp-bastion-python?logo=python)](https://pypi.org/project/mcp-bastion-python/2.0.0/)
117
+ [![PyPI 2.0.1](https://img.shields.io/badge/PyPI-2.0.1-3775A9?logo=pypi&logoColor=white)](https://pypi.org/project/mcp-bastion-python/2.0.1/)
118
118
  [![PePy all-time downloads (mcp-bastion-python)](https://img.shields.io/pepy/dt/mcp-bastion-python?label=PePy%20all-time%20downloads)](https://pepy.tech/projects/mcp-bastion-python)
119
- [![Python](https://img.shields.io/pypi/pyversions/mcp-bastion-python)](https://pypi.org/project/mcp-bastion-python/)
119
+ [![Python](https://img.shields.io/pypi/pyversions/mcp-bastion-python)](https://pypi.org/project/mcp-bastion-python/2.0.1/)
120
120
  [![CI](https://img.shields.io/github/actions/workflow/status/vaquarkhan/MCP-Bastion/ci.yml?branch=main&label=CI)](https://github.com/vaquarkhan/MCP-Bastion/actions/workflows/ci.yml)
121
- [![Docker: GHCR mcp-bastion-proxy (port 8080)](https://img.shields.io/badge/docker%20%28ghcr%29-mcp--bastion--proxy%20%7C%208080-2496ED?logo=docker)](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-proxy)
122
- [![Docker: GHCR mcp-bastion-dashboard (port 7000)](https://img.shields.io/badge/docker%20%28ghcr%29-mcp--bastion--dashboard%20%7C%207000-2496ED?logo=docker)](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-dashboard)
121
+ [![Docker: GHCR mcp-bastion-proxy v2.0.1](https://img.shields.io/badge/GHCR-mcp--bastion--proxy%3Av2.0.1-2496ED?logo=docker)](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-proxy)
122
+ [![Docker: GHCR mcp-bastion-dashboard v2.0.1](https://img.shields.io/badge/GHCR-mcp--bastion--dashboard%3Av2.0.1-2496ED?logo=docker)](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-dashboard)
123
123
  [![License: Source Available](https://img.shields.io/badge/license-Source%20Available-orange.svg)](LICENSE)
124
124
  [![Website](https://img.shields.io/badge/website-vaquarkhan.github.io/MCP--Bastion-blue?logo=github)](https://vaquarkhan.github.io/MCP-Bastion/)
125
125
 
126
126
  **The Zero-Trust control plane for MCP agents.** Your agent can call databases, APIs, and shell tools. One bad prompt can leak PII; one runaway loop can burn your API budget in minutes; three agents on one server with no identity boundary is a confused-deputy incident waiting to happen. MCP-Bastion wraps your MCP server with **local** guardrails: **agent IAM**, supply-chain checksums, injection blocking, PII redaction, and **denial-of-wallet caps**, under **5ms overhead**, with no third-party safety API.
127
127
 
128
+ **Guiding rule:** Stay a **zero-infra, drop-in library** - the guardrail brain that composes with any gateway, not a gateway itself. Strategy: [docs/ZERO_INFRA_STRATEGY.md](docs/ZERO_INFRA_STRATEGY.md).
129
+
128
130
  <p align="center">
129
131
  <img
130
132
  src="images/mcp-bastion-mcp-surface-scale.png"
@@ -147,7 +149,7 @@ MCP-Bastion acts as the **Zero-Trust Control Plane** for your agents, addressing
147
149
  ### Define your agent policies (`bastion.yaml`)
148
150
 
149
151
  ```yaml
150
- # Stop the Confused Deputy ProblemIdentity-Aware Routing
152
+ # Stop the Confused Deputy Problem - Identity-Aware Routing
151
153
  agent_iam:
152
154
  enabled: true
153
155
  token_metadata_key: bastion_agent_token
@@ -169,11 +171,11 @@ server_verification:
169
171
 
170
172
  Generate a manifest after a trusted build: `mcp-bastion manifest server.py pyproject.toml -o mcp-server.manifest.json`
171
173
 
172
- Deep dive: [docs/RUNTIME_GOVERNANCE.md](docs/RUNTIME_GOVERNANCE.md) · [docs/ROADMAP.md](docs/ROADMAP.md)
174
+ Deep dive: [docs/RUNTIME_GOVERNANCE.md](docs/RUNTIME_GOVERNANCE.md) · [docs/ROADMAP.md](docs/ROADMAP.md) (future 3.0+ plan)
173
175
 
174
176
  ### Full MCP surface + horizontal scale (2.0.0)
175
177
 
176
- Previously, most pillars ran only on **`tools/call`**. **2.0.0** extends the pipeline to **`resources/read`**, **`prompts/get`**, **`sampling/createMessage`**, and **`elicitation/create`**closing exfil/injection gaps on the rest of the MCP surface.
178
+ Previously, most pillars ran only on **`tools/call`**. **2.0.0** extends the pipeline to **`resources/read`**, **`prompts/get`**, **`sampling/createMessage`**, and **`elicitation/create`** - closing exfil/injection gaps on the rest of the MCP surface.
177
179
 
178
180
  For **multi-replica** deployments, enable **`state_backend.type: redis`** so rate limits, replay nonces, cost budgets, and session tool scope are shared across pods (default `memory` is single-process).
179
181
 
@@ -195,8 +197,30 @@ Battle-tested patterns from the broader MCP gateway ecosystem, wired into the mi
195
197
  | **RBAC fnmatch globs** | Role permissions like `read_*` / `files_*` with **specificity-aware** matching |
196
198
  | **Audit JSONL + `mcp-bastion tail`** | Append-only compliance log; `audit.jsonl_path` in config or `mcp-bastion tail -p audit.jsonl` |
197
199
  | **Cost checkpoint** | Optional disk persistence for session totals across restarts (`cost_tracker.checkpoint_path`, memory backend only) |
200
+ | **Cost-aware policy (`cost_policy`)** | Live spend rules: degrade model, force discovery filter, require approval; expensive-chain blocking |
201
+ | **Governance attestation** | `mcp-bastion attest export --session …` - signed session bundle with policy hash + controls fired |
202
+ | **Boundary mode** | Mandatory proxy auth on every request (`boundary_mode` + `edge_auth` / `agent_iam`) - [GATEWAY_BOUNDARY.md](docs/GATEWAY_BOUNDARY.md) |
203
+ | **Ungated PromptGuard** | `prompt_guard.use_ungated_default: true` → ProtectAI DeBERTa classifier (no HF gate) |
198
204
 
199
205
  ```yaml
206
+ cost_policy:
207
+ enabled: true
208
+ rules:
209
+ - when: { session_spend_pct_gte: 80 }
210
+ action: degrade_model
211
+ target_model: gpt-4o-mini
212
+ - when: { session_spend_pct_gte: 95 }
213
+ action: require_approval
214
+ expensive_chain:
215
+ enabled: true
216
+ max_projected_cost_usd: 1.0
217
+
218
+ governance:
219
+ attestation_enabled: true
220
+
221
+ boundary_mode:
222
+ enabled: true # requires edge_auth or agent_iam
223
+
200
224
  argument_guards:
201
225
  enabled: true
202
226
  rules:
@@ -229,7 +253,7 @@ cost_tracker:
229
253
  | **Guardrails without a rewrite** | Drop-in middleware: `secure_fastmcp(mcp)` or one `bastion.yaml` |
230
254
  | **Privacy your legal team accepts** | PromptGuard + Presidio run **in your process**; data stays on your network |
231
255
  | **Stop runaway agents & budget burn** | **On by default:** 15 tool calls/session, 60s timeout, 50k token budget. **Optional:** per-tool caps, USD session/day limits, response offload |
232
- | **Shrink context & cut token spend** | **Opt-in:** discovery filter (fewer tools in `tools/list`), output budget + session offload (**up to ~99% on oversized tool outputs**), lexical similarity cache[measured benchmarks](docs/BENCHMARKS.md) |
256
+ | **Shrink context & cut token spend** | **Opt-in:** discovery filter (fewer tools in `tools/list`), output budget + session offload (**up to ~99% on oversized tool outputs**), lexical similarity cache - [measured benchmarks](docs/BENCHMARKS.md) |
233
257
  | **Something that ships today** | PyPI, npm, Docker on GHCR, FastMCP, TypeScript wrapper, CI validate, live dashboard |
234
258
  | **Policy your team can review** | `bastion.yaml` in Git, hot reload, OWASP-aligned controls ([docs/PILLARS.md](docs/PILLARS.md)) |
235
259
 
@@ -251,17 +275,17 @@ Blocked calls return standard errors (`RateLimitExceededError` **-32002**, `Toke
251
275
 
252
276
  ### Token reduction & cost saving
253
277
 
254
- Bastion does not only **block** runaway spendit **reduces** how much **tool output and tool-catalog** tokens reach the model on each turn (not the user’s LLM prompt text itself):
278
+ Bastion does not only **block** runaway spend - it **reduces** how much **tool output and tool-catalog** tokens reach the model on each turn (not the user’s LLM prompt text itself):
255
279
 
256
280
  | Savings lever | What it does | Default |
257
281
  |---------------|--------------|---------|
258
282
  | **Discovery filter** | Hides unused tools from `tools/list` so agents carry a smaller tool catalog in context (~**85%** fewer catalog tokens in [benchmarks](docs/BENCHMARKS.md) with 20→3 tools) | Opt-in |
259
283
  | **Output budget + offload** | Truncates oversized tool responses; stores the rest in-session for `bastion_get_offloaded` (**up to ~99.7%** on 50k-token dumps; **0%** when already under budget) | Opt-in |
260
- | **Lexical similarity cache** | Skips redundant tool calls when queries are near-identical (Jaccard word overlapnot embedding “semantic” search) | Opt-in |
284
+ | **Lexical similarity cache** | Skips redundant tool calls when queries are near-identical (Jaccard word overlap - not embedding “semantic” search) | Opt-in |
261
285
  | **Token budget caps** | Hard stop before session token burn exceeds your limit | **On** (50k tokens) |
262
286
  | **USD session/day limits** | Dollar ceilings via cost tracker | Opt-in |
263
287
 
264
- There is **no honest single “X% prompt reduction”** figuresavings are **input-dependent**. See **[docs/BENCHMARKS.md](docs/BENCHMARKS.md)** for reproducible pytest benchmarks and live numbers.
288
+ There is **no honest single “X% prompt reduction”** figure - savings are **input-dependent**. See **[docs/BENCHMARKS.md](docs/BENCHMARKS.md)** for reproducible pytest benchmarks and live numbers.
265
289
 
266
290
  <p align="center">
267
291
  <img
@@ -273,9 +297,9 @@ There is **no honest single “X% prompt reduction”** figure — savings are *
273
297
  </p>
274
298
  <p align="center"><sub>Reproduce: <code>PYTHONPATH=src python -m pytest tests/test_benchmarks_finops_rbac.py -v</code> · Regenerate report: <code>python scripts/generate_benchmark_report.py</code></sub></p>
275
299
 
276
- Less tool output and catalog noise per turn means lower LLM input costwithout sending prompts to a third-party optimizer API.
300
+ Less tool output and catalog noise per turn means lower LLM input cost - without sending prompts to a third-party optimizer API.
277
301
 
278
- **Bottom line:** MCP turned every server into an agent gateway overnight. Bastion is the firewall that makes that gateway safe to run in productionin **three lines of code** or one config file.
302
+ **Bottom line:** MCP turned every server into an agent gateway overnight. Bastion is the firewall that makes that gateway safe to run in production - in **three lines of code** or one config file.
279
303
 
280
304
  ### OWASP MCP Top 10 + production attacks
281
305
 
@@ -320,7 +344,7 @@ All **10** [OWASP MCP Top 10](https://owasp.org/www-project-mcp-top-10/) risks a
320
344
 
321
345
  | Lever | Controls | Benchmark |
322
346
  |-------|----------|-----------|
323
- | Smaller tool catalog in context | Discovery filter on `tools/list` | ~85% catalog tokens (20→3 tools)[BENCHMARKS.md](docs/BENCHMARKS.md) |
347
+ | Smaller tool catalog in context | Discovery filter on `tools/list` | ~85% catalog tokens (20→3 tools) - [BENCHMARKS.md](docs/BENCHMARKS.md) |
324
348
  | Less tool output in every turn | Output budget, session offload, `bastion_get_offloaded` | Up to ~99.7% on oversized dumps; 0% when under budget |
325
349
  | Fewer redundant calls | Lexical similarity cache (Jaccard overlap) | Exact repeat hits; paraphrase misses at 0.9 |
326
350
  | Predictable spend | Token budget caps, USD session/day limits | Session defaults on |
@@ -359,7 +383,7 @@ More paths (TypeScript, CI validate, Docker): **[docs/QUICK_START.md](docs/QUICK
359
383
 
360
384
  ### How it works
361
385
 
362
- MCP-Bastion sits **in-process** on your MCP server and inspects every `tools/call` before it reaches databases, APIs, or shell toolsthen redacts sensitive data on the way back.
386
+ MCP-Bastion sits **in-process** on your MCP server and inspects every `tools/call` before it reaches databases, APIs, or shell tools - then redacts sensitive data on the way back.
363
387
 
364
388
  ```mermaid
365
389
  flowchart LR
@@ -389,7 +413,7 @@ flowchart TB
389
413
  TS --> Sidecar["Rate limit in-process · ML via sidecar"]
390
414
  ```
391
415
 
392
- > **Releases:** npm, PyPI, and prebuilt **Docker** on GHCRsee [DOCKER.md](DOCKER.md). **Community:** GitHub **Issues**, **Discussions**, **PRs**. **Security:** [SECURITY.md](SECURITY.md).
416
+ > **Releases:** npm, PyPI, and prebuilt **Docker** on GHCR - see [DOCKER.md](DOCKER.md). **Community:** [SUPPORT.md](SUPPORT.md) · [CONTRIBUTING.md](CONTRIBUTING.md) · [FUNDING.md](FUNDING.md) · **Security:** [SECURITY.md](SECURITY.md).
393
417
 
394
418
  ---
395
419
 
@@ -421,9 +445,9 @@ Hooks into MCP SDKs (TypeScript, Python) and FastMCP via standard middleware. No
421
445
 
422
446
  ### Complete feature catalog
423
447
 
424
- **Pillar definitions:** Security controls, `bastion.yaml` sections, and how they relate to dashboard health rows are documented in [docs/PILLARS.md](docs/PILLARS.md) (canonical reference; avoids ambiguous “total pillar” counts). The same page lists **extended** features restored in 1.0.16+ (semantic firewall, sensitive classifier, external policy, edge auth, tool allowlist, session scope, tool metadata guard, multi-tenant, audit hash chain, pricing hooks, telemetry sinks, **red team** and **doctor** CLIs, etc.), **FinOps/context** pillars in 1.0.17+ (output budget, discovery filter, response scan, grounding guard), and **runtime governance** (agent IAM, server verificationintroduced in 1.0.18+, **shipped in 2.0.0**).
448
+ **Pillar definitions:** Security controls, `bastion.yaml` sections, and how they relate to dashboard health rows are documented in [docs/PILLARS.md](docs/PILLARS.md) (canonical reference; avoids ambiguous “total pillar” counts). The same page lists **extended** features restored in 1.0.16+ (semantic firewall, sensitive classifier, external policy, edge auth, tool allowlist, session scope, tool metadata guard, multi-tenant, audit hash chain, pricing hooks, telemetry sinks, **red team** and **doctor** CLIs, etc.), **FinOps/context** pillars in 1.0.17+ (output budget, discovery filter, response scan, grounding guard), and **runtime governance** (agent IAM, server verification - introduced in 1.0.18+, **shipped in 2.0.0**).
425
449
 
426
- > **Deeper context:** [docs/SECURITY_OBSERVABILITY.md](docs/SECURITY_OBSERVABILITY.md)**OWASP MCP Top 10** alignment, attack scenarios, and SIEM/log integrations. **Framework add-ons** (LangChain, OpenAI, Bedrock, …) are listed under [Framework Integrations](#framework-integrations) below.
450
+ > **Deeper context:** [docs/SECURITY_OBSERVABILITY.md](docs/SECURITY_OBSERVABILITY.md) - **OWASP MCP Top 10** alignment, attack scenarios, and SIEM/log integrations. **Framework add-ons** (LangChain, OpenAI, Bedrock, …) are listed under [Framework Integrations](#framework-integrations) below.
427
451
 
428
452
  #### Threat prevention & content safety
429
453
 
@@ -431,21 +455,21 @@ Hooks into MCP SDKs (TypeScript, Python) and FastMCP via standard middleware. No
431
455
  |--------|----------------|
432
456
  | **Prompt injection defense** | Meta **PromptGuard** scores tool arguments; malicious / jailbreak-style payloads can be blocked before execution (local inference, no third-party API). |
433
457
  | **Content filter** | Block **shell/code execution** patterns, **sensitive file paths**, and **URLs**; optional **allowlist** / **denylist** regex or substring rules. |
434
- | **PII redaction** | **Microsoft Presidio** detects many entity types in outbound tool/resource text (SSN, email, phone, cards, passport, IBAN, licenses, etc.—see Presidio docs). |
458
+ | **PII redaction** | **Microsoft Presidio** detects many entity types in outbound tool/resource text (SSN, email, phone, cards, passport, IBAN, licenses, etc. - see Presidio docs). |
435
459
 
436
460
  #### Access control, integrity & abuse
437
461
 
438
462
  | Feature | What you get |
439
463
  |--------|----------------|
440
- | **Agent IAM (Confused Deputy)** | Bind **API tokens** to **agent identities**; per-agent `allowed_tools` / `blocked_tools`, **resource URI** allow/block, optional rate limitsstops a support bot from calling admin tools or reading secret resources. See [docs/RUNTIME_GOVERNANCE.md](docs/RUNTIME_GOVERNANCE.md). |
441
- | **Full MCP surface guards (2.0.0)** | **`resources/read`**, **`prompts/get`**, **`sampling/createMessage`**, **`elicitation/create`**same inbound/outbound pillars as tool calls (not only `tools/call`). [docs/MCP_SURFACE_AND_SCALE.md](docs/MCP_SURFACE_AND_SCALE.md) |
442
- | **Distributed state (2.0.0)** | **`state_backend: redis`**shared rate limits, replay nonces, cost caps, session scope across replicas. `pip install mcp-bastion-python[redis]` |
464
+ | **Agent IAM (Confused Deputy)** | Bind **API tokens** to **agent identities**; per-agent `allowed_tools` / `blocked_tools`, **resource URI** allow/block, optional rate limits - stops a support bot from calling admin tools or reading secret resources. See [docs/RUNTIME_GOVERNANCE.md](docs/RUNTIME_GOVERNANCE.md). |
465
+ | **Full MCP surface guards (2.0.0)** | **`resources/read`**, **`prompts/get`**, **`sampling/createMessage`**, **`elicitation/create`** - same inbound/outbound pillars as tool calls (not only `tools/call`). [docs/MCP_SURFACE_AND_SCALE.md](docs/MCP_SURFACE_AND_SCALE.md) |
466
+ | **Distributed state (2.0.0)** | **`state_backend: redis`** - shared rate limits, replay nonces, cost caps, session scope across replicas. `pip install mcp-bastion-python[redis]` |
443
467
  | **Server verification (supply chain)** | SHA-256 **manifest checksums** verified at startup and on every `tools/call`; `mcp-bastion manifest` generates trusted manifests after a signed-off build. |
444
- | **RBAC** | **Tool-level** allow/deny by **role** (from request metadata); **fnmatch globs** (`read_*`) with specificity-aware matching in `bastion.yaml`. **Pair with Agent IAM or edge auth**alone, roles are only as trustworthy as whatever sets `metadata["role"]`. [Live matrix →](docs/BENCHMARKS.md#rbac-tool-level-opt-in) |
445
- | **Argument guards (2.0.0)** | **JSONPath + regex** block/redact on `tools/call` arguments before schema validationstops shell injection and secret exfil in argv-style payloads. |
468
+ | **RBAC** | **Tool-level** allow/deny by **role** (from request metadata); **fnmatch globs** (`read_*`) with specificity-aware matching in `bastion.yaml`. **Pair with Agent IAM or edge auth** - alone, roles are only as trustworthy as whatever sets `metadata["role"]`. [Live matrix →](docs/BENCHMARKS.md#rbac-tool-level-opt-in) |
469
+ | **Argument guards (2.0.0)** | **JSONPath + regex** block/redact on `tools/call` arguments before schema validation - stops shell injection and secret exfil in argv-style payloads. |
446
470
  | **Schema validation** | Validate `tools/call` arguments against **JSON Schema** before the tool runs (block malformed or bypass attempts). |
447
471
  | **Replay guard** | **Nonce** tracking to reject replayed requests (configurable **require_nonce**). |
448
- | **Rate limiting** | **Token-bucket** style limits: **max iterations** per session, **timeout**, **token budget**—stops runaway loops and brute-force patterns. |
472
+ | **Rate limiting** | **Token-bucket** style limits: **max iterations** per session, **timeout**, **token budget** - stops runaway loops and brute-force patterns. |
449
473
  | **Circuit breaker** | Stop calling tools that fail repeatedly (limits blast radius of bad upstreams or poisoned tools). |
450
474
 
451
475
  #### FinOps & performance
@@ -453,18 +477,18 @@ Hooks into MCP SDKs (TypeScript, Python) and FastMCP via standard middleware. No
453
477
  | Feature | What you get |
454
478
  |--------|----------------|
455
479
  | **Cost tracker** | Per-**session** and optional per-**day** USD caps; blocks when budget is exceeded. Optional **disk checkpoint** for restart-safe totals (memory backend). |
456
- | **Semantic cache** (lexical) | Optional **Jaccard word-overlap** cache for near-identical tool queriesnot embedding-based; see [benchmarks](docs/BENCHMARKS.md#lexical-similarity-cache-opt-in-semantic-cache-in-config). |
480
+ | **Semantic cache** (lexical) | Optional **Jaccard word-overlap** cache for near-identical tool queries - not embedding-based; see [benchmarks](docs/BENCHMARKS.md#lexical-similarity-cache-opt-in-semantic-cache-in-config). |
457
481
  | **Low overhead** | Middleware on the hot path targeting **&lt;5 ms** typical overhead (see [docs/METRICS.md](docs/METRICS.md)). |
458
482
 
459
483
  #### Audit, metrics & alerting
460
484
 
461
485
  | Feature | What you get |
462
486
  |--------|----------------|
463
- | **Audit logging** | Structured **allow/deny** decisions with **reason**, **tool**, **tenant_id**, **trace_id**, **request_id**—feed SOC / compliance. Optional **JSONL file sink** + **`mcp-bastion tail`**. |
487
+ | **Audit logging** | Structured **allow/deny** decisions with **reason**, **tool**, **tenant_id**, **trace_id**, **request_id** - feed SOC / compliance. Optional **JSONL file sink** + **`mcp-bastion tail`**. |
464
488
  | **Alert sinks** | **Slack** incoming webhook; **generic HTTP** webhooks (PagerDuty, Teams, custom APIs); **multiple URLs**; **retry**, **backoff**, **timeout** in `bastion.yaml`. |
465
489
  | **In-memory metrics** | **Global MetricsStore**: requests, blocks, PII counts, cost, per-tool stats, latency samples, rolling **time series** buckets. |
466
490
  | **Real-time dashboard** | **Web UI** with a top **KPI summary** (totals, block %, top threat, active users/tenants), **traffic & block charts**, **blocked-by-reason/kind** (with readable reasons / tooltips), **PII by entity** (severity-style coloring, e.g. high-risk types emphasized), **top tools**, **cost by user**, **latency P50/P95/P99**, **forensics table** (tenant filter, trace/replay helpers), **recent alerts**, **insights & anomalies** (heuristic signals), **dark/light theme**, **Prometheus** `/metrics`, **JSON** `/api/metrics`, loading/empty guidance instead of a blank first paint. |
467
- | **OpenTelemetry** | Optional **OTLP** span export`pip install mcp-bastion-python[otel]`[docs/OTEL.md](docs/OTEL.md). |
491
+ | **OpenTelemetry** | Optional **OTLP** span export - `pip install mcp-bastion-python[otel]` - [docs/OTEL.md](docs/OTEL.md). |
468
492
 
469
493
  #### Policy, packaging & developer experience
470
494
 
@@ -473,19 +497,19 @@ Hooks into MCP SDKs (TypeScript, Python) and FastMCP via standard middleware. No
473
497
  | **Policy-as-code** | Single **`bastion.yaml`**: toggles for all request-path controls plus audit, alerts, and hot reload ([docs/PILLARS.md](docs/PILLARS.md)); load via `load_config` / `build_middleware_from_config`. |
474
498
  | **Hot reload** | Optional **reload `bastion.yaml` on change** without restarting the MCP server ([docs/POLICY_AS_CODE.md](docs/POLICY_AS_CODE.md)). |
475
499
  | **Composable middleware** | **`compose_middleware`** ordering; **`MCPBastionMiddleware`** flags for each pillar. |
476
- | **CLI** | **`mcp-bastion validate`**, **`manifest`** (SHA-256 manifest for server verification), **`serve`** (HTTP MCP), **`dashboard`** (optional **`--reload`** / **`--demo`**), **`redteam`**, **`doctor`**[docs/CLI.md](docs/CLI.md). |
500
+ | **CLI** | **`mcp-bastion validate`**, **`manifest`**, **`attest export`**, **`serve`**, **`dashboard`**, **`redteam`**, **`doctor`**, **`tail`** - [docs/CLI.md](docs/CLI.md). |
477
501
  | **Python + TypeScript** | **`mcp-bastion-python`** on PyPI; **`@mcp-bastion/core`** on npm for TypeScript MCP servers (rate limits in-process; prompt/PII via optional sidecar). |
478
- | **Containers** | **Dockerfile**, **docker-compose** profiles (proxy + optional dashboard)[DOCKER.md](DOCKER.md). **Prebuilt images (GHCR):** [`mcp-bastion-proxy`](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-proxy), [`mcp-bastion-dashboard`](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-dashboard)published on each `v*` tag ([publish-docker.yml](.github/workflows/publish-docker.yml)). |
502
+ | **Containers** | **Dockerfile**, **docker-compose** profiles (proxy + optional dashboard) - [DOCKER.md](DOCKER.md). **Prebuilt images (GHCR):** [`mcp-bastion-proxy`](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-proxy), [`mcp-bastion-dashboard`](https://github.com/vaquarkhan/MCP-Bastion/pkgs/container/mcp-bastion-dashboard) - published on each `v*` tag ([publish-docker.yml](.github/workflows/publish-docker.yml)). |
479
503
 
480
504
  ### Real-Time Dashboard and Alerts
481
505
 
482
- **🎥 Demo (screen recording):** [Watch on Vimeo](https://vimeo.com/1186084574)overview of the dashboard and metrics (link opens the player on Vimeo).
506
+ **🎥 Demo (screen recording):** [Watch on Vimeo](https://vimeo.com/1186084574) - overview of the dashboard and metrics (link opens the player on Vimeo).
483
507
 
484
508
  <p align="center">
485
509
  <a href="https://vimeo.com/1186084574" title="Watch MCP-Bastion dashboard demo on Vimeo">
486
510
  <img
487
511
  src="docs/images/dashboard.png"
488
- alt="MCP-Bastion dashboardrequest KPIs, block rate, PII redacted, cost, top tools, and forensics"
512
+ alt="MCP-Bastion dashboard - request KPIs, block rate, PII redacted, cost, top tools, and forensics"
489
513
  width="920"
490
514
  style="max-width:100%; height:auto; border-radius:12px; border:1px solid #e2e8f0;"
491
515
  />
@@ -510,14 +534,14 @@ mcp-bastion dashboard --port 7000
510
534
  <p align="center">
511
535
  <img
512
536
  src="docs/images/api-metrics.png"
513
- alt="Example /api/metrics JSONrequests_total, blocked_total, pii_redacted_total, cost_total, top_tools"
537
+ alt="Example /api/metrics JSON - requests_total, blocked_total, pii_redacted_total, cost_total, top_tools"
514
538
  width="720"
515
539
  style="max-width:100%; height:auto; border-radius:8px; border:1px solid #e2e8f0;"
516
540
  />
517
541
  </p>
518
542
  <p align="center"><sub><code>/api/metrics</code> JSON for Grafana, Datadog, or custom pollers</sub></p>
519
543
 
520
- *Dashboard: total requests, blocked count and %, PII redacted, cost; blocked-by-reason bars; top tools; cost by user; recent alertsopen [http://localhost:7000/](http://localhost:7000/) while `mcp-bastion dashboard` is running.*
544
+ *Dashboard: total requests, blocked count and %, PII redacted, cost; blocked-by-reason bars; top tools; cost by user; recent alerts - open [http://localhost:7000/](http://localhost:7000/) while `mcp-bastion dashboard` is running.*
521
545
 
522
546
  - **Alerts:** Slack webhook and cost-threshold alerts. See [dashboard/README.md](dashboard/README.md).
523
547
 
@@ -543,11 +567,11 @@ Full index: **[docs/README.md](docs/README.md)** (docs hub) · published site en
543
567
  | [docs/DETAILED_TUTORIAL.md](docs/DETAILED_TUTORIAL.md) | Step-by-step implementation tutorial for new teams |
544
568
  | [docs/USE_CASES.md](docs/USE_CASES.md) | Real use cases: enterprise gateway, LLM products, internal tools, SaaS, compliance |
545
569
  | [docs/ATTACK_PREVENTION.md](docs/ATTACK_PREVENTION.md) | Examples showing how MCP-Bastion prevents real attacks (injection, PII leak, rate exhaustion, path traversal, RBAC, replay) |
546
- | [docs/PILLARS.md](docs/PILLARS.md) | Canonical pillar counts: **18** request-path features (10 core + 8 extended), **14** dashboard `pillar_health` rows, **20+** `bastion.yaml` top-level areassee the doc for scope |
570
+ | [docs/PILLARS.md](docs/PILLARS.md) | Canonical pillar counts: **18** request-path features (10 core + 8 extended), **14** dashboard `pillar_health` rows, **20+** `bastion.yaml` top-level areas - see the doc for scope |
547
571
  | [docs/SUPPLY_CHAIN.md](docs/SUPPLY_CHAIN.md) | CI merge gates, releases, npm provenance, PyPI Trusted Publishing |
548
572
  | [docs/INTEGRATION_MODELS.md](docs/INTEGRATION_MODELS.md) | Middleware + `bastion.yaml` vs “change base URL”; bridge for Python, TS, Desktop, HTTP, integrations |
549
573
  | [examples/ci/README.md](examples/ci/README.md) | Copy-paste GitHub Actions snippet to run `mcp-bastion validate` on your policy file |
550
- | [docs/BENCHMARKS.md](docs/BENCHMARKS.md) | **Measured** RBAC matrix, output-budget reduction (up to ~99% on large tool outputs), discovery filter, lexical cachepytest + report generator |
574
+ | [docs/BENCHMARKS.md](docs/BENCHMARKS.md) | **Measured** RBAC matrix, output-budget reduction (up to ~99% on large tool outputs), discovery filter, lexical cache - pytest + report generator |
551
575
  | [docs/REDTEAM.md](docs/REDTEAM.md) | Interpreting harness / red-team scores; which `bastion.yaml` pillars to enable; Node vs Python **scope** (`packages/core/README.md`) |
552
576
  | [docs/SECURITY_OBSERVABILITY.md](docs/SECURITY_OBSERVABILITY.md) | **OWASP MCP Top 10**, integration hooks, **fleet-scale `bastion.yaml` rollout**, **SIEM / SOC audit** patterns |
553
577
  | [docs/METRICS.md](docs/METRICS.md) | Performance overhead (&lt;5ms) and effectiveness metrics (dashboard, Prometheus, OTEL) |
@@ -555,7 +579,8 @@ Full index: **[docs/README.md](docs/README.md)** (docs hub) · published site en
555
579
  | [docs/GITHUB_PAGES.md](docs/GITHUB_PAGES.md) | Publish docs as a GitHub Pages website from this same repo |
556
580
  | [docs/QUICK_START.md](docs/QUICK_START.md) | Minimal FastMCP / `bastion.yaml` / CI snippets (time-to-value) |
557
581
  | [docs/DISCOVERY.md](docs/DISCOVERY.md) | Registry and ecosystem discovery checklist |
558
- | [docs/ROADMAP.md](docs/ROADMAP.md) | High-level directions; execution tracked in GitHub Issues |
582
+ | [docs/ROADMAP.md](docs/ROADMAP.md) | **Future roadmap (3.0+):** security, identity, FinOps, discoverability, maturity |
583
+ | [docs/COMPARISON.md](docs/COMPARISON.md) | vs unguarded MCP, thin proxy, full AI/MCP gateway |
559
584
  | [docs/ENGINEERING_10_10.md](docs/ENGINEERING_10_10.md) | Strategic path to 10/10 on injection depth, tool poisoning, gateway maturity, FinOps metrics, project maturity |
560
585
  | [CONTRIBUTING.md](CONTRIBUTING.md) | Contributor guide and **`good first issue`** ideas |
561
586
 
@@ -564,11 +589,12 @@ Full index: **[docs/README.md](docs/README.md)** (docs hub) · published site en
564
589
  **Prebuilt images (after the first [publish-docker](.github/workflows/publish-docker.yml) run, usually on a `v*` release tag):**
565
590
 
566
591
  ```bash
567
- docker pull ghcr.io/vaquarkhan/mcp-bastion-proxy:latest
568
- docker run -p 8080:8080 ghcr.io/vaquarkhan/mcp-bastion-proxy:latest
592
+ docker pull ghcr.io/vaquarkhan/mcp-bastion-proxy:v2.0.1
593
+ docker run -p 8080:8080 ghcr.io/vaquarkhan/mcp-bastion-proxy:v2.0.1
569
594
  # Dashboard (optional, port 7000):
570
- # docker pull ghcr.io/vaquarkhan/mcp-bastion-dashboard:latest
571
- # docker run -p 7000:7000 ghcr.io/vaquarkhan/mcp-bastion-dashboard:latest
595
+ # docker pull ghcr.io/vaquarkhan/mcp-bastion-dashboard:v2.0.1
596
+ # docker run -p 7000:7000 ghcr.io/vaquarkhan/mcp-bastion-dashboard:v2.0.1
597
+ # :latest is updated on each v* tag publish
572
598
  ```
573
599
 
574
600
  **Build locally** (any revision):
@@ -607,10 +633,10 @@ See [docs/CLI.md](docs/CLI.md).
607
633
 
608
634
  On every pull request and push to `main`, [`.github/workflows/ci.yml`](.github/workflows/ci.yml) runs:
609
635
 
610
- 1. `pip install -e ".[dev,policy,dashboard]"`install the Python package with tests, YAML policy loading, and FastAPI for dashboard tests.
611
- 2. `mcp-bastion validate --config bastion.yaml.example`ensure the example policy file loads.
612
- 3. `python -m pytest --cov=mcp_bastion --cov-fail-under=92`full Python test suite with **≥92%** line coverage on `src/mcp_bastion` (see `[tool.coverage.*]` in `pyproject.toml` for measured paths and gates).
613
- 4. `npm ci` and `npm test`TypeScript workspace tests.
636
+ 1. `pip install -e ".[dev,policy,dashboard]"` - install the Python package with tests, YAML policy loading, and FastAPI for dashboard tests.
637
+ 2. `mcp-bastion validate --config bastion.yaml.example` - ensure the example policy file loads.
638
+ 3. `python -m pytest --cov=mcp_bastion --cov-fail-under=92` - full Python test suite with **≥92%** line coverage on `src/mcp_bastion` (see `[tool.coverage.*]` in `pyproject.toml` for measured paths and gates).
639
+ 4. `npm ci` and `npm test` - TypeScript workspace tests.
614
640
 
615
641
  To validate **your** repo’s `bastion.yaml` in CI without cloning MCP-Bastion, see [examples/ci/README.md](examples/ci/README.md).
616
642
 
@@ -639,10 +665,10 @@ See **[docs/SECURITY_OBSERVABILITY.md](docs/SECURITY_OBSERVABILITY.md)** for the
639
665
 
640
666
  ## Why MCP-Bastion
641
667
 
642
- - **Active enforcement**Intercepts MCP tool traffic so policies (prompt injection checks, PII handling, content rules, RBAC, and more) run before tools execute and before sensitive results propagate.
643
- - **Local-first classification**PromptGuard and Presidio run in your environment; you are not required to send prompts to a third-party API for guardrail scoring.
644
- - **Stateful guardrails**Per-session rate limits, iteration caps, token budgets, and cost tracking to reduce runaway loops and unexpected spend.
645
- - **Composable integration**Use `bastion.yaml` with `build_middleware_from_config()` or wire `MCPBastionMiddleware` / `wrapWithMcpBastion` in Python or TypeScript. For a separate process in front of an upstream MCP server, use a wrapper or proxy you control; see [docs/INTEGRATION_MODELS.md](docs/INTEGRATION_MODELS.md).
668
+ - **Active enforcement** - Intercepts MCP tool traffic so policies (prompt injection checks, PII handling, content rules, RBAC, and more) run before tools execute and before sensitive results propagate.
669
+ - **Local-first classification** - PromptGuard and Presidio run in your environment; you are not required to send prompts to a third-party API for guardrail scoring.
670
+ - **Stateful guardrails** - Per-session rate limits, iteration caps, token budgets, and cost tracking to reduce runaway loops and unexpected spend.
671
+ - **Composable integration** - Use `bastion.yaml` with `build_middleware_from_config()` or wire `MCPBastionMiddleware` / `wrapWithMcpBastion` in Python or TypeScript. For a separate process in front of an upstream MCP server, use a wrapper or proxy you control; see [docs/INTEGRATION_MODELS.md](docs/INTEGRATION_MODELS.md).
646
672
 
647
673
  ---
648
674
 
@@ -665,7 +691,7 @@ See **[docs/SECURITY_OBSERVABILITY.md](docs/SECURITY_OBSERVABILITY.md)** for the
665
691
  | File | Purpose |
666
692
  |------|---------|
667
693
  | `examples/python_server_example.py` | Minimal middleware chain |
668
- | `examples/full_demo.py` | Multi-pillar stack (core toggles: rate limit, PII, RBAC, …see **docs/PILLARS.md**) |
694
+ | `examples/full_demo.py` | Multi-pillar stack (core toggles: rate limit, PII, RBAC, … - see **docs/PILLARS.md**) |
669
695
  | `examples/llm_server.py` | Shared MCP server for LLM clients |
670
696
  | `examples/llm_openai_example.py` | OpenAI |
671
697
  | `examples/llm_claude_example.py` | Claude |
@@ -695,7 +721,7 @@ pip install mcp-bastion-python==2.0.0
695
721
  `pip install mcp-bastion-python[policy]`
696
722
  (adds `pyyaml`; otherwise you may get `ImportError` when loading policy files).
697
723
  - **Prompt injection (PromptGuard):** two layers:
698
- 1. **Regex heuristics** (always on) block obvious jailbreak strings such as “ignore previous instructions”no model download required.
724
+ 1. **Regex heuristics** (always on) block obvious jailbreak strings such as “ignore previous instructions” - no model download required.
699
725
  2. **Meta Llama Prompt Guard 2** (`meta-llama/Llama-Prompt-Guard-2-86M`) is a **gated** Hugging Face model. Request access, then run `huggingface-cli login`. Without ML, obvious attacks are still blocked; unverified payloads are **blocked** when `fail_open: false` (default). Run `mcp-bastion doctor` to verify ML availability.
700
726
 
701
727
  The PyPI wheel ships the full `mcp_bastion` tree (including `config`, `cli`, `otel`, dashboard metrics, and alert sinks). If you use an older wheel that omits modules, upgrade to the current release.
@@ -734,23 +760,23 @@ pip install mcp-bastion-fastmcp # FastMCP servers
734
760
 
735
761
  | Package | Protects | Version | Downloads |
736
762
  |---------|----------|---------|-----------|
737
- | [mcp-bastion-langchain](https://pypi.org/project/mcp-bastion-langchain/) | LangChain | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-langchain) · [pepy](https://pepy.tech/projects/mcp-bastion-langchain) |
738
- | [mcp-bastion-openai](https://pypi.org/project/mcp-bastion-openai/) | OpenAI GPT | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-openai) · [pepy](https://pepy.tech/projects/mcp-bastion-openai) |
739
- | [mcp-bastion-anthropic](https://pypi.org/project/mcp-bastion-anthropic/) | Anthropic Claude | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-anthropic) · [pepy](https://pepy.tech/projects/mcp-bastion-anthropic) |
740
- | [mcp-bastion-bedrock](https://pypi.org/project/mcp-bastion-bedrock/) | AWS Bedrock | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-bedrock) · [pepy](https://pepy.tech/projects/mcp-bastion-bedrock) |
741
- | [mcp-bastion-gemini](https://pypi.org/project/mcp-bastion-gemini/) | Google Gemini | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-gemini) · [pepy](https://pepy.tech/projects/mcp-bastion-gemini) |
742
- | [mcp-bastion-crewai](https://pypi.org/project/mcp-bastion-crewai/) | CrewAI | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-crewai) · [pepy](https://pepy.tech/projects/mcp-bastion-crewai) |
743
- | [mcp-bastion-llamaindex](https://pypi.org/project/mcp-bastion-llamaindex/) | LlamaIndex | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-llamaindex) · [pepy](https://pepy.tech/projects/mcp-bastion-llamaindex) |
744
- | [mcp-bastion-groq](https://pypi.org/project/mcp-bastion-groq/) | Groq | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-groq) · [pepy](https://pepy.tech/projects/mcp-bastion-groq) |
745
- | [mcp-bastion-mistral](https://pypi.org/project/mcp-bastion-mistral/) | Mistral AI | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-mistral) · [pepy](https://pepy.tech/projects/mcp-bastion-mistral) |
746
- | [mcp-bastion-cohere](https://pypi.org/project/mcp-bastion-cohere/) | Cohere | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-cohere) · [pepy](https://pepy.tech/projects/mcp-bastion-cohere) |
747
- | [mcp-bastion-azure](https://pypi.org/project/mcp-bastion-azure/) | Azure OpenAI | 0.1.3 | [pypistats](https://pypistats.org/packages/mcp-bastion-azure) · [pepy](https://pepy.tech/projects/mcp-bastion-azure) |
748
- | [mcp-bastion-vertexai](https://pypi.org/project/mcp-bastion-vertexai/) | Vertex AI | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-vertexai) · [pepy](https://pepy.tech/projects/mcp-bastion-vertexai) |
749
- | [mcp-bastion-huggingface](https://pypi.org/project/mcp-bastion-huggingface/) | Hugging Face | 0.1.3 | [pypistats](https://pypistats.org/packages/mcp-bastion-huggingface) · [pepy](https://pepy.tech/projects/mcp-bastion-huggingface) |
750
- | [mcp-bastion-deepseek](https://pypi.org/project/mcp-bastion-deepseek/) | DeepSeek AI | 0.1.3 | [pypistats](https://pypistats.org/packages/mcp-bastion-deepseek) · [pepy](https://pepy.tech/projects/mcp-bastion-deepseek) |
751
- | [mcp-bastion-together](https://pypi.org/project/mcp-bastion-together/) | Together AI | 0.1.3 | [pypistats](https://pypistats.org/packages/mcp-bastion-together) · [pepy](https://pepy.tech/projects/mcp-bastion-together) |
752
- | [mcp-bastion-fireworks](https://pypi.org/project/mcp-bastion-fireworks/) | Fireworks AI | 0.1.3 | [pypistats](https://pypistats.org/packages/mcp-bastion-fireworks) · [pepy](https://pepy.tech/projects/mcp-bastion-fireworks) |
753
- | [mcp-bastion-fastmcp](https://pypi.org/project/mcp-bastion-fastmcp/) | FastMCP servers | 0.1.2 | [pypistats](https://pypistats.org/packages/mcp-bastion-fastmcp) · [pepy](https://pepy.tech/projects/mcp-bastion-fastmcp) |
763
+ | [mcp-bastion-langchain](https://pypi.org/project/mcp-bastion-langchain/) | LangChain | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-langchain) · [pepy](https://pepy.tech/projects/mcp-bastion-langchain) |
764
+ | [mcp-bastion-openai](https://pypi.org/project/mcp-bastion-openai/) | OpenAI GPT | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-openai) · [pepy](https://pepy.tech/projects/mcp-bastion-openai) |
765
+ | [mcp-bastion-anthropic](https://pypi.org/project/mcp-bastion-anthropic/) | Anthropic Claude | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-anthropic) · [pepy](https://pepy.tech/projects/mcp-bastion-anthropic) |
766
+ | [mcp-bastion-bedrock](https://pypi.org/project/mcp-bastion-bedrock/) | AWS Bedrock | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-bedrock) · [pepy](https://pepy.tech/projects/mcp-bastion-bedrock) |
767
+ | [mcp-bastion-gemini](https://pypi.org/project/mcp-bastion-gemini/) | Google Gemini | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-gemini) · [pepy](https://pepy.tech/projects/mcp-bastion-gemini) |
768
+ | [mcp-bastion-crewai](https://pypi.org/project/mcp-bastion-crewai/) | CrewAI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-crewai) · [pepy](https://pepy.tech/projects/mcp-bastion-crewai) |
769
+ | [mcp-bastion-llamaindex](https://pypi.org/project/mcp-bastion-llamaindex/) | LlamaIndex | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-llamaindex) · [pepy](https://pepy.tech/projects/mcp-bastion-llamaindex) |
770
+ | [mcp-bastion-groq](https://pypi.org/project/mcp-bastion-groq/) | Groq | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-groq) · [pepy](https://pepy.tech/projects/mcp-bastion-groq) |
771
+ | [mcp-bastion-mistral](https://pypi.org/project/mcp-bastion-mistral/) | Mistral AI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-mistral) · [pepy](https://pepy.tech/projects/mcp-bastion-mistral) |
772
+ | [mcp-bastion-cohere](https://pypi.org/project/mcp-bastion-cohere/) | Cohere | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-cohere) · [pepy](https://pepy.tech/projects/mcp-bastion-cohere) |
773
+ | [mcp-bastion-azure](https://pypi.org/project/mcp-bastion-azure/) | Azure OpenAI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-azure) · [pepy](https://pepy.tech/projects/mcp-bastion-azure) |
774
+ | [mcp-bastion-vertexai](https://pypi.org/project/mcp-bastion-vertexai/) | Vertex AI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-vertexai) · [pepy](https://pepy.tech/projects/mcp-bastion-vertexai) |
775
+ | [mcp-bastion-huggingface](https://pypi.org/project/mcp-bastion-huggingface/) | Hugging Face | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-huggingface) · [pepy](https://pepy.tech/projects/mcp-bastion-huggingface) |
776
+ | [mcp-bastion-deepseek](https://pypi.org/project/mcp-bastion-deepseek/) | DeepSeek AI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-deepseek) · [pepy](https://pepy.tech/projects/mcp-bastion-deepseek) |
777
+ | [mcp-bastion-together](https://pypi.org/project/mcp-bastion-together/) | Together AI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-together) · [pepy](https://pepy.tech/projects/mcp-bastion-together) |
778
+ | [mcp-bastion-fireworks](https://pypi.org/project/mcp-bastion-fireworks/) | Fireworks AI | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-fireworks) · [pepy](https://pepy.tech/projects/mcp-bastion-fireworks) |
779
+ | [mcp-bastion-fastmcp](https://pypi.org/project/mcp-bastion-fastmcp/) | FastMCP servers | 2.0.0 | [pypistats](https://pypistats.org/packages/mcp-bastion-fastmcp) · [pepy](https://pepy.tech/projects/mcp-bastion-fastmcp) |
754
780
 
755
781
  ## Publish (PyPI / npm)
756
782
 
@@ -760,7 +786,15 @@ pip install mcp-bastion-fastmcp # FastMCP servers
760
786
 
761
787
  ## Developer Guide
762
788
 
763
- Integration examples for Python and TypeScript.
789
+ Integration examples for Python and TypeScript. Full contributor and feature docs:
790
+
791
+ | Doc | Description |
792
+ |-----|-------------|
793
+ | [docs/DEVELOPER_GUIDE.md](docs/DEVELOPER_GUIDE.md) | Repo layout, local dev, tests, release |
794
+ | [docs/FEATURES.md](docs/FEATURES.md) | How-to for all 18 security pillars |
795
+ | [docs/RBAC.md](docs/RBAC.md) | RBAC roles, fnmatch globs, Agent IAM pairing |
796
+ | [CONTRIBUTING.md](CONTRIBUTING.md) | PR checklist and good-first issues |
797
+ | [SUPPORT.md](SUPPORT.md) · [FUNDING.md](FUNDING.md) | Help and sponsorship |
764
798
 
765
799
  ---
766
800
 
@@ -816,7 +850,7 @@ See `VALIDATION_CHECKLIST.md` and `SETUP_GUIDE.md`.
816
850
 
817
851
  ### Python Tutorial: FastMCP Server
818
852
 
819
- FastMCP server with MCP-Bastion via `secure_fastmcp` (patches tool dispatchsee [integrations/mcp-bastion-fastmcp/README.md](integrations/mcp-bastion-fastmcp/README.md)).
853
+ FastMCP server with MCP-Bastion via `secure_fastmcp` (patches tool dispatch - see [integrations/mcp-bastion-fastmcp/README.md](integrations/mcp-bastion-fastmcp/README.md)).
820
854
 
821
855
  **Step 1: Install dependencies**
822
856
 
@@ -851,9 +885,9 @@ python server.py
851
885
  MCP-Bastion (via `secure_fastmcp`):
852
886
  - Scans **tool arguments** for prompt injection before execution
853
887
  - Redacts PII in **tool results** on the way out
854
- - Enforces default rate limits (**15** calls per session, **60s** timeoutsee `TokenBucketRateLimiter`)
888
+ - Enforces default rate limits (**15** calls per session, **60s** timeout - see `TokenBucketRateLimiter`)
855
889
 
856
- For **full** `bastion.yaml` policy or **resource** (`resources/read`) PII redaction, use the low-level MCP `Server` with `build_middleware_from_config()`see [docs/QUICK_START.md](docs/QUICK_START.md) path B.
890
+ For **full** `bastion.yaml` policy or **resource** (`resources/read`) PII redaction, use the low-level MCP `Server` with `build_middleware_from_config()` - see [docs/QUICK_START.md](docs/QUICK_START.md) path B.
857
891
 
858
892
  **Alternative: Policy-as-Code**
859
893
 
@@ -1182,10 +1216,18 @@ MCP-Bastion is distributed under the **MCP-Bastion Community and Commercial Lice
1182
1216
 
1183
1217
  - **Free** for non‑commercial use when you **cite MCP-Bastion** and the **copyright** notice (see [CITATION.cff](CITATION.cff); you can list *your* name, team, or org as authors or as who used the software, while still including the project and repository in the credit).
1184
1218
  - **Copyright** is retained. Do not remove license or copyright text, and do not republish a duplicate of the work as if it were unrelated software without meeting the License terms.
1185
- - **Commercial use** (as defined in the License) may still require a **separate written agreement**see [COMMERCIAL_LICENSE.md](COMMERCIAL_LICENSE.md).
1219
+ - **Commercial use** (as defined in the License) may still require a **separate written agreement** - see [COMMERCIAL_LICENSE.md](COMMERCIAL_LICENSE.md).
1186
1220
 
1187
1221
  See also:
1188
1222
 
1189
1223
  - [LICENSE](LICENSE)
1190
1224
  - [COMMERCIAL_LICENSE.md](COMMERCIAL_LICENSE.md)
1225
+ - [FUNDING.md](FUNDING.md) - sponsorship and sustainability
1226
+ - [SUPPORT.md](SUPPORT.md) - docs, issues, response expectations
1191
1227
  - [CITATION.cff](CITATION.cff)
1228
+
1229
+ ---
1230
+
1231
+ ## Product overview deck
1232
+
1233
+ **[MCP-Bastion features deck (PDF)](docs/mcp-bastian-features-deck.pdf)** - cost-aware runtime governance, pillar map, FinOps benchmarks, and deployment patterns in a short slide deck for evaluators and stakeholders.