TesteMCP
MCP server for reading and listing JSON documents, designed to be used with Claude Haiku and Headroom compression to reduce token usage. It demonstrates an end-to-end MCP tool-use loop with stdio transport.
README
MCPTeste — MCP server + client com Claude Haiku e compressão de contexto
Teste end-to-end de um MCP server que expõe tools de leitura de documentos JSON, um MCP client que consome essas tools, e o Claude Haiku 4.5 decidindo quais chamar dentro de um loop de tool use. Os outputs das tools passam pelo Headroom antes de entrar no contexto do modelo.
Setup
python3 -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
cp .env.example .env # preencha ANTHROPIC_API_KEY
Uso
# server sozinho (stdio — fica aguardando o protocolo em stdin)
python -m src.server
# client: sobe o server como subprocesso e conversa com o modelo
python -m src.client "Qual o valor total da invoice 001?"
python -m src.client "Resuma o relatorio do primeiro trimestre de 2026"
# mesma pergunta sem compressão, para comparar input_tokens
python -m src.client "Resuma o relatorio do primeiro trimestre de 2026" --no-compression
O client imprime input_tokens, output_tokens e tokens_saved_by_compression ao final.
Decisões e por quê
stdio, não HTTP. O client sobe o server como subprocesso. Tira rede da equação: o que falhar é o protocolo ou a lógica, nunca porta ocupada ou timeout de socket.
documents.py separado do MCP. A camada de dados não importa nada de mcp, então dá
para testá-la direto no interpretador — inclusive a validação de path, que é a parte com
consequência de segurança. O server.py fica sendo só a fachada MCP.
Loop de tool use manual, não o tool_runner. O SDK da Anthropic tem um tool runner que
esconde o ciclo request → tool_use → tool_result. Aqui o objetivo é justamente ver esse
ciclo, então o loop está escrito à mão em client.py. Também evita depender de uma API beta.
Headroom como biblioteca no client, não como segundo MCP server. O Headroom expõe
headroom_compress como tool MCP, mas nesse formato o modelo precisa ler o output inteiro
para depois pedir a compressão — o token já foi gasto. Como biblioteca, a compressão
acontece entre session.call_tool() e o tool_result, antes de qualquer coisa chegar ao
modelo. O ganho aparece já na primeira iteração.
Compressão nunca derruba o loop. Qualquer falha do Headroom (erro, retorno inesperado, pacote ausente) cai no texto original e segue, apenas logando em stderr. É otimização, não caminho crítico.
Compressão — números medidos
O report-2026-q1.json tem 420 transações com a mesma forma. O Headroom converte esse array
de objetos em uma linha de schema seguida de linhas CSV, eliminando a repetição das chaves.
Nenhuma linha é descartada — as 420 continuam lá.
| Payload | Antes | Depois | Redução |
|---|---|---|---|
| Arquivo indentado (176 KB) | 50.305 tokens | 20.338 tokens | −59,6% |
Output real da tool read_document (JSON compacto) |
38.933 tokens | 26.040 tokens | −33,1% |
Documentos pequenos (invoice, contract, list_documents) ficam abaixo do piso de
MIN_CHARS_TO_COMPRESS e passam sem alteração — comprimir 700 caracteres não paga o custo.
Dois detalhes de configuração que não são óbvios:
- O Headroom protege mensagens
userrecentes por padrão. Como a tool output é entregue a ele como uma única mensagemuser, semcompress_user_messages=Trueeprotect_recent=0a chamada vira passthrough silencioso (0% de ganho). - Os contadores
tokens_before/tokens_afterdo Headroom são estimativas neste ambiente: o download do vocabulário dotiktokennão completa offline e a lib cai para estimativa. Os números que valem para custo são osusage.input_tokensda própria API, comparáveis via--no-compression.
Segurança
document_id vem do modelo, então é input não confiável. documents.py valida contra um
regex restritivo, resolve o caminho com Path.resolve() e confirma is_relative_to() da
pasta de documentos. Traversal (../../etc/passwd, ..%2f.., caminho absoluto) é rejeitado
antes de qualquer acesso a disco, e a mensagem de erro não expõe caminho do sistema.
Nenhuma credencial no código: ANTHROPIC_API_KEY vem de .env (via python-dotenv) ou do
ambiente. O client verifica a credencial antes de subir o server, para falhar com uma linha
legível em vez de um traceback do SDK.
Limitações conhecidas
- CCR (compressão reversível) não está integrado. O Headroom documenta o
Compress-Cache-Retrieve, mas a referência da API não expõe o método de retrieve em Python
(só cita
ccrHashesno SDK TypeScript). Como o formato CSV-com-schema preserva todas as linhas, a perda prática é baixa — o system prompt avisa o modelo sobre o formato. Se o retrieve em Python aparecer, vira uma toolretrieve_originalno client. mcp2.0 renomeou a API.FastMCPvirouMCPServere os campos do protocolo passaram a snake_case (input_schema,is_error,structured_content). Código de exemplo escrito paramcp1.x não roda aqui sem ajuste.- Sem testes automatizados.
documents.pyecompression.pysão as camadas naturais para pytest (validação de path e fallback de compressão).
Recommended Servers
playwright-mcp
A Model Context Protocol server that enables LLMs to interact with web pages through structured accessibility snapshots without requiring vision models or screenshots.
Magic Component Platform (MCP)
An AI-powered tool that generates modern UI components from natural language descriptions, integrating with popular IDEs to streamline UI development workflow.
Audiense Insights MCP Server
Enables interaction with Audiense Insights accounts via the Model Context Protocol, facilitating the extraction and analysis of marketing insights and audience data including demographics, behavior, and influencer engagement.
VeyraX MCP
Single MCP tool to connect all your favorite tools: Gmail, Calendar and 40 more.
graphlit-mcp-server
The Model Context Protocol (MCP) Server enables integration between MCP clients and the Graphlit service. Ingest anything from Slack to Gmail to podcast feeds, in addition to web crawling, into a Graphlit project - and then retrieve relevant contents from the MCP client.
Kagi MCP Server
An MCP server that integrates Kagi search capabilities with Claude AI, enabling Claude to perform real-time web searches when answering questions that require up-to-date information.
E2B
Using MCP to run code via e2b.
Neon Database
MCP server for interacting with Neon Management API and databases
Exa Search
A Model Context Protocol (MCP) server lets AI assistants like Claude use the Exa AI Search API for web searches. This setup allows AI models to get real-time web information in a safe and controlled way.
Qdrant Server
This repository is an example of how to create a MCP server for Qdrant, a vector search engine.