Skip to main content

mcp-bloat

PyPI version Python versions License: MIT

Audit how many tokens your MCP servers eat from your context window — before your agent pays for them.

Every MCP server you connect makes your AI client load that server's tool schemas into the model's context — on every session, before you've asked a single question. A handful of servers can quietly consume a noticeable share of the context window. mcp-bloat measures it: it finds your MCP configs, connects to each server for real, and prints the token bill.

Install

pip install mcp-bloat
# or, without installing:
uvx mcp-bloat

For exact token counts (tiktoken's cl100k_base instead of a chars/4 estimate), install the accurate extra:

pip install "mcp-bloat[accurate]"

Usage

# Audit every MCP server in your known client configs
mcp-bloat

# See it work without configuring anything: audits three generated demo servers
mcp-bloat --demo

# Machine-readable output
mcp-bloat --json

# Just the per-server totals, without the per-tool breakdown
mcp-bloat --summary

# Fail CI if your servers eat more than 30,000 tokens of context
mcp-bloat --budget 30000

# Audit one specific config file
mcp-bloat --config ./mcp.json

# Audit one remote server directly, by URL — for example a server you
# use through ChatGPT or another hosted client
mcp-bloat --url https://example.com/mcp

# Look up ONE tool by name — which server(s) host it and what it costs
mcp-bloat --tool createPaymentTransaction

# If that server expects an Authorization header, pass it through
# (--header is repeatable, and --name sets the label shown in the report)
mcp-bloat --url https://example.com/mcp --header "Authorization: Bearer <token>"

# Compute the percentages against a specific model's context window —
# looked up live from OpenRouter/LiteLLM (free, no API key; cached 24h)
mcp-bloat --model gpt-5
mcp-bloat --model claude-sonnet-4-5

# …or set the window size yourself (this overrides --model)
mcp-bloat --window 128000

Which window am I using?

Every percentage in the report is relative to a context window. By default that's 200,000 tokens. Pass --model NAME to measure against the window of the model you actually use — mcp-bloat resolves the name against live model data from OpenRouter (with LiteLLM as a fallback and a small built-in snapshot when you're offline), and the report states which model and window it used. --window N skips the lookup and uses exactly N tokens. A server that eats 14% of a 200k window eats about 22% of a 128k one — same tokens, different pain.

Looking up a single tool

The full audit tells you which server is fat; sometimes you just want one tool. --tool NAME runs the audit as usual, then reports only that tool — no URL or config spelunking needed, since the tool names come from the servers themselves:

mcp-bloat --tool createPaymentTransaction

Matching is exact and case-insensitive first, then falls back to substring matches. If the same tool name is hosted by several servers, every match is shown. Each match reports the server and config it came from, the tool's total tokens, its share of that server's tool bill and of the context window, and a cost split — how much of the bill is the name + description text versus the input schema (the two parts plus the JSON structure roughly add up to the total). If nothing matches, you get the closest tool names that do exist and exit code 2. --tool combines with --config and --url to search just that target, and with --model/--window for the window percentage; with --json it prints {"tool": ..., "matches": [...]} instead.

From mcp-bloat --demo --tool run_tests:

Tool lookup: run_tests
┏━━━━━━━━━━━┳━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┳━━━━━━━━┳━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━┳━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┓
┃ Tool      ┃ Server      ┃ Source                                     ┃ Tokens ┃ % of server ┃ % of 200k ctx ┃ Cost split                      ┃
┡━━━━━━━━━━━╇━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━╇━━━━━━━━╇━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━╇━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━┩
│ run_tests │ dev-toolbox │ Demo — mcp-bloat --demo (generated config) │    208 │        8.7% │          0.1% │ description ≈ 39 · schema ≈ 166 │
└───────────┴─────────────┴────────────────────────────────────────────┴────────┴─────────────┴───────────────┴─────────────────────────────────┘

╭─ mcp-bloat tool lookup ──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│ 1 match for 'run_tests' across 1 server(s).                                                                                                                  │
│ Cost split: description counts the tool's name + description text; schema counts its inputSchema. The two parts plus the JSON structure roughly add up to    │
│ the total.                                                                                                                                                   │
│ Counting method: tiktoken cl100k_base                                                                                                                        │
╰──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯

