MCP Resources Are For Caching

MCP Resources Are For Caching

If your MCP client doesn’t support resources, it is not a good client.

There! I said it!

It’s because MCP resources are for improved prompt utilization, namely cache invalidation. Without resources, you eat through your context and token budget faster than Elon at a drug store. And so if your client doesn’t support it, you basically can’t do RAG with MCP. At least not in a way that anyone would consider production worthy.

RAG documents are BIG

You don’t want to duplicate files. See this here:

system prompt
user message with tool definitions
agent message with tool calls
user message with tool call results
giant file 1
giant file 2
another agent message with tool calls
user message with tool call results
giant file 2
giant file 3
...

That’s 2 tool calls. The second one contains a duplicate file.

Is this bad? If your answer is “no” then this blog post isn’t going to resonate with you.

Separate results from whole files

The core of it: A well-implemented app, MCP or not, will keep track of the documents returned from a RAG query and avoid duplicating them in the prompt. To do this, you keep a list of resource IDs that you’ve seen before (sure, call it a “cache”).

Format the RAG tool response in the prompt like so:

<result uri="rag://polar-bears/74.md" />
<result uri="rag://chickens/23.md" />

<full-text uri="rag://chickens/23">
Chickens are...
</full-text>

In other words:

  1. The return value of the function, to the LLM, is an array of resources
  2. The full text is included elsewhere, for reference

URIs are useful as a cache key.

btw I’m just spitballing what the prompt format should be for returning results. You can play around with it, you might already have strong opinions. The point is, mapping must be done.

MCP is not LLM-readable

There’s been a lot of discussion about if LLMs can interpret OpenAPI fine, and if so, why use MCP. That misses the entire point. MCP isn’t supposed to be interpreted directly by an LLM.

When you implement an MCP client, you should be mapping MCP concepts to whatever works for that LLM. This is called implementing the protocol. If you throw vanilla MCP objects into a prompt, it could actually work. But a good client is going to map the results to phrases & formats that particular LLM has gone through extraordinarily expensive training to understand.

MCP is a protocol

MCP standardizes how tools should return their results. MCP resources exist so that tools (e.g. RAG search) can return files, and client can de-duplicate those files across many calls.

Yes, it’s cool that you can list a directory, but that’s not the primary purpose of resources. Without resources, your LLMs just eat more tokens unnecessarily.

(Side note: did you notice that neither Anthropic nor OpenAI supports resources in their APIs? It’s a conspiracy..)

Resources are table stakes MCP support

If a client doesn’t support MCP resources, it’s because they don’t care enough to implement a proper client. Period.

While I’m at it, prompts are just functions with special handling of the results. Might as well support those too.

Discussion