The Contract
- JSON without asking. When stdout is not a terminal (which is every agent), commands print the exact API response as one JSON line. Errors are JSON envelopes on stderr with stable
codefields and arequestId. - Semantic exit codes.
0success,1API or runtime error,2usage error,3authentication error,4confirmation required,130/143interrupted by SIGINT / SIGTERM. Unknown commands fail hard with no fuzzy “did you mean” to misread. - Never hangs. Nothing waits on stdin unless it is a real terminal, and missing input is an immediate exit 2 with the fix in the message. Every request is bounded, response body included:
--timeout <duration>(90s,1500ms,5m) caps the whole command, retries and pages included, so it fits a tool-call budget. Long-running commands such asemails generatedefault to their own budget. SIGINT or SIGTERM stops the request in flight. - Stable surface. Commands and flags are additive across releases, and the manifest describes the installed build exactly.
Replaying an Unknown Outcome
The API keeps working after the CLI disconnects. So a write that ends inCLI_TIMEOUT, CLI_CONNECTION, CLI_INTERRUPTED or a 5xx may still complete. Its error envelope carries the idempotencyKey it was sent with and a retryCommand that re-runs it with that key, so the API returns the first attempt’s result instead of doing the work twice:
retryCommand; never re-run the original command with a fresh key. A 409 IDEMPOTENCY_IN_PROGRESS means the first attempt is still running (the API holds its key for up to 15 minutes): wait, then run retryCommand again. A read that fails this way changed nothing and simply re-runs.
The replay needs the API’s idempotency store. While it is degraded, the six fail-closed writes refuse with a retryable 503 rather than run unmetered or send twice. Those are send, trigger fire, automation run, automation test, email audit, and inbox placement test; Idempotency lists the routes.
Other writes run without the guarantee. So for a write that must not happen twice (creating a brand, say), pass --max-retries 0, and check whether it landed before you run retryCommand.
The Confirmation Protocol
Irreversible commands (campaign sends, deletes, trigger fires, cancels) do not execute in a non-interactive session. They exit with code 4 and print an envelope:summary to your human, and only run the confirmCommand after they approve. Passing --yes yourself is reserved for actions the user already asked for explicitly. Test sends (emails send --test --to you@example.com) are the safe lane and skip the gate.
Discovery for Agents
brew-cli docs api (the live GET /v1/help catalog) and the served agent guide at https://brew.new/api/v1/llms.txt.
The repo also ships a ready-made skill at skills/brew-cli/SKILL.md that teaches Claude Code and compatible harnesses this whole contract in about fifty lines.
A Typical Agent Session
Need Help?
Our team is ready to support you at every step of your journey with Brew. Choose the option that works best for you:- Self-Service Tools
- Talk to Our Team
Search Documentation
Type in the “Ask any question” search bar at the top left to instantly find relevant documentation pages.
Ask ChatGPT or Claude
Click here to open the Copy page menu at the top of this page, then send the page to ChatGPT, Claude, or your editor.