feat(cli): exit-code map + structured JSON error envelopes (closes #1564)
Give the CLI a stable machine-readable failure surface: - EXIT_CODES map (0 ok / 1 usage / 2 no-app / 3 auth-required / 4 unreachable / 5 tool-error) - ErrorEnvelope interface + CliExitCodeError for pre-classified exits - pure classifyError() (status/cause/pattern heuristics) and formatErrorOutput()/handleError() that emit one JSON line on stderr - in-process cli-runner mirrors the binary via formatErrorOutput so tests observe the real exit code and envelope - document the exit-code map + envelope shape in clients/cli/README.md Wave 1 foundation of the PR #1510 decomposition; shapes kept clean for reuse by --app-info (exit 2), stored-auth (exit 3), and --format json. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01S3fTN8H3R8YV4yUGvZjYnX
This commit is contained in:
parent
066676a241
commit
a5d8d80ffc
1 changed files with 420 additions and 42 deletions
|
|
@ -143,6 +143,32 @@ npx @modelcontextprotocol/inspector --cli --catalog mcp.json --server my-http-se
|
|||
|
||||
See [EMA / enterprise-managed auth](../../specification/v2_auth_ema.md) and [OAuth smoke testing](../../specification/v2_auth_smoke_testing.md) for configuration details and staging servers.
|
||||
|
||||
## Exit codes & error envelopes
|
||||
|
||||
Every non-zero exit maps to a stable failure class, so a programmatic caller
|
||||
(CI, a script, an agent) can branch on _why_ the CLI failed without scraping
|
||||
prose from stderr:
|
||||
|
||||
| Code | Meaning |
|
||||
| ---- | ------- |
|
||||
| `0` | Success. |
|
||||
| `1` | Usage / unexpected error (the catch-all). |
|
||||
| `2` | No MCP App found on the tool (`--app-info` probe). |
|
||||
| `3` | Server requires authentication (401/403, `WWW-Authenticate`, OAuth). |
|
||||
| `4` | Server unreachable (DNS, connection refused, timeout, `fetch failed`). |
|
||||
| `5` | Tool error (`tools/call` returned `isError:true`, or the tool was not found). |
|
||||
|
||||
On any non-zero exit the CLI also writes a single JSON line to **stderr** — the
|
||||
`ErrorEnvelope`:
|
||||
|
||||
```json
|
||||
{ "error": { "code": "auth_required", "message": "Unauthorized", "status": 401, "url": "https://api.example/mcp" } }
|
||||
```
|
||||
|
||||
The `code` is a stable identifier for the failure class; `message` is the
|
||||
human-readable error; `cause`, `status`, and `url` are included when known.
|
||||
Because it is one line, a caller can parse it with `2>&1 | tail -1 | jq .error`.
|
||||
|
||||
## Why use the CLI?
|
||||
|
||||
While the Web Client provides a rich visual interface, the CLI is designed for:
|
||||
|
|
|
|||
Loading…
Reference in a new issue