OpenClaw Agents CLI Guide: agents add, bind, Routing Precedence, and the Second-Agent Trap
With one agent, every inbound message has an obvious home. Add a second and some of them stop going anywhere.
The pages that rank for openclaw agents split into two kinds. The official multi-agent routing doc runs to roughly 5,500 words and covers everything from WhatsApp DM splits to per-agent Memory Wiki vaults. The CLI reference page is a short flag list. A third-party note condenses the routing order into about 550 words. All three explain what an agent is, list the binding priority, and show agents add followed by agents list --bindings. None of them walks through the afternoon you actually live through: a working single-agent install, one new agent, and a Telegram chat that quietly goes unanswered. That transition is the angle here, after the commands themselves.
What agents add actually creates
An agent in OpenClaw is a separate brain on the same Gateway. It gets its own workspace for AGENTS.md, SOUL.md, and notes, its own state directory for auth profiles and model config, and its own session store. The defaults, per the docs:
Workspace
~/.openclaw/workspace-<agentId> for every agent except the default one, which keeps ~/.openclaw/workspace.
Agent directory
~/.openclaw/agents/<agentId>/agent, holding openclaw-agent.sqlite with that agent's sessions and credentials.
Never point two agents at the same --agent-dir. The docs are blunt about it: auth and session state collide. Also know that the workspace is only the default working directory. Absolute paths still reach the rest of the disk unless you turn on sandboxing, which the sandbox guide covers per agent.
Adding an agent from a script
openclaw agents add research \
--workspace ~/.openclaw/workspace-research \
--model <model-id> \
--bind telegram:research \
--non-interactive --json--non-interactive wants a name, and it wants --workspace unless you pass --role instead. Roles seed a template: coordinator, researcher, writer, or reviewer.
The trap is the Gateway state. Plain non-interactive creation needs the local Gateway running, while interactive setup and role-based creation need it stopped, so a provisioning script that adds one blank agent and then one --role reviewer agent has to stop the Gateway between the two calls or one of them fails, and it will not be the one you expect if you wrote the script from memory.
If you want the whole set at once, openclaw agents team create builds a coordinator and three specialists, each in its own workspace, with the coordinator's subagents.allowAgents pointing at them.
The three shapes of --bind
Bindings decide which agent receives a message. The flag takes channel[:accountId], and the three spellings behave differently:
openclaw agents bind --agent research --bind telegram:research # one account
openclaw agents bind --agent chat --bind whatsapp:* # every account
openclaw agents bind --agent main --bind discord # the "default" account onlyThe last one surprises people. A binding with no account id matches the literal account key default, and nothing else on Discord. If you later add a second Discord bot under its own account id, the bare binding does not cover it.
The wildcard is a fallback. An explicit telegram:research beats telegram:* no matter which was added first.
Undo with openclaw agents unbind --agent research --bind telegram:research, or --all to strip every binding from that agent. Check the result with openclaw agents bindings.
Routing precedence
The Gateway picks the most specific match. The tier order from the routing docs, highest first: exact peer, parent peer, peer wildcard, guild plus roles, guild, team, account, channel, and finally the fallback owner. Inside a single tier, the first binding in config order wins.
The CLI flag only reaches the account and channel tiers. Peer bindings (sending one WhatsApp group, or one person's E.164 number, to a different agent) live in the bindings array in config, with a match.peer object of kind and id. You edit those with the tools from the config CLI guide, then run openclaw config validate before restarting anything.
{
agentId: "family",
match: { channel: "whatsapp", peer: { kind: "group", id: "1203630xxxx@g.us" } }
}The second-agent trap
On a one-agent install nobody configures an owner, because there is only one candidate. The docs spell out what happens once there are two: a message that matches no binding is not handed to the first agent in the list. It sits undispatched until a binding matches or a fallback owner resolves.
So the chat that worked yesterday, the one you never bound because it never needed binding, goes silent. No error in the chat. The openclaw message CLI starts asking you to pick a System Agent for the same reason.
My order of operations, every time, before running agents add on a box that already has a working agent:
openclaw agents list --bindings
openclaw config set agents.defaults.systemAgent.agentId main
openclaw agents bind --agent main --bind telegram:*Bind the existing agent explicitly, name it the System Agent, then add the newcomer with narrower bindings so its explicit accounts outrank the old wildcard. If you upgraded from an older multi-agent config, openclaw doctor --fix converts the legacy implicit routing into channel-wide bindings and explicit owners; the Gateway doctor guide explains what else that flag touches.
Credentials do not all follow you
Interactive agents add copies only portable static credentials, meaning api_key and static token profiles. OAuth profiles stay behind unless the profile is marked copyToAgents: true. When a secondary agent's OAuth refresh fails, it reads through to the auth-inheritance owner's credential for the same profile id and takes whichever token is fresher. Convenient. It also means two agents can quietly share one subscription login, so if the research agent must bill to a different account, sign in from that agent directly. The secrets guide has the storage side.
Identity
openclaw agents set-identity --agent research --from-identity reads name, emoji, theme, and avatar out of the agent's IDENTITY.md, local avatar files are capped at 2 MB and cannot point outside the workspace, and if you are unsure what belongs in that file the workspace files guide goes through it.
Deleting an agent
openclaw agents delete research is gentler than it sounds. The workspace and session directories go to the Trash rather than being erased. Before that, the command closes terminals, cancels background work, and waits up to 15 seconds for active runs to drain. If cleanup fails partway, the agent is already gone from config while its files linger as pending cleanup. Fix the error it printed and run the delete again.
Before deleting, run openclaw agents bindings --agent research and note what it owned. If it held the only binding for a channel, you are back in the unrouted-message situation above.
Common failure modes
Old chat stopped answering after agents add
It matched no binding and there is no fallback owner. Bind it explicitly and set agents.defaults.systemAgent.agentId.
New bot account routes to the wrong agent
A bare --bind discord only covers the default account. Bind the new account id explicitly.
An agent shows as degraded
Its database belongs to another agent, usually a copied or reused agentDir. Follow the database recovery steps, then restart the Gateway.
Provisioning script fails on the second add
Role-based creation needs the Gateway stopped; plain non-interactive creation needs it running.
Final verdict
Bind the agent you already have before you create the one you want. The routing docs describe the undispatched-message rule in one sentence, and it is the sentence I would tattoo on a new install. Once the routing is explicit, the multi-agent orchestration guide picks up where agents start delegating to each other.
Ready to build?
Get the OpenClaw Starter Kit — config templates, 5 production-ready skills, deployment checklist. Go from zero to running in under an hour.
$14 $6.99
Get the Starter Kit →Also in the OpenClaw store
Get the free OpenClaw quickstart guide
Step-by-step setup. Plain English. No jargon.