Claude Academy
Sign in

MCP Advanced Topics · lesson 3 of 4

Tool Design Principles

The single biggest predictor of agent quality is tool design, not model choice. The cert tests this hard.

1. Make tools obvious

  • One tool, one job. If a tool's description has "or" in it, split it.
  • Name the tool by verb + object: search_tickets, not tickets.
  • Description = a teacher's note: "Use this when... Don't use this when..."

2. Constrain inputs

  • Use enums for fixed vocabularies.
  • Require only the fields that must be present. Optional > required.
  • Default values reduce hallucination.
  • Validate at the boundary — return clear errors if input is invalid.

3. Return structured, focused output

  • Prefer JSON or short structured text over walls of prose.
  • Include only what Claude needs to make the next decision.
  • Long blobs → return a resource URI Claude can fetch if needed.
  • Include provenance (IDs, timestamps) so Claude can refer back.

4. Idempotency & safety

  • Mark destructive tools with destructiveHint: true.
  • Mark idempotent tools with idempotentHint: true — Claude can retry without fear.
  • For non-idempotent writes (sending a message, charging a card), require a confirm: true argument and a user confirmation in the host.

5. Errors are first-class

  • Return is_error: true with a useful message — Claude reads errors and adapts.
  • Distinguish:
    • User error (bad input) → "ValidationError: customer_id must be UUID"
    • Transient (network, rate limit) → "TransientError: retry after 5s"
    • Permanent (resource gone) → "NotFoundError: ticket 1234 deleted"
  • Never raise an unstructured exception that bubbles up as a stack trace — the model can't reason about that.

6. Composability

Design tools so Claude can chain them:

  • find_customer → returns customer_id
  • get_customer_orders → takes customer_id
  • refund_order → takes order_id, requires confirm

This is more flexible than one mega-tool find_and_refund(query).

7. Limit blast radius

  • Read tools should be safe defaults.
  • Write tools should be narrow (create_ticket not modify_anything).
  • Sensitive ops (delete, transfer, refund) should require explicit confirmation flow.

8. Test descriptions like prompts

Description quality drives tool-selection accuracy. Iterate:

  • Run 20 sample queries through Claude with your tool list.
  • Track which queries triggered the right tool.
  • Edit descriptions where it picked wrong; re-run.

CCA-F cheatsheet

BadGood
do_stuffupdate_ticket_status
"Handles tickets""Update a ticket's status field. Use when the user confirms moving a ticket to a new state."
args: {...freeform}Typed schema with enums and required fields
Raises Python exceptionReturns {is_error: true, code: "...", message: "..."}
Returns 20KB JSON dumpReturns top fields + a resource URI for details

See also