oc-claude-api — independently scanned and version-tracked by SaferSkills.
SaferSkills independently audited oc-claude-api (Agent Skill) and scored it 96/100 (green). The audit ran 55 deterministic rules across Security, Supply Chain, Maintenance, Transparency, and Community; it found 0 high-severity and 1 lower-severity findings. The full rule-by-rule trace and per-finding evidence are below. Free, methodology-open.
Findings & checks · 1 flagged
The text {match} tells the agent to skip the normal "ask the user first" gate. Used adversarially it removes the human-in-the-loop check before destructive or sensitive actions, turning a normally-gated agent into a fire-and-forget executor.
Every scanned point with the score it earned and what moved between them.
First recorded scan — no prior version to compare against.
The primary manifest — the file an agent reads to learn what this artifact does.
On first invocation, read `references/orchestrator.md` and follow its welcome protocol.
First-party harness for building, debugging, and optimizing applications on the Claude API / Anthropic SDK. Owns model routing, prompt caching (on by default), tool-use design, batch/streaming patterns, and version-migration playbooks. Apps built or touched through this skill ship prompt caching from the first commit and carry token-ceiling guardrails per phase.
This is the Claude-in-the-loop counterpart to the rest of the pipeline. If you're building an LLM feature — a chatbot, an extraction pipeline, an agent, an LLM judge — this skill owns the request layer: which model, how it's cached, how tools are wired, and how the code moves when a model version bumps. It does not own agent topology or harness loops (that's oc-agent-forge), retrieval (oc-rag-forge), or prompt versioning + eval datasets (oc-prompt-ops). It owns the Claude API surface those skills build on.
Accuracy contract. Model IDs, prices, parameters, and breaking changes in this skill and its reference docs are sourced from the Claude Code built-inclaude-apiskill (when present), not from memory. It is not bundled with opchain. When in doubt about a model ID, a price, a beta header, or a deprecated parameter, invokeclaude-apirather than inventing one; if it is not installed, query the Models API (client.models.list()/client.models.retrieve(id), seereferences/model-routing.md§ Live capability lookup). The most recent models are Fable 5 (claude-fable-5), Opus 4.8 (claude-opus-4-8), Sonnet 4.6 (claude-sonnet-4-6), and Haiku 4.5 (claude-haiku-4-5).
APP-ARCHITECT (planning) TRI-DEV (building)
Phase 2: Spec ──"AI app?"──▶ oc-claude-api model-routing decision tree
│ routing → checkpoint key_decisions;
│ app-architect folds it into
│ 11-ai-architecture.md
▼
oc-agent-forge (topology/loop) ──reads model routing──┐
oc-rag-forge (retrieval) ──reads model routing──┤
oc-prompt-ops (eval/versioning)──reads model routing──┘App-architect auto-invokes oc-claude-api in Phase 2 when the discovery interview flags an AI app — triggers are "AI app", "agent", "chatbot", "LLM in the loop", "summarize/extract/classify with a model", "Claude", "Anthropic". The decision tree runs, picks the per-phase model, and records the routing in this skill's checkpoint; app-architect reads it back into 02-architecture.md and 11-ai-architecture.md. The user doesn't call /oc-claude-api separately for new projects — but they can invoke it directly to migrate, audit caching, design tools, or set cost guardrails on existing code.
Model routing is owned here and read by siblings. oc-agent-forge decides subagent topology and tool budgets but reads this skill's per-task model choice; oc-rag-forge reads it for the answer-synthesis model; oc-prompt-ops reads it to pin the model its eval datasets run against. Siblings read it where the checkpoint protocol lets them: the routing decision appended to this skill's context_primer.key_decisions (per-phase model + effort), and 11-ai-architecture.md once app-architect has assembled it. skill_state below is private working state, not the shared surface.
CLAUDE API COMMANDS
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
BUILD / DEBUG
/oc-claude-api Design or debug a Claude API integration
/oc-claude-api tool-use Schema-first tool-use patterns (defer-load, parallel)
OPTIMIZE
/oc-claude-api cache-audit Audit prompt-cache hit rate (target ≥ 60%)
/oc-claude-api cost Token-ceiling + per-phase cost guardrails
LIFECYCLE
/oc-claude-api migrate Migrate code across model versions → diff PR
/checkpoint Show checkpoint status
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
Type any command to begin. /oc-claude-api to see this again.The first decision on any Claude API task is which model per phase. Default toward capability, drop to cheaper tiers only when the task is genuinely simple or high-volume. Read references/model-routing.md for the full table; the shape:
What is this call doing?
│
├─ Spec authoring, architecture, code audit, migration, hard reasoning,
│ long-horizon agentic work
│ └─▶ claude-opus-4-8 (the default for intelligence-sensitive work)
│ └─ most demanding / overnight autonomous runs → claude-fable-5
│
├─ Build, reverse-spec, codegen, balanced agentic loops, tool-heavy work
│ └─▶ claude-sonnet-4-6 (best speed/intelligence balance)
│
└─ Cheap repetitive phases: classification, routing, extraction, label-gen,
high-volume summarization
└─▶ claude-haiku-4-5 (fastest, cheapest; 200K context)Routing principles
to claude-opus-4-8 for anything intelligence-sensitive and surface a cheaper option, don't impose it.
mid-conversation invalidates the cache. For a cheaper sub-task, spawn a subagent on the cheaper model (Haiku) rather than swapping the main loop's model.
claude-sonnet-4-6,not claude-sonnet-4-6-20251114). Pull IDs from references/model-routing.md.
output_config.effort (low→max; xhigh on Opus 4.7/4.8) and adaptive thinking (thinking: {type: "adaptive"}). budget_tokens is removed on Fable 5 / Opus 4.8 / 4.7 (400) and deprecated on 4.6.
Every integration this skill builds ships prompt caching from the first commit — not as a later optimization pass. Prompt caching is a prefix match: any byte change anywhere in the prefix invalidates everything after it. Get the prompt assembly order right (stable content first, volatile content last) and most caching works for free.
What to cache, in render order (tools → system → messages):
datetime.now(), no per-user IDs, no conditionalsections interpolated into it. Inject dynamic context later in messages.
breakpoint at the end of the shared span, before the varying question.
cache_control: {type: "ephemeral"} gives a 5-minute TTL (ttl: "1h" for bursty traffic). Max 4 breakpoints per request. Verify with usage.cache_read_input_tokens — zero across repeated identical-prefix requests means a silent invalidator is at work. Full placement patterns, cost math, and the silent-invalidator audit checklist live in references/prompt-caching.md.
/oc-claude-api cache-audit — target ≥ 60% hit ratecache-audit traces the prompt-assembly path, classifies every input by stability, checks rendered order matches stability order, and reports the cache hit rate against a ≥ 60% target. Output:
## Prompt Cache Audit
### Hit rate
- cache_read / (cache_read + cache_creation + input): 41% ← BELOW 60% TARGET
### Silent invalidators found
| Location | Pattern | Fix |
|---|---|---|
| system prompt header | `f"Current date: {datetime.now()}"` | Move to a user-turn message |
| tools=build_tools(user) | tool set varies per user | Freeze + sort deterministically |
### Breakpoint placement
- system block: present, but invalidated upstream by the date interpolation
- Recommended: 1 breakpoint on last (frozen) system block; 1 on last shared-context block
### Verdict: FAIL — fix the two invalidators, re-auditThree patterns, schema-first throughout. Full code shapes in references/tool-use.md.
tool description is prescriptive about when to call, not just what it does ("Call this when the user asks about current prices"). Recent Opus models reach for tools conservatively — trigger conditions in the description give measurable lift. Use strict: true on the tool definition (with additionalProperties: false + required) to guarantee inputs validate.
defer_loading: true and add a tool_search_tool_regex_20251119 / _bm25_20251119 tool. Claude searches and loads only the relevant schemas. Schemas are appended, not swapped — the prompt cache survives. Never defer every tool (400) — the search tool and at least one real tool stay loaded.
tool_useblocks. Execute concurrently and return all tool_result blocks in a single user message — splitting them across messages silently trains Claude to stop calling tools in parallel. A failed tool returns tool_result with is_error: true — don't drop it.
Prefer the SDK's tool runner (client.beta.messages.tool_runner / toolRunner) for the loop unless you need human-in-the-loop approval, custom logging, or conditional execution — then use the manual agentic loop.
/oc-claude-api migrateMoves existing Claude API code across model versions (4.6 → 4.7 → 4.8, Mythos Preview → Fable 5) and replaces retired models. Produces a diff PR, not a silent in-place rewrite. Full per-target breaking-change checklists in references/migration-playbooks.md.
The flow is fixed:
file list, ask before editing — "migrate my codebase" / "upgrade to Sonnet 4.6" is ambiguous (what, not where). Never start editing on an ambiguous scope.
registries, capability gates, and test fixtures need different handling (add alongside vs. swap vs. regenerate). See the classification table in the playbook.
[BLOCKS] items (e.g.budget_tokens → adaptive thinking, strip temperature/top_p/top_k, remove last-assistant-turn prefills) are code edits; [TUNE] items (effort, prompt re-tuning) are recommendations.
API or behavioral shift that motivates it.
oc-prompt-ops: /oc-prompt driftre-runs the frozen goldset against the new pinned model before merge, then open the PR via oc-git-ops. If oc-prompt-ops is not installed, run the project's own test suite plus a hand-picked golden sample (a weaker gate than /oc-prompt drift: no frozen baseline, no per-case delta) and put the result in the PR body; if oc-git-ops is not installed, open the PR with gh pr create and the same body.
response.model.startswith(target)./oc-claude-api costSets and enforces token ceilings per phase so an LLM feature can't run away with spend. Levers, cheapest-first:
~16000 (under SDK HTTPtimeouts); streaming default ~64000; classification ~256. Lowballing truncates mid-thought and forces a retry — the opposite of cheap.
single biggest cost lever on repeated-context workloads.
work to Sonnet, reserve Opus/Fable for the phases that need them.
sees a running countdown and self-moderates. Distinct from max_tokens, which is an enforced ceiling the model doesn't see.
Live cost ops are `oc-cost-ops`./oc-claude-api costsets static per-phase ceilings and records them in this checkpoint; it does not track live spend. Attributed spend, budgets and the cost-regression gate are/oc-cost attribute,/oc-cost budgetand/oc-cost gate(oc-cost-ops reads this skill's price table + model IDs).
| Skill | Relationship |
|---|---|
oc-app-architect | Auto-invokes this skill in Phase 2 on AI apps; reads the routing back into 11-ai-architecture.md |
oc-agent-forge | Owns agent topology + harness loops; reads this skill's model routing |
oc-rag-forge | Owns retrieval; reads model routing for the answer-synthesis call |
oc-prompt-ops | Owns prompt versioning + eval datasets; /oc-prompt drift eval-gates migrate diffs before merge |
oc-stack-forge | Recommends the overall stack; this skill owns the Claude request layer within it |
oc-integrations-engineer | Owns third-party API auth |
oc-code-auditor | Audits the request layer for unparsed tool inputs, missing refusal handling, leaked keys |
oc-cost-ops | Owns attributed spend, budgets and the cost-regression gate; reads this skill's price table + model IDs. This skill sets static ceilings only |
oc-git-ops | Opens the migration diff PR (via its pre-PR gate: oc-docs-forge docs packet → oc-repo-ops readiness) |
Boundary: this skill owns the Claude API request surface — model choice, caching, tool wiring, streaming/batch, migration. It does not own agent topology, retrieval, prompt eval, or third-party auth. Siblings own those and build on the request layer this skill defines.
The shared checkpoint schema, write rules and resume protocol live in references/checkpoint-protocol.md, bundled with this skill. This section adds only what is specific to oc-claude-api.
{project-dir}/.checkpoints/oc-claude-api.checkpoint.json
| Event | What to Save |
|---|---|
| Model routing decided | Per-phase model map + effort levels, appended to context_primer.key_decisions (the sibling-readable copy) |
| Caching wired | Breakpoint placement, measured hit rate |
| Cache audit run | Hit rate, invalidators found, verdict |
| Tools designed | Tool count, strict/defer-load/parallel flags |
| Migration run | Source/target model, files touched, breaking-change items applied, PR link |
| Cost ceilings set | Per-phase max_tokens, batch/cache decisions |
{
"model_routing": {
"spec": "claude-opus-4-8",
"build": "claude-sonnet-4-6",
"classify": "claude-haiku-4-5"
},
"caching": { "breakpoints": 2, "hit_rate": 0.71, "ttl": "5m" },
"tools": { "count": 6, "strict": true, "defer_load": false, "parallel": true },
"last_migration": {
"from": "claude-opus-4-7",
"to": "claude-opus-4-8",
"files": 4,
"blocks_applied": 1,
"pr": "https://github.com/org/repo/pull/123"
},
"cost": { "max_tokens_default": 16000, "batch": false, "task_budget": null }
}first commit. A frozen system prompt and deterministic tool order are architectural decisions, not afterthoughts.
cache away. Spawn a cheaper subagent instead of swapping the main loop's model.
claude-opus-4-8for intelligence-sensitive work and surface cheaper options — never silently route to Haiku to save money.
the model when to call, not just what the tool does. Parse tool inputs as JSON, never raw-string-match.
the most common bug — verify against the built-in claude-api skill, or the Models API when it is absent.
the breaking-change checklist, eval-gate, explain every edit, then open a PR.
path is the correctly-sized one plus caching, not a starved ceiling.
refusal, pause_turn,max_tokens, and model_context_window_exceeded are real branches — reading content[0] unconditionally breaks on refused or paused turns.
references/model-routing.md — per-task/phase model selection with a decision tablereferences/prompt-caching.md — cache_control usage, what to cache, TTL, hit-rate mathreferences/tool-use.md — schema-first design, tool_choice, parallel calls, defer-loadreferences/migration-playbooks.md — step-by-step model-version migration → diff PR~30 seconds. Free. No account. Every finding cites a rule and a line of evidence.