An interactive, opinionated walkthrough of how to wire up Claude — from the surface you touch
(Claude Code: auth, model, settings.json) down to the
Anthropic API it sits on (keys, request config, thinking, effort, caching). Builders generate
copy-paste config; callouts flag the 400-errors before you hit them.
Claude Code is a client for the Anthropic API. Authenticating Claude Code and authenticating a raw API call resolve credentials the same way — first match wins. Pick how you want to authenticate and the builder shows the setup and the precedence note.
ANTHROPIC_API_KEY → ANTHROPIC_AUTH_TOKEN →
ant auth login profile → cloud-provider credentials. A stale exported ANTHROPIC_API_KEY
silently overrides an ant profile and your /login session — truly unset it
(an empty "" still wins its slot). In Claude Code, run /status to see which method is active.
settings.json. Use
.claude/settings.local.json (git-ignored) for anything machine-specific.
Default to Claude Opus 4.8 (claude-opus-4-8) unless you have a reason not to.
Use the bare alias verbatim — never append a date suffix (e.g. claude-opus-4-8, not
claude-opus-4-8-20251101); a wrong ID 404s.
| Model | ID (use this) | Context | Max out | $ / 1M in→out | Use for |
|---|---|---|---|---|---|
| Claude Opus 4.8 ★ default | claude-opus-4-8 | 1M | 128K | $5 → $25 | Most agentic / coding / hard reasoning |
| Claude Sonnet 4.6 | claude-sonnet-4-6 | 1M | 64K | $3 → $15 | Best speed/intelligence balance |
| Claude Haiku 4.5 | claude-haiku-4-5 | 200K | 64K | $1 → $5 | Fast, cheap, simple tasks |
| Claude Opus 4.7 | claude-opus-4-7 | 1M | 128K | $5 → $25 | Prev-gen Opus (pin if needed) |
| Claude Fable 5 | claude-fable-5 | 1M | 128K | $10 → $50 | Most capable; hardest long-horizon work |
/model — interactive picker inside a session.claude --model claude-opus-4-8 — per-invocation flag."model": "claude-opus-4-8" in settings.json — persistent default.ANTHROPIC_MODEL env var — overrides for the shell.client.models.retrieve("claude-opus-4-8") → .max_input_tokens,
.capabilities[...]. The table above is a snapshot.settings.jsonClaude Code reads layered settings files, most-specific wins:
| File | Scope | Commit it? |
|---|---|---|
~/.claude/settings.json | User — all your projects | n/a (personal) |
.claude/settings.json | Project — shared with the team | Yes — check it in |
.claude/settings.local.json | Project — just you, this machine | No — git-ignored |
| Managed (enterprise) | Org-deployed, highest precedence | Admin-controlled |
.claude/settings.json (team) or ~/.claude/settings.json (personal).
permissions.allow/deny use tool-matcher syntax; deny always beats
allow.hooks entry in settings.json (the harness runs it),
not a model instruction. Common events: PreToolUse, PostToolUse, Stop./v1/messagesEverything Claude Code does is ultimately a call to the Messages API. Here's the client init and the knobs that matter, then a builder that assembles a real call.
# pip install anthropic — reads ANTHROPIC_API_KEY / ANTHROPIC_AUTH_TOKEN / ant profile from anthropic import Anthropic client = Anthropic() # no args: resolves credentials from the environment
// npm install @anthropic-ai/sdk import Anthropic from "@anthropic-ai/sdk"; const client = new Anthropic(); // resolves from env
curl https://api.anthropic.com/v1/messages \ -H "x-api-key: $ANTHROPIC_API_KEY" \ -H "anthropic-version: 2023-06-01" \ -H "content-type: application/json" \ -d '{ ... }'
16000 non-streaming; ~64000 when streaming. Stream for anything over ~16K or you'll hit SDK HTTP timeouts.thinking: {type:"adaptive"}. Claude decides depth itself; interleaves between tool calls. (On Opus 4.7/4.8/Fable 5 this is the only thinking mode — a fixed budget_tokens 400s.)output_config: {effort: "low"|"medium"|"high"|"xhigh"|"max"}. Default high. xhigh is the sweet spot for coding/agentic work."omitted" (empty thinking text). Set "summarized" if you surface reasoning to users.cache_control: {type:"ephemeral"} on the stable prefix; ~0.1× reads. Prefix-match: any byte change invalidates everything after it.tools:[...] with name / description / input_schema; the description is the highest-leverage field.thinking: {type:"enabled", budget_tokens: N} returns 400. Use thinking: {type:"adaptive"}
and control depth with output_config.effort.temperature, top_p, top_k all 400. Steer with the prompt instead.role:"assistant" turn 400s. Use output_config.format (structured outputs) or a
system instruction to shape output.max_tokens. Use .stream() +
.get_final_message() / .finalMessage().thinking:{type:"disabled"} 400s (omit thinking entirely), and the org must allow
30-day data retention (ZDR orgs 400 on every request). Handle stop_reason:"refusal" before reading
content.| Code | Type | Retry? | Usual cause |
|---|---|---|---|
| 400 | invalid_request_error | No | Bad params, removed field, non-alternating roles |
| 401 | authentication_error | No | Missing/invalid key, or both API key + auth token set |
| 404 | not_found_error | No | Typo'd / date-suffixed model ID |
| 429 | rate_limit_error | Yes | RPM/TPM exceeded — SDK backs off automatically |
| 529 | overloaded_error | Yes | Temporary capacity — retry with backoff |