efficient-api-usage
Cost and latency optimization for Anthropic API usage. Covers prompt caching, batch API, and when to combine them.
Codex または Claude でインストール この Prompt をコピーして Codex、Claude、または他のアシスタントに貼り付けると、Skill ページを確認してインストールできます。
メニュー
Cost and latency optimization for Anthropic API usage. Covers prompt caching, batch API, and when to combine them.
Codex または Claude でインストール この Prompt をコピーして Codex、Claude、または他のアシスタントに貼り付けると、Skill ページを確認してインストールできます。
SOC 職業分類に基づく
Write up research experiments and findings as an interactive, self-contained HTML report published as a claude.ai Artifact, with figures and data exploration. Use when creating a research report from experiment results.
How to write a comprehensive research report for your supervisor summarizing experiment findings, hypothesis tests, and data exploration. Use when you need to communicate results from multiple experiments with proper analysis, visualizations, and interactive data exploration.
How to send notifications to the human supervisor via ntfy.sh. Use when you need input, hit a blocker, or update them on your progress.
Standard experiment folder structure and templates. Reference for creating or validating experiment folders.
Read model outputs, samples, or log entries by eye and report specific observations about what's in them. Use when asked for a "qualitative" read/analysis, or when the goal is to understand WHAT is in the data rather than count patterns. Not for numerical summaries, metric computation, or classifier-driven sweeps.
How to evaluate research samples using structured JSON output from claude -p. Covers criteria writing, the core judging pattern, and practical examples.
| name | efficient-api-usage |
| description | Cost and latency optimization for Anthropic API usage. Covers prompt caching, batch API, and when to combine them. |
Caches the KV representations of prompt prefixes so repeated requests with shared context skip re-processing.
How it works:
cache_control breakpoint where the prefix is identicalcache_control at the boundary between stable context and variable content"ttl": "1h" for 1-hour duration (value must be a string: "5m" or "1h")Pricing (relative to base input cost):
Break-even: 5-min TTL pays off after 2 requests (1.25× + 0.1× = 1.35× vs 2× uncached). 1-hour TTL needs 3+ requests (2× + 0.2× = 2.2× vs 3× uncached). Pick 1h only when you expect the prefix to be reused enough times to amortize the doubled write cost.
Limits and silent failures:
cache_control breakpoints per request.cache_creation_input_tokens: 0.f"Today is {datetime.now()}")json.dumps(d) without sort_keys=True — Python dict iteration order can shift the bytesset or filtered conditionally)cache_read_input_tokens stays 0 across runs you expect to hit, diff the rendered request bodies — one of these is almost always the cause.Two modes:
response = client.messages.create(
model="claude-sonnet-4-6",
max_tokens=1024,
system=[
{
"type": "text",
"text": "<large stable context>",
"cache_control": {"type": "ephemeral"},
}
],
messages=[{"role": "user", "content": "variable question"}],
)
response = client.messages.create(
model="claude-sonnet-4-6",
max_tokens=1024,
cache_control={"type": "ephemeral"},
system="<large stable context>",
messages=[{"role": "user", "content": "variable question"}],
)
Verifying cache behavior — check response.usage:
cache_creation_input_tokens > 0 → cache miss, wrote to cachecache_read_input_tokens > 0 → cache hitProcesses requests asynchronously at 50% of standard pricing. Most batches complete in <1 hour, max 24 hours.
Limits: 100k requests or 256 MB per batch, whichever comes first.
When to use: any workload that doesn't need real-time responses — evals, bulk classification, data analysis, content generation.
With structured outputs (output_config.format.json_schema): all object types in the schema must have "additionalProperties": false. This is an API-level requirement (not batch-specific).
from anthropic.types.message_create_params import MessageCreateParamsNonStreaming
from anthropic.types.messages.batch_create_params import Request
batch = client.messages.batches.create(
requests=[
Request(
custom_id=f"request-{i}",
params=MessageCreateParamsNonStreaming(
model="claude-sonnet-4-6",
max_tokens=1024,
messages=[{"role": "user", "content": question}],
),
)
for i, question in enumerate(questions)
]
)
| Scenario | Real-time needed? | Shared prefix? | Strategy | Discount vs base |
|---|---|---|---|---|
| Chat / interactive | Yes | Yes (system prompt) | Prompt caching | ~90% on cached input |
| Chat / interactive | Yes | No | Standard API | None |
| Bulk eval / analysis | No | Yes | Batch + caching | 50% base + ~90% on cached input |
| Bulk eval / analysis | No | No | Batch only | 50% |
The discounts stack. Include identical cache_control blocks in every request within the batch.
Caveat: batch requests are processed concurrently and asynchronously, so cache hits are best-effort (typically 30-98% hit rate). To maximize hits:
shared_system = [
{
"type": "text",
"text": "<large shared context>",
"cache_control": {"type": "ephemeral", "ttl": "1h"},
}
]
batch = client.messages.batches.create(
requests=[
Request(
custom_id=f"request-{i}",
params=MessageCreateParamsNonStreaming(
model="claude-sonnet-4-6",
max_tokens=1024,
system=shared_system,
messages=[{"role": "user", "content": q}],
),
)
for i, q in enumerate(questions)
]
)