Sample output

From mcp-bloat --demo (three generated servers: a tidy one, a medium one, and a deliberately huge one):

Demo — mcp-bloat --demo (generated config)
┏━━━━━━━━━━━━━┳━━━━━━━━━━━┳━━━━━━━┳━━━━━━━━┳━━━━━━━━━━━━━━━┳━━━━━━━━━┓
┃ Server      ┃ Transport ┃ Tools ┃ Tokens ┃ % of 200k ctx ┃ Status  ┃
┡━━━━━━━━━━━━━╇━━━━━━━━━━━╇━━━━━━━╇━━━━━━━━╇━━━━━━━━━━━━━━━╇━━━━━━━━━┩
│ notes-lite  │ stdio     │     3 │    204 │          0.1% │ ok      │
│ dev-toolbox │ stdio     │    15 │  2,394 │          1.2% │ ok      │
│ mega-api    │ stdio     │    50 │ 25,164 │         12.6% │ ⚠ BLOAT │
└─────────────┴───────────┴───────┴────────┴───────────────┴─────────┘

…

dev-toolbox — tools by cost
┏━━━━━━━━━━━━━━━━┳━━━━━━━━┳━━━━━━━━━━━━━┓
┃ Tool           ┃ Tokens ┃ % of server ┃
┡━━━━━━━━━━━━━━━━╇━━━━━━━━╇━━━━━━━━━━━━━┩
│ grep           │    254 │       10.6% │
│ run_tests      │    208 │        8.7% │
│ list_files     │    199 │        8.3% │
│ edit_file      │    186 │        7.8% │
│ run_command    │    174 │        7.3% │
│ read_file      │    172 │        7.2% │
│ get_git_diff   │    164 │        6.9% │
│ fetch_url      │    158 │        6.6% │
│ create_branch  │    155 │        6.5% │
│ write_file     │    152 │        6.3% │
│ search_docs    │    147 │        6.1% │
│ get_git_status │    130 │        5.4% │
│ lint           │    108 │        4.5% │
│ format_code    │    107 │        4.5% │
│ package_info   │     80 │        3.3% │
└────────────────┴────────┴─────────────┘

…

╭─ mcp-bloat summary ───────────────────────────────────────────────────╮
│ Total: 27,762 tokens  (13.9% of a 200,000-token context window)       │
│ Of your 27,762 tokens, that's:                                        │
│   2.8% of Claude Sonnet 5.5's 1,000,000 window                        │
│   6.9% of GPT-5's 400,000 window                                      │
│   2.6% of Gemini 2.5 Pro's 1,048,576 window                           │
│   16.9% of DeepSeek V3's 163,840 window                               │
│ Servers audited: 3                                                    │
│ Counting method: tiktoken cl100k_base                                 │
│ Most expensive single tool: list_workflow_run (mega-api) — 690 tokens │
│ ⚠ Over 10,000 tokens on its own: mega-api (25,164)                    │
╰───────────────────────────────────────────────────────────────────────╯

After each config's server table, the report drills into that server's tools — every tool's token cost, fattest first, with its share of the server's tool bill — and the summary names the single most expensive tool of the whole run. Pass --summary to collapse the report back to per-server totals only; --json always includes the per-tool data (each server's tools array — including each tool's description/schema token split — plus a top-level most_expensive_tool).

In default mode (no --model/--window), the summary also lines your total up against several current frontier models' context windows at once — resolved from the same live model data — so you can see the cost on the models people actually use; pass --model or --window and the summary sticks to that single window instead.

Any single server over 10,000 tokens is flagged ⚠ BLOAT.

How the counting works

For each configured server, mcp-bloat:

  1. Connects to the server over MCP (stdio or streamable HTTP) and performs the standard initialize handshake.
  2. Calls tools/list (and prompts/list / resources/list when the server supports them — prompts and resources are surfaced to the model too).
  3. For every tool, serializes {name, description, inputSchema} to JSON — the same information a client sends to the model so it can call the tool — and counts the tokens in that string.

Token counting uses tiktoken's cl100k_base encoding when the accurate extra is installed, and falls back to a chars/4 estimate otherwise. The report always states which method produced the numbers.

