Blog · 2026-05-18

MCP needs a process, not a lambda

MCP clients assume the server is still there for the next call. Why per-request serverless breaks that, and what an always-on process changes.

MCP assumes your server is still there for the next call. A serverless function assumes the opposite: it spins up per request, answers, and forgets everything in between. Those two models do not fit, and the mismatch is why MCP servers on per-request platforms produce broken sessions, dropped streams and slow tool chains. The fix is not cleverer code, it is a different runtime shape: one process that stays up.

Why do MCP sessions break on serverless?

A Model Context Protocol session is a conversation, not a one-off request. The client connects, negotiates capabilities in an initialize handshake, lists your tools, and then keeps calling them over the same session, often dozens of times as an agent works through a task. Three things go wrong when each of those steps lands on a function that was born for that request:

  • Torn-down transports. MCP transports can be long-lived: stdio pipes, or an HTTP connection the server holds open to stream. A per-request platform recycles the instance when the response ends, so the connection the client is counting on is gone mid-session, and the client sees a broken transport rather than a clean answer.
  • Per-request state loss. Anything the server kept in memory, session context from the handshake, a warm cache, an open connection to a backing API, evaporates between invocations. The next call may land on a fresh instance that has never seen this client.
  • Cold starts, multiplied. An agent does not make one request, it makes a chain of them. Every cold start adds its latency to a single link in that chain, and a ten-tool-call task pays the toll ten times. The user experiences this as an assistant that thinks in slow motion.

None of this is a defect in serverless platforms. They are built for stateless request handling and are good at it. MCP simply is not that workload.

What does an always-on slot change?

On DenkOps, an MCP server runs in one always-on slot: a process that starts once and keeps running. That single property resolves all three failures. There is no cold start, because the process is already warm when the next tool call arrives. The transport is not torn down underneath the client, because nothing is recycled between requests. And in-memory state survives from one call to the next, so caches stay warm and connections stay open. For state that must also survive redeploys, the slot mounts a durable disk at /persist, covered in state that survives redeploys.

Doesn't stateless streamable HTTP solve this?

It helps, and the DenkOps SDK uses it: servers built with defineMcp speak stateless streamable HTTP, POST-only at /mcp, so any MCP client that supports remote servers can connect without the server holding a stream. But statelessness at the protocol layer does not change the runtime economics underneath. A per-request platform still pays a cold start per call in the worst case, still gives your handlers nowhere to keep a warm cache or a pooled connection, and still cannot host the many MCP servers that do hold sessions or streams. A stateless protocol on top of an always-on process gives you both halves: maximum client compatibility, and a runtime that is simply there.

If you want to feel the difference rather than read about it, deploy the starter: one file, one command, and every tool call after the first hits a process that never left.

FAQ

Does an MCP server need to stay running between tool calls?

Usually yes. An MCP server holds a session, over stdio or a long-lived HTTP connection, rather than answering one-off requests. On an always-on slot the process just keeps running, so there is no cold start and no risk of the transport being torn down mid-session the way it can be on a per-request serverless function.

Can I host an MCP server on a serverless function at all?

Sometimes, if the server is fully stateless and the client tolerates the latency. But you inherit cold starts on every link of an agent's tool-call chain, you lose all in-memory state between invocations, and any transport the server needs to hold open can be recycled mid-session. An always-on process removes that whole failure class.

What is an always-on slot on DenkOps?

A slot is a process that starts when you deploy and stays up: no scale-to-zero, no per-request recycling. Your MCP endpoint at `https://<slug>.denkops.host/mcp` is served by that warm process, with a durable `/persist` disk for state that must outlive redeploys.

Ship it yourself: bunx denkops deploy or say "deploy on DenkOps" from your coding agent.

Start on DenkOps →

← Ship a backend from Claude Code · Give your agent memory with denkops.store →