AI Agent Tool Calling: An Interface Design Guide for Getting Models to Use the Right Tools

Design Agent tools like an API for an engineer who can't ask questions — clear definitions fix more bugs than prompt tuning.
The article argues that Agent problems like calling the wrong tool, fabricating arguments, and endlessly retrying often stem not from the model but from the tool design itself. The model can only see the tool's name, description, and input schema — that's the entire contract. The author recommends writing descriptions like onboarding docs, using consistent verb_noun naming, limiting and merging tools, letting schemas carry constraints, trimming output, and writing error messages that explain the next step. You also need idempotent writes, read/write separation, hard limits in code, and a test set of 20–50 real requests to systematically fix issues.
Title
AI Agent Tool Calling: An Interface Design Guide for Getting Models to Use the Right Tools
Meta Description
The root cause of AI Agent tool-calling failures often isn't the model — it's the tool interface design. This article lays out practical design principles across six dimensions — tool descriptions, naming conventions, schema constraints, output trimming, error messages, and testing methods — to get models to use the right tools.
Article Content
Slap a few tools onto your Agent, write a decent system prompt, run a few test requests — everything looks fine. Then real users show up, and the problems surface: when it should be calling get_order, it picks search; where it should pass an order ID, it fills in a customer name; it retries the same failing call five times in a row; and after stuffing a 40,000-token API response into the context, it completely forgets what the user asked.

