Lesson 8 · Domain 2 — Tool Design & MCP Integration (18% of exam)

Tool Descriptions & Structured MCP Errors

Domain 2 is about the interface between Claude and the systems it calls. The two ideas in this lesson both come down to the same principle: the model can only act as well as the information you give it — about which tool to pick, and about what went wrong when one fails.

Descriptions are the selection mechanism

Not the tool's name. Not its internal implementation. The description is what the model actually reads to decide which tool fits a given request. Minimal or near-identical descriptions across similar tools produce unreliable routing — not because the model is confused, but because it genuinely doesn't have enough information to differentiate.

The official guide's sample question is a clean illustration: get_customer ("Retrieves customer information") and lookup_order ("Retrieves order details") — both minimal, both accepting similar identifier formats. The agent frequently calls get_customer when a user asks about an order. The fix isn't infrastructure. It's expanding each description with input formats, example queries, edge cases, and explicit boundaries — telling the model when to use this tool versus the similar one next to it. Few-shot examples, a routing layer, or consolidating both tools into one are all more effort than the situation calls for as a first move.

Fix the description before you build infrastructure
This is the Domain 2 version of Domain 1's "hooks vs. prompts" lesson, aimed the other direction: don't reach for a routing classifier or a merged mega-tool when the actual gap is a couple of missing sentences in a description. Infrastructure is the right call eventually — just not the first call.

Structured errors: give the agent something to act on

MCP tool failures set isError: true. What matters is everything else in that response. A generic { isError: true, message: "Operation failed" } tells the calling agent nothing — should it retry? Ask the user? Give up? Structured metadata answers that:

interface McpToolError {
  isError: true;
  errorCategory: "transient" | "validation" | "permission" | "business";
  isRetryable: boolean;
  message: string; // human-readable, safe to relay to the user
}

// Bad — the caller can't decide anything from this
return { isError: true, message: "Operation failed" };

// Good — the caller knows exactly what to do next
return {
  isError: true,
  errorCategory: "business",
  isRetryable: false,
  message: "Refund exceeds the $500 policy limit for automated approval.",
} satisfies McpToolError;

errorCategory distinguishes transient failures (timeouts, unavailability — worth retrying) from validation errors (bad input — retrying won't help), permission errors, and business-rule violations (like the refund limit above — never retryable, needs a different path entirely). isRetryable makes that explicit rather than implied, preventing wasted retry attempts on errors that can't succeed no matter how many times you try.

One more distinction: failure vs. nothing found

A search that legitimately returns zero matches is not an error — it's a successful query with an empty result. Conflating "the tool couldn't run" with "the tool ran and found nothing" removes information the agent needs to respond correctly (retry a broken call vs. tell the user honestly that nothing matched).

Why this matters beyond the exam

Primary source: the Model Context Protocol specification defines the isError pattern and tool description conventions directly — this lesson compresses Task Statements 2.1 and 2.2.

Check your understanding

Q1. get_customer and lookup_order have minimal, nearly identical descriptions, and the agent frequently calls the wrong one for order questions. What's the most effective first fix?
Q2. A tool call fails and returns only { isError: true, message: "Operation failed" }. What's wrong with this response?
Q3. A search tool returns zero matches for a well-formed, valid query. How should this be represented?

Want to draft a tool description for something you're actually building, and stress-test whether it's specific enough? Share it and I'll help sharpen it.