Field notes
Shipping a production MCP server
Writing an MCP server takes an afternoon. Writing one that agents use correctly takes a week of tool design.
MCP won because the alternative was writing the same integration four times for four clients. Standing up a server that responds correctly takes an afternoon. Standing up one that agents use correctly, without thrashing, is a week of design work, and almost all of that week goes into tool shape.
This site runs one, at the same domain you are reading, so the notes below are from something live rather than from a sample repository.
Design the tool surface first
Before writing code, write the list of tool names and one-line descriptions. If you cannot describe a tool in one sentence without "and", it is two tools. If two descriptions sound similar, the model will pick the wrong one at some point and you will spend a day confused about why.
- Name for intent, not implementation.
find_customer_by_emailbeatsdb_query. - Prefer specific over flexible. Flexible tools shift the burden of correctness onto the model, which is exactly backwards.
- Ten is a lot. Beyond that, group by domain and consider separate servers rather than one sprawling surface.
- Write descriptions for a smart stranger. Include when not to use the tool. That line does more work than any other.
Inputs and outputs are a contract
Validate every input with a real schema at the boundary and reject early with a message that tells the caller how to fix it. Agents recover well from precise errors and badly from vague ones.
On the way out, three rules have saved me repeatedly:
- Stable shape, always. Same fields on success and failure, with an explicit status. Shape-shifting responses cause hallucinated field names.
- Cap size and say so. Return the first N results plus the omitted count and a hint for narrowing. Unbounded returns eat the context window and the agent loses the task.
- Errors as data, not exceptions.
{ status: 'not_found', hint: '...' }'lets the agent adapt. A stack trace makes it retry blindly.
Resources and prompts, the underused half
Most servers only ship tools. Resources let a client read reference material without spending a tool call, and prompts let you ship the correct usage pattern along with the capability.
On this site's server, static positioning and bio content are resources while contact submission is a tool. That split keeps read-only material out of the agent's decision loop, which is both cheaper and less error-prone.
Transport, auth, and the security floor
Local stdio servers inherit the trust of the machine. Remote servers do not, and a remote MCP server is a public execution surface with a friendly protocol on top.
- Scoped tokens per client, revocable, never long-lived shared keys.
- Per-token tool allowlists, so a read-only integration cannot reach a write tool even by mistake.
- Rate limits per token and per tool, with clear 429 semantics.
- Audit log of every call with caller, arguments, and outcome. This is your only forensic record.
The full model, including per-user consent and irreversible-action gating, is in MCP server security and auth.
Performance: cache like the caller is impatient
Agents call the same tools repeatedly within a run, often with identical arguments. Without caching you pay for that in latency and in provider load.
- Short-lived response cache keyed on tool plus normalized arguments. Even 30 seconds removes most duplicate work.
- Longer cache for genuinely static resources, with an explicit invalidation path.
- Aggressive timeouts. A tool that hangs is worse than a tool that fails, because the agent has no signal to act on.
The bug was not in the server. Two tools had descriptions that overlapped by one clause, and the agent picked the wrong one about a fifth of the time.
Testing at three levels
- Unit. The functions behind the tools, tested normally. Boring and essential.
- Protocol. Assert the tool list, input schemas, and error shapes. This is your compatibility contract with every client, and it should fail loudly on any accidental change.
- Behavioral. Give a real agent a task and assert which tools it chose. This is the only layer that catches ambiguous descriptions, which is the most common real defect.
Behavioral tests belong in the same suite as everything else in LLM evals that actually catch regressions.
Versioning without breaking clients
You do not control the clients. Assume old agents will call your server for a long time.
- Additive changes are safe. Renames and removals are not.
- To change a tool's behavior, add a new tool and mark the old one deprecated in its description.
- Never repurpose an existing field name. Add a new one and let the old one go quiet.
The checklist I use before calling one done
- Ten or fewer tools, each describable in one sentence.
- Schema validation and instructive errors on every input.
- Capped, stable-shaped responses with explicit status.
- Scoped tokens, allowlists, rate limits, audit log.
- Caching plus timeouts on everything external.
- Protocol tests and at least five behavioral tests.
- A deprecation path documented before the first client integrates.
If you want an MCP server designed and shipped against your systems, that falls under custom AI agent development. If you have one already and it behaves oddly, tool-surface review is part of the production readiness audit.
Frequently asked
What is an MCP server?
A Model Context Protocol server exposes tools, resources, and prompts over a standard protocol so any compatible AI client can use them. Write the integration once and Claude, Cursor, and other clients can all call it.
How many tools should an MCP server expose?
Fewer than you want to. Every tool competes for the model's attention and for context space. Ten sharply defined tools beat forty overlapping ones. If two tools have similar descriptions, the model will pick wrong.
How do you test an MCP server?
Three layers. Unit tests on the underlying functions, protocol tests that assert schemas and error shapes, and behavioral tests where a real agent is given a task and you check that it selects the right tools.
Should an MCP server be remote or local?
Local over stdio for developer tooling that touches a machine. Remote over HTTP for anything multi-user or backed by shared data, which then needs real auth, rate limits, and audit logging.
Want this shipped in your stack?
The $1,000 AI audit gets you a ranked action plan in 48 hours.
90-minute live review of your workflows, agents, retrieval, permissions, evals, costs, and observability. Fee credits toward the build.

Written by
Alex Cinovoj, TechTide AI
Founder and CTO of TechTide AI, a Columbus, Ohio AI-automation agency, and co-host of the Automation Vibes podcast. 13 years of mixed IT across support, systems, cloud, architecture, and engineering, with the last 2 years on AI implementation. Lovable Champion and community leader, and has completed Anthropic Academy courses in Agent Engineering, Claude Code, MCP, and Context Engineering.