Most people's first instinct is to blame the model, or pile more instructions into the system prompt. But the real problem is usually the tools themselves. The model knows nothing about your system — all it can see is the three things you give it: the name, the description, and the parameter schema. If those three things are vague, overlapping, or too noisy, the model can only guess — and it guesses with total confidence.
The core thesis of this article: design your tools as an interface for the model, the same way you'd design an API for an engineer who can't ask you any questions.
What a Tool Actually Looks Like to the Model
No matter what framework you use, a tool ultimately arrives at the model as three fields: name, description, and input schema. That's the entire contract.
The model can't see your implementation code, your database structure, or the comments you left in the code. The entire basis for deciding "when to call this tool and what arguments to pass" is those few lines of definition. Write these definitions as the most important documentation in the project, because to the Agent, they genuinely are.
Function Calling / Tool Calling mechanics: This is the underlying capability of modern LLM Agents. The model itself can't execute any code — it only outputs a structured JSON blob during inference, declaring "which function I want to call and what arguments to pass," which the external runtime (the Agent framework) parses and actually executes, then feeds the result back to the model as a new message. This means the model's entire "world knowledge" at the moment of the call comes only from the tool definition; it can't query your code or database to correct its understanding. Precisely for this reason, the tool's name, description, and schema effectively play the role of "prompt" — they are the most direct and most trusted context for the model's decision, often higher in priority than generic instructions in the system prompt. Understanding this makes it clear why refining definitions is more effective than piling on prompts.
Write Tool Descriptions the Way You'd Write Onboarding Docs
A good tool description answers four questions: what it does, when to use it, when not to use it, and what it returns.
Compare these two approaches:
search: Searches for things.
search_help_articles: Full text search over the public help center.
Use it for general "how do I" questions about product features.
Do not use it to look up a specific customer, order or invoice;
use get_order or get_customer for those.
Returns up to 5 articles with title, url and a short snippet.
The second is longer, but that's completely fine. Descriptions cost far less than a wrong call. The line "don't use it for X" is the one people skip most often, yet it's precisely the line that prevents the most errors, because it tells the model where the boundary lies between two similar tools.
Naming matters just as much. search and lookup sitting side by side is a coin flip. search_help_articles and get_order_by_id are not confusing. Use a consistent verb_noun pattern, and avoid two names that could reasonably be understood as the same thing.
Fewer Tools, Clearer Boundaries
Every additional tool raises the model's decision difficulty by a notch. An Agent with 40 tools has to scan 40 descriptions at every step, and the odds that two of those tools overlap in function climb fast.
A few practical rules:
- Merge tools that differ by only one parameter. Instead of keeping
get_open_orders,get_closed_orders, andget_cancelled_orders, build a singlelist_orderswith astatusenum field. - Don't map your REST API one-to-one. Your API was designed for frontend code that knows exactly what it needs. Agents are better served by task-oriented tools, like a single
find_customerthat accepts an email or name, rather than five low-level endpoints that must be chained together correctly. - Split out tools that do genuinely different things. A single
manage_usertool with anactionfield that canread,update, ordeleteis hiding a destructive operation behind an innocuous-sounding name. Separate outdelete_userso you can describe it clearly and require approval.
If you find yourself writing a long paragraph in the system prompt about "which tool to use in which situation," that's a signal the tools themselves need clearer boundaries.
Let the Schema Do the Constraining
The input schema is your best line of defense against garbage arguments. Every constraint you put in the schema is one the model doesn't need to remember from prose. A well-designed schema should:
- Use enums instead of free text. If the schema only allows four values, the model can't invent a status called "pending."
- Specify format and source in the description. A note like "get this from find_customer, never guess" stops the model from fabricating plausible-looking IDs.
- Mark only genuinely required fields as required. If a simple call demands the model fill in five required fields, it will make up values for the ones it doesn't know.
- Set reasonable limits. Adding a
maximumtolimitprevents a single call from returning thousands of rows.
Even so, you still need to validate in your own code. The schema only guides the model; it provides no guarantees. Check arguments in the tool implementation, reject bad ones, and return a clear message.
Structured output and JSON Schema constraints: Most tool-calling interfaces use JSON Schema to describe parameters, and mainstream models have seen a huge number of schemas during training, so they have a strong tendency to follow keywords like enum, type, required, and maximum. But note that the strength of a schema's constraint depends on whether the vendor has enabled "constrained decoding" — some APIs force the model to output JSON conforming to the schema, while others merely use it as a hint. So enums greatly reduce (but do not entirely eliminate) the probability of the model fabricating values. This is also why the original article stresses "you still need to validate in your own code": the schema is probabilistic guidance, while server-side validation is the deterministic line of defense — the two cannot substitute for each other.
Return Only What the Model Needs, Not Everything You Have
Tool output goes straight into the model's context. A tool that returns the full API response — with nested metadata, internal IDs, and 200 fields per record — burns tokens and buries the useful parts.
Shape the output for the model's next decision. Human-readable values like "2 x Blue T shirt" and "49.90 EUR" are easier for the model to reason about than raw cents and nested arrays, and easier to relay back to the user. For list-type tools, return a short summary of each item plus a way to fetch details, and note in the output that results were truncated, e.g. "note": "showing 5 of 132, narrow with status". Otherwise the model will think it saw everything.
Error Messages Are Instructions
When a tool fails, the error message is the model's only basis for deciding what to do next. A stack trace or a bare 400 Bad Request gives it nothing, so the model can only retry the same call or give up.
Write error messages as if for a junior engineer. Two elements make them work: the message explains in plain language what went wrong, and it says what to do instead. A single line like "Do not retry" cuts out a whole class of loops where the Agent keeps hammering a tool that will never succeed.
These errors should be returned to the model as ordinary tool results for it to read, not thrown as exceptions that crash the Agent loop. Reserve real exceptions for cases the model can't fix, like a database being down.
Idempotency: In distributed systems, idempotency means the same operation produces the same effect whether executed once or many times. It's especially critical for Agents, because model retries are the norm — network timeouts, context misunderstandings, unclear error messages all trigger duplicate calls. If create_refund isn't idempotent, a single retry could refund a customer twice. A common approach is to have the caller pass an idempotency key; the server records that the key has already been processed and returns the original result for duplicate requests without actually re-executing. Payment APIs like Stripe use this pattern. When designing Agent write tools, any operation involving money, inventory, or any irreversible external change should include an idempotency key by default, and expose it explicitly to the model as a field in the schema.
Design for the Errors That Will Inevitably Happen
Even with excellent tool design, the model will sometimes call the wrong tool, or call the right tool twice. Plan ahead:
- Make write operations idempotent where possible. Accept an idempotency key on
create_refundso a duplicate call doesn't refund twice. - Separate reads from writes. Read tools can run freely. Write tools that touch money, data, or any external change should go through an approval step, or at minimum require a confirmation field.
- Put hard limits in code, not in prompts. A line in the system prompt saying "never refund more than 100 euros" is just a suggestion. The same check inside
create_refundis a rule.
Test Tools the Way You Test Code
Whether a tool is well designed can't be judged by reading the code — only by watching the Agent use it.
Build a set of real requests, 20 to 50 to start, each annotated with the tool call you expect. Have the Agent run these requests, and log every tool call and its arguments. Then look for patterns:
- Wrong tool selected: overlapping descriptions, or a missing "do not use for" note.
- Fabricated arguments: a field that shouldn't be required, or a description that doesn't say where the value comes from.
- Repeatedly failing calls: an error message that doesn't tell the model what to do next.
- Long, meandering execution: output that's too large, or an Agent that needs too many small tools to complete one task.
Change one tool at a time and rerun the test set. It's the same loop as any other test suite, and it's the fastest way to turn "the Agent is flaky" into specific fixes.
Key Takeaways
The ceiling on a model's precision is the precision of the tools you give it. Clear names, descriptions that say when not to use them, schemas with enums and real constraints, compact output, and error messages that explain the next step will fix more Agent bugs than any amount of prompt tuning. Design your tools as an API for someone who can't ask you questions — because that's exactly who's using them.
One-line Summary
Design Agent tools like an API for an engineer who can't ask questions — clear definitions fix more bugs than prompt tuning.
Paragraph Summary
The article argues that Agent problems like calling the wrong tool, fabricating arguments, and endlessly retrying often stem not from the model but from the tool design itself. The model can only see the tool's name, description, and input schema — that's the entire contract. The author recommends writing descriptions like onboarding docs, answering what it does, when to use it, when not to, and what it returns; using a consistent verb_noun naming pattern to avoid confusion; limiting the number of tools, merging tools with overlapping boundaries, and avoiding one-to-one REST API mappings. Schemas should carry the constraint burden, using enums, format notes, and sensible required fields to prevent garbage arguments. Tool output should be trimmed to the information the model needs for its next decision, and error messages should clearly explain the problem and the alternative. You also need to design for failure — idempotent writes, read/write separation, hard limits in code — and systematically identify and fix issues with a test set of 20–50 real requests.
Related articles

Huberman's Rational Supplement Guide: A Five-Layer Health Framework and Scientific Decision-Making
Stanford neurobiology professor Huberman proposes a rational supplement framework: behavior and nutrition are the foundation, basic combination supplements serve as insurance, and sleep/hormonal/cognitive directions should stick to single-ingredient experiments. Omega-3 is the top single-ingredient choice, and melatonin is not recommended.

The Unsung Painter Behind Gilded Age Manhattan Interior Design
HN discussion highlights the painter behind Gilded Age Manhattan interiors: he created murals and decorative paintings but was long overlooked as his work was seen as architectural appendage.

Can AI Agents Be Socially Engineered? Understanding Prompt Injection and Tool Permission Risks
Through Invariant Lab's GitHub Issue injection and Brave's AI browser attack, this article analyzes how Prompt Injection induces AI Agents to perform unauthorized actions, and offers protection advice across three layers: least privilege, tool validation, and operation auditing.