Where tools run
A mental model for hosted vs. self-hosted (MCP) vs. inline tools — and what happens, machine by machine, when a smith calls a tool from a web app, a chat surface like Telegram, or email.
The one idea. A tool is just a function — call it
execute(). Two questions decide everything else: who calls that function, and over what wire. Ingram Cloud always runs the model; the model only ever asks for a tool. What turns that ask into a real action is something — sometimes Ingram Cloud, sometimes your own server — invokingexecute().
Three separate layers
"Who runs the tool?" resolves into three questions with three different answers:
- Runs the model — decides a tool should be called. This is always Ingram Cloud; the LLM lives there. Your code never runs inference.
- Runs
execute()— runs the tool's actual code. For a hosted tool it's Ingram Cloud; for your tool it's always your server. - Does the side-effect — the real-world action (the SMTP send, the API
write). Usually a third party (an email/SMTP provider, a SaaS API) that
execute()calls.
The word "hosted" only describes layer 2. And there are exactly two kinds of tool:
- Hosted by Ingram Cloud — e.g.
web_search,web_fetch. Ingram Cloud implements and runs them end-to-end. You write no code; your server never hears about the call. - Your tools (self-hosted, via MCP) — e.g.
send_email, calendar/contacts actions. The code is yours and always runs on your server. The only question is how the request reaches yourexecute()— over your/mcpendpoint, or inline in your own loop.
Explore it live
Pick an entry point (row) and a tool kind (column), then step through the
trace. Watch the ★ — that's the exact moment execute() runs, and on whose
machine. The summary table and the MCP-vs-inline panel below the explorer load
straight into it.
execute() here? Your `/mcp` endpoint — Ingram Cloud reached your server over HTTP to invoke the tool. IC is the trigger; your endpoint is the caller.execute() runsThe whole model on one page — click any row to load it above.
| Entry point + tool | Runs the model | Runs execute() | Side-effect |
|---|---|---|---|
| Web → send_email (MCP) | Ingram Cloud | your /mcp (HTTP from IC) | External service |
| Web → send_email (inline) | Ingram Cloud | your agent loop (in-process) | External service |
| Web → web_search (hosted) | Ingram Cloud | Ingram Cloud | Ingram Cloud |
| Telegram → send_email (MCP) | Ingram Cloud | your /mcp (HTTP from IC) | External service |
| Telegram → web_search (hosted) | Ingram Cloud | Ingram Cloud | Ingram Cloud |
| Email channel → reply (your key) | Ingram Cloud | — (no tool of yours) | Email provider, sent by IC |
MCP vs. inline — when to choose which
Reach for MCP (IC calls your /mcp)
- The tool must work on a channel or schedule — inline doesn't exist there.
- It's shared across many entry points, or needs approval / human-in-the-loop gating.
- You want Ingram Cloud to drive the whole run; you just expose an endpoint.
- Cost: you host an HTTP endpoint IC can reach; identity arrives as headers.
Reach for inline (you drive the loop)
- The run already starts in your own server process (a web app you host).
- The tool lives in-process — you want zero extra hops and no shared secret.
- You want full control of the agent loop and don't need IC to gate.
- Limit: only where your code drives the loop — never on channels.
Rule of thumb: if a channel or a schedule can trigger it, it has to be MCP. If your own server is always the one driving the run, inline is the shortest path.
Deployments have no inline path
Ingram Cloud drives deployment runs, so the inline path doesn't exist there: a
self-hosted tool must go through /mcp. Anything you want available on a
deployment has to be reachable as an MCP tool.
The one exception: an email deployment. Because Ingram Cloud owns the deployment address and holds the email-provider key you configured for it, IC originates that outbound call on your behalf — see the Email deployment scenario in the explorer.
Identities on MCP calls travel as headers — the run's smith (X-IC-Smith-Id)
and your stable end-user id (X-IC-Smith-External-Id) — which is how your /mcp
endpoint knows who it's acting for. See Tools & approvals for the
full auth model.