This is a close proxy for what clients actually send, not a byte-exact replica: individual clients wrap tool definitions slightly differently, and models with different tokenizers will count a little differently. Treat the numbers as accurate to a few percent — more than enough to find the server that's eating your context.

Servers that fail to start or don't respond within the timeout (default 20s, --timeout to change) are reported as errors; they never abort the rest of the audit. Server stderr is discarded so broken servers can't corrupt the report.

Config locations searched

  • Claude Code — ~/.claude.json, ./.mcp.json
  • Cursor — ~/.cursor/mcp.json, ./.cursor/mcp.json
  • Claude Desktop — ~/.config/Claude/claude_desktop_config.json, ~/Library/Application Support/Claude/claude_desktop_config.json, %APPDATA%\Claude\claude_desktop_config.json (Windows)
  • Windsurf — ~/.codeium/windsurf/mcp_config.json
  • VS Code — ./.vscode/mcp.json (the servers key)
  • Gemini CLI — ~/.gemini/settings.json, ./.gemini/settings.json (both the url and httpUrl spellings for HTTP servers)
  • Codex CLI — ~/.codex/config.toml (the [mcp_servers.*] tables)

Clients that don't keep MCP servers in a local config file — ChatGPT, for instance — can still be covered: take the server's URL and pass it to --url, with --header for any authorization header the server expects.

Malformed config files produce a warning, not a crash.

Security

mcp-bloat is read-only: it never modifies your config files or your servers. A few things worth knowing before you run it:

  • It starts your servers. Auditing works by launching each configured MCP server exactly the way your client would (stdio commands are executed; HTTP endpoints are connected to) and asking it to list its tools. Only audit configs you trust — a malicious server in a config you copied from the internet gets run, same as it would by Claude or Cursor.
  • Your secrets stay yours. Config files often hold API keys in env blocks. Those values are passed to the server process that needs them and are never printed — not in the terminal report, not in --json output. The same goes for --header values.
  • No telemetry. There is no analytics, no phone-home, and no account. The only network requests are to your own configured HTTP servers and the model-list lookups (OpenRouter / LiteLLM) — plain GETs that send no data about you or your configs, cached locally for 24 hours. Everything works offline from the cache or the built-in snapshot.

Found a problem? Please open an issue on GitHub.

License

MIT

Metadata

Release files for mcp-bloat 0.6.1

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for mcp-bloat 0.6.1
File Size Uploaded Provenance Actions
mcp_bloat-0.6.1.tar.gz 39.7 kB With provenance Details for mcp_bloat-0.6.1.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for mcp-bloat 0.6.1
File Interpreter ABI Platform Actions
mcp_bloat-0.6.1-py3-none-any.whl Python 3 none any Details for mcp_bloat-0.6.1-py3-none-any.whl

Total release size: 72.9 kB

Release files / mcp_bloat-0.6.1.tar.gz

Download URL mcp_bloat-0.6.1.tar.gz
Size 39.7 kB
Tags Source
SHA-256 checksum
How to use checksums
079e22e11a9e188f0d49fa0601265d4e5d8c8721ef61631ec063a6975ea78ee4
BLAKE2b-256 checksum
How to use checksums
d42d9b88feeceadab220062f43cb96de6f1675d1c36bee9e1ae929688176bdb6
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

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 Nov 1, 2026.

Transparency log

Release files / mcp_bloat-0.6.1-py3-none-any.whl

Download URL mcp_bloat-0.6.1-py3-none-any.whl
Size 33.2 kB
Tags Python 3
SHA-256 checksum
How to use checksums
54b6e933f360f905742cf51d76d6bcaf53291d70456de49a8bef02bd7c0ac97b
BLAKE2b-256 checksum
How to use checksums
da3cd9c78b97a0eee00af1f82b2cce5900b9447aaa72fa090b40843943a664ba
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

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 Nov 1, 2026.

Transparency log

Security for mcp-bloat 0.6.1

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.

Full provenance

All 2 files in this release have been uploaded with provenance metadata.

Select from 2 files

Attestation for mcp_bloat-0.6.1.tar.gz

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 Nov 1, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.6.1 This release

2 release files Full provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page