MCP and CLIs: how agents reach the world
Hosts, clients and servers; tools, resources and prompts; stdio or HTTP; and when a good CLI is all you need.
Meer Habib
Senior Mobile Engineer · Chittagong
An agent is only as useful as the tools it can reach. There are two common ways to give it more: a command-line tool it can run in a shell, and an MCP server it can connect to. They solve the same problem in different ways, and knowing which to build saves a lot of work.
The CLI: the tool agents already know
Coding agents have a shell. Anything with a good command-line interface is already a tool:
gh pr list --state open --json number,title
eas build --platform ios --profile preview
psql -c "select count(*) from notes"CLIs work well for agents when they follow a few habits:
--helpthat explains itself. The agent reads it the same way a new engineer would.- Machine-readable output, like a
--jsonflag, so results can be parsed instead of guessed. - Clear exit codes and errors that say what went wrong and what to try.
- No interactive prompts. An agent can't answer "Are you sure? (y/n)". Offer a
--yesflag. - Quiet by default. Short output keeps the context clean.
If your product already has an API, a small CLI in front of it is often the fastest way to make it usable by agents.
MCP: a standard plug
The Model Context Protocol is an open standard for connecting AI apps to tools and data. Instead of every app writing its own integration for every service, a service writes one MCP server, and any MCP-capable app can use it.
The pieces:
- Host: the app with the model in it, like Claude Code or an IDE.
- Client: the connection the host keeps to one server.
- Server: your program. It says what it offers, and does the work when asked.
A server can offer three kinds of things:
- Tools: actions the model can call, like
create_frameorrun_query. - Resources: data the app can read into context, like a file, a schema or a document.
- Prompts: ready-made instructions a user can pick, like "review this pull request".
Under the hood it's JSON-RPC: small JSON messages like "list your tools" and "call this tool with these arguments". It runs over two transports:
- stdio: the host starts your server as a local process and talks through its input and output. Simple and private, and ideal for tools that work on the user's machine.
- HTTP: the server runs remotely, which suits services with accounts, like a hosted database or an issue tracker.
Adding a local server to Claude Code is one line:
claude mcp add shelf -- npx tsx ./mcp/server.tsWhich one should you build?
| Situation | Build |
|---|---|
| The agent works in a terminal already, and the action is one command | A CLI |
| You want many AI apps, not just coding agents, to use it | An MCP server |
| The tool needs to show the model rich data or documents | An MCP server, with resources |
| You want the fastest possible first version | A CLI, then MCP later |
They aren't rivals. Shelf has both: a CLI for scripts and quick use, and an MCP server so agents can drive the full set of actions with proper descriptions.
Designing tools either way
The rules from how agents work apply to both:
- One tool, one job, with a name that says what it does.
- Descriptions that say what comes back, not just what goes in.
- Short results; offer a way to ask for more.
- Errors the model can act on: "frame not found; call list_frames to see valid IDs" beats "error 404".
- Destructive actions are explicit, and ideally reversible.
Building something like this?
Booking new projects for Q4. Replies within 24h.