prompt-notebooka working lab notebook · v0.42
Note 039 · 2026-07-01 · 6 min

Tool use, from the model's point of view

Most bugs I've hit in agentic pipelines vanish once I stop asking 'why did the model call the tool wrong?' and start asking 'what did the tool schema actually look like to it?'

The mental shift that made agentic pipelines much less frustrating for me was small. I stopped trying to reason about the model as a black box that mysteriously "should" call the tool correctly, and started imagining what the tool schema actually looked like inside its context. It is a boring, plumbing-level view. It also fixed most of my bugs.

What the model actually sees

When you register a tool, the schema is serialised into the model's context — usually as a JSON blob or a compact function signature. From the model's perspective, that blob is a specification of a function it may call, no more and no less. Everything the model knows about your tool is inside that spec. If the field is not described, it is unknown. If the description says "the user's email," it will fill it with something that looks like a user's email, whether or not that string was ever actually mentioned in the conversation.

The model calls the schema, not the tool.

Three failure modes that are actually schema bugs

1. "It keeps inventing arguments." This is almost always an underspecified field. If your parameter is described as "id: the record id", the model will generate something that plausibly looks like a record id. If the description is "id: the exact record id from the context above. must be a UUID. do not invent.", the model will refuse to call rather than hallucinate. Descriptions are not documentation — they are instructions.

2. "It calls the wrong tool." Usually because two tools have overlapping descriptions. If search_customers says "find customers by name" and lookup_account says "look up an account by name," the model is going to guess, and it will guess wrong for a subset of inputs. Rename them, differentiate the descriptions, add explicit "use this when …" hints.

3. "It calls the tool with the right arguments and then narrates the answer instead of using the tool's response." This is a state-handling bug: the model does not have the tool response in a slot it treats as authoritative. Depending on the framework, you either return the tool response as a properly-typed message the model can see on its next turn, or you're going to have to inject it into the user turn manually.

The "read the prompt as the model sees it" trick

Once per project I print out the fully-serialised prompt as the model receives it: system, user turn(s), tool schemas, retrieved chunks, everything. I read it slowly, out loud if I'm alone. Roughly half the bugs I've had in agentic systems reveal themselves in that read-through: a tool description in the second person ("you should use this"), a schema field with a name that means one thing to me and another to a language model, a system prompt that contradicts itself two hundred tokens later.

This is the single most useful debugging habit I have picked up in the last year, and it requires no tooling at all.

A minimal, boring tool schema I like

{
  "name": "get_order_status",
  "description":
    "Returns the current fulfillment status for a single order. "
    "Use this ONLY when the user has provided an explicit order id. "
    "Do not use this to search for orders by email or name.",
  "parameters": {
    "type": "object",
    "properties": {
      "order_id": {
        "type": "string",
        "description":
          "The exact order id as it appears in the conversation. "
          "Format: 'ORD-' followed by 8 hex characters. "
          "Do not fabricate or reformat."
      }
    },
    "required": ["order_id"]
  }
}

Two things worth stealing from this: an explicit "use ONLY when" clause in the description, and a formatted-example clause in the field description ("Format: …"). Between them, they kill about 80% of the fabrication cases I used to see.

The heuristic I now use

When a tool call goes wrong, my first question is no longer "what did the model do?" It is: "what did the model see?" I look at the schema, the descriptions, and the last few user turns as if I were the model — with only that information, and no wider common sense. It is astonishing how often the bug is right there, in a field description I wrote in three seconds and never looked at again.

One-line takeaway

The schema is the tool. Treat descriptions as prompt copy — because that's exactly what they are.

Get the next note in your inbox

One long note every week or so. Plain text, no tracking pixels, no launch announcements. Unsubscribe with one click.

free · ~2,000 words per note · never any tracking