Stateless and Read-Only by Design
What is a stateless MCP server?
A stateless MCP server holds no session state between requests. Each call is self-contained, so any server instance can answer it, the fleet scales flat behind a plain load balancer, and nothing about you carries between calls. Bassethound is stateless by design. Every sniff_domain call is one self-contained, read-only request.
Best move: pick a stateless MCP server when you want an endpoint that scales flat and where no call depends on the one before it.
Why it works: a stateless server derives its whole response from the request in hand, so any instance can answer any call. No sticky sessions, no server-side memory, no cleanup.
Key takeaways
- A stateless MCP server holds no session state between requests. Each JSON-RPC call is self-contained.
- The MCP Streamable HTTP transport supports both stateful operation (an Mcp-Session-Id session) and stateless operation. The server chooses.
- Statelessness lets any instance answer any request, so you scale horizontally behind a plain load balancer with no sticky routing.
- Stateless and stores-nothing are different claims. Stateless is about session lifetime, storage is about persistence, and a server can be both.
- Bassethound is a stateless remote MCP server. One sniff_domain call is one self-contained, read-only request that returns the whole five-layer dossier.
What does “stateless” mean in the MCP protocol?
MCP runs JSON-RPC 2.0 over a transport. For remote servers that transport is Streamable HTTP: the client POSTs requests to one endpoint. The spec allows a server to be stateful or stateless. A stateful server hands back an Mcp-Session-Id at initialize and expects every later request to carry it, holding your context in memory between calls. A stateless server skips that. It treats each POST as a complete unit of work, deriving its whole response from the request body in hand. No session to establish, none to resume, none to expire. The client can still hold conversation state on its side. The server just refuses to. This is the property HTTP itself was built on. Each request stands on its own, and the server needs no memory of what came before to answer it. Statelessness is a server choice, not a protocol gap. The MCP transport supports both modes, and a server declares its stance by whether it issues and requires a session id.
Why does statelessness let a remote MCP server scale?
When no instance holds session state, any instance can answer any request. Put ten servers behind a load balancer and route each call to whichever is free. No sticky sessions, no session-affinity rules, no shared session store to keep instances in sync. A server can crash mid-fleet and take nothing with it, because it was holding nothing. Cold starts are cheap. A fresh instance is ready the moment it boots, with no session cache to warm. Scaling down is just as clean. Drain an instance and no caller loses a session, because there was no session to lose. Contrast the stateful path. Sticky routing pins a client to one instance, a crash drops that client’s context, and horizontal scale needs a shared session backend that becomes its own bottleneck and failure mode. Stateless trades server-side convenience for operational flatness, and for a read-only enrichment endpoint that trade is one-sided.
What can a stateless MCP server not hold onto?
Be honest about the limit. A stateless server has no memory across calls, so it cannot build context incrementally the way a stateful session can. It will not remember your previous query, accumulate a working set, or run a long server-side task tied to a session id you poll. It cannot push a server-initiated notification to a session, because it keeps no session to push to. Anything the agent needs to correlate has to come back inside one response, or the agent host has to hold that context itself. For an enrichment tool this shapes the design rather than breaking it. If a single call returns everything correlated, the agent never needs the server to remember. That is why fusion matters here: one sniff_domain call returns five correlated layers together, so no second call depends on the server recalling the first. The constraint is real. The design routes around it.
How does statelessness tighten security and trust?
A server that carries nothing from one request to the next has little to leak. No session store means no session tokens to steal, no cross-request state to poison, no accumulated caller data sitting warm in memory. The server judges each call on its own contents, which shrinks the attack surface to the request in front of you. Read-only compounds this. The server observes public domains and returns a report; it writes nothing on your side and mutates nothing on the target. Statelessness also underwrites the keyless model. Because the server owns the crawl and holds no per-caller session, one sign-in is enough to meter you, and there is no API key to provision and store for each caller. You bring no secret, so there is no secret to protect. The honest answer to “what do you keep about my calls?” is that nothing carries between them and your results are stored against your account, which the privacy policy governs.
How is Bassethound stateless in practice?
Bassethound is a remote MCP server at mcp.bassethound.ai/mcp exposing one tool, sniff_domain(domain, profile). Every call is a complete unit of work. You pass a domain and a profile (fast, standard, or deep), Digby sniffs the target, and the server returns the full five-layer dossier in that one response: tech stack, infrastructure, firmographics, AI-readiness, and security, fused into a top-level summary. Nothing carries to the next call. The server issues no session and requires none. Because the dossier is correlated in a single payload, the agent never has to make a second call that depends on the server remembering the first. Connect any host that speaks MCP (Claude, Cursor, ChatGPT), and each request stands alone. The free tier rate-limits with no key. The paid tier adds OAuth for depth and volume without changing the stateless shape.
Bassethound perspective
Stateless reads like a limitation on a slide, and every stateful enrichment pipeline will tell you so. We think the opposite, and the tell is in the call count. A stateful enrichment session pins you to an instance, opens a cursor, and streams state you have to manage on both ends. It sells that ceremony as sophistication. We serve one self-contained call that returns five correlated layers, and an agent that never has to ask the server what it said last time. Correlation belongs in the response, not in a session. Once it lives there, the session is dead weight. It adds sticky routing, a shared state store, and a fresh failure mode, and buys the agent nothing a single fused payload does not already give it. Statelessness is not the thing we gave up to ship faster. It is the property that lets one call scale flat and stay free of any key of yours. Competitors reaching for stateful richness are optimizing the wrong axis. Depth belongs in the dossier, not in the session.
Sources
- Model Context Protocol specification: https://modelcontextprotocol.io/specification
- Model Context Protocol: https://modelcontextprotocol.io
- MDN Web Docs, An overview of HTTP: https://developer.mozilla.org/en-US/docs/Web/HTTP/Overview
- IETF RFC 9110, HTTP Semantics: https://datatracker.ietf.org/doc/html/rfc9110
Frequently asked questions
Is a stateless server the same as one that keeps no records?
Close but not identical. Stateless describes session lifetime: the server keeps no context between requests. Stores-nothing describes persistence: the server writes nothing to disk or a database. A server can be stateless yet log requests, or stateful yet ephemeral. Bassethound is stateless and read-only: it holds no context between calls, and it does persist your results against your account.
Can a stateless MCP server still handle multi-step work?
Yes, but the steps live on the client side. The agent host holds the conversation and decides what to call next, while each server call stays self-contained. For enrichment, a single call that returns everything correlated removes most of the need for server-held steps in the first place.
Does MCP require sessions?
No. The MCP Streamable HTTP transport supports sessions via the Mcp-Session-Id header, but a server can operate without them. Whether a server is stateful or stateless is its own decision, not a protocol mandate.
Is Bassethound stateless?
Yes. Bassethound is a stateless, read-only remote MCP server. Every sniff_domain call is one self-contained request that returns the full five-layer dossier. Nothing carries between calls. Your results are stored against your account.
What are the downsides of a stateless MCP server?
It cannot build context across calls, run long server-side sessions you poll, or push session-scoped notifications. The client carries any state that must persist. For a read-only enrichment endpoint that returns correlated results in one call, that tradeoff costs little and buys flat scaling and a clean trust story.