Skip to content

⚡ Claude Token Optimization2026-06-12 — security-guard #4813

Description

@github-actions

Target Workflow: security-guard

Source report: #4810
Est. cost/active run: ~$0.94 (avg 194K tokens, claude-sonnet-4-5)
Est. cost/all runs (amortized): ~$0.33/run (65% are zero-cost early-exit noops)
Cache read/write rate: N/A — per-turn breakdown unavailable (single aggregate in logs)
LLM turns: avg 1.2 across all runs; bimodal: 2 (simple) vs 4–5 (complex)

Current Configuration

Setting Value
Model claude-sonnet-4-5
Tools loaded github: with toolsets: [pull_requests, repos]
GitHub MCP tools actually called None — agent uses bash gh pr diff/view/api instead
Pre-agent steps Yes (3: fetch diff, fetch PR metadata, pass relevance count)
Max turns 6
Prompt size ~5.5 KB instructions + up to 100 KB pre-fetched diff
Early-exit noop rate 65% (11/17 runs; 0 tokens)

Bimodal Run Pattern

Pattern Runs Tokens Turns Est. Cost
2-turn simple review 3 ~122K avg 2 ~$0.59/run
4–5-turn complex review 3 ~263K avg 4–5 ~$1.26/run
Zero-token noop 11 0 0 $0.00

Root cause of multi-turn explosion: Each turn re-sends the full growing context as input (Anthropic charges per-turn input). A 5-turn run sends ~375K cumulative input tokens vs ~110K for 2-turn — 3.4×. The tool_usage log confirms agents make prohibited bash fetches in complex-diff runs despite the existing instruction:

bash_gh pr view 4797  → run #4000 (274K, 5-turn failure)
bash_gh pr diff 4797  → run #4000 (274K, 5-turn failure)
bash_gh pr view 4783  → run #3985 (264K, 5-turn success)
bash_gh pr diff 4784  → run #3991 (262K, 4-turn success)

Recommendations

1. Strengthen the no-bash-fetch constraint (highest impact)

The existing prohibition is buried mid-prompt. Move it to the top as a hard constraint:

## ⚠️ Hard Constraints

1. **No bash GitHub fetches** — no `gh pr diff`, `gh pr view`, `gh api`, `git diff`,
   `git log`, `git show`, or `curl` to GitHub URLs. All PR data is pre-fetched below.
2. **One extra fetch maximum** — if `[DIFF TRUNCATED ...]` appears, call
   `mcp__github__get_pull_request_diff` **once**, then emit your safe-output immediately.
3. **No file reads** — analyze the diff only.

Estimated savings: Eliminating 2–3 bash-fetch turns saves ~130–195K tokens/affected run (~50–70% on complex runs).


2. Remove repos toolset — loaded but never called via MCP

The repos toolset (~10–12 tool schemas) is loaded into every system prompt but zero MCP calls to mcp__github__get_file_contents or similar were observed. The agent uses bash instead.

# Before
toolsets: [pull_requests, repos]

# After
toolsets: [pull_requests]

Keep pull_requests for mcp__github__get_pull_request_diff on truncation.

Estimated savings: ~10 schemas × 600 tokens × 3.3 avg turns ≈ ~20K tokens/active run (~10%)


3. Reduce DIFF_LIMIT from 100 KB to 30 KB

At 100 KB / 3.5 chars per token, a saturated diff injects ~28K tokens/turn into the growing context. At 30 KB → ~8.5K tokens, saving ~19.5K tokens per turn, compounded across multi-turn runs.

# Before
DIFF_LIMIT=100000
# After
DIFF_LIMIT=30000

Estimated savings: ~19.5K tokens × turns for large-diff PRs ≈ ~30–50K tokens/affected run (~15–20%)


4. Reduce max-turns from 6 to 3

After Recommendations 1–2, expected turn pattern: turn 1 (analyze), optional turn 2 (fetch full diff), turn 3 (safe-output). Max-turns 3 is a structural guard against regressions.

max-turns: 3

Risk: Test on a PR touching both setup-iptables.sh and squid-config.ts before deploying.


5. Move variable content to end of prompt (cache optimization)

The security file count (__GH_AW_EXPR_66EB691F__) appears in section 2 of the prompt, breaking Anthropic's prefix cache early. Move it inline with the diff block:

## Changed Files (up to 30 KB) | Security-critical files changed: __GH_AW_EXPR_66EB691F__

This lets ~3–4 KB of stable instructions cache on turns 2+.

Estimated savings: ~15–30% of per-turn input cost on turns 2+ (unquantified without cache hit rate data — see action item below).

Cache Analysis (Anthropic-Specific)

Per-turn breakdown estimated for a 5-turn run (~267K total):

Turn Est. Input Est. Cache Write Est. Cache Read Net New
1 ~55K ~55K ~0 ~55K
2 ~63K ~8K ~55K ~8K
3 ~68K ~5K ~63K ~5K
4–5 ~75K avg ~5K ~70K ~5K

Cache writes from Turn 1 (~55K) are read back at $0.30/M vs $3/M (10×) in turns 2–5. This works within a run but not across runs (unique diff per PR breaks the cross-run prefix).

Action item: Instrument the workflow to log Anthropic usage.cache_read_input_tokens per turn to confirm actual hit rate.

Expected Impact

Metric Current Projected Savings
Tokens/active run ~194K ~120K ~−38%
Cost/active run ~$0.94 ~$0.58 ~−38%
LLM turns (complex runs) 4–5 2–3 −2 turns
Session time (complex runs) ~10–16 min ~5–8 min ~−50%

Implementation Checklist

  • Add hard-constraint block above "## Your Task" (Rec. 1)
  • Change toolsets: [pull_requests, repos]toolsets: [pull_requests] (Rec. 2)
  • Change DIFF_LIMIT=100000DIFF_LIMIT=30000 (Rec. 3)
  • Change max-turns: 6max-turns: 3 (Rec. 4)
  • Move security file count to end of prompt near diff block (Rec. 5, optional)
  • Recompile: gh aw compile .github/workflows/security-guard.md
  • Post-process: npx tsx scripts/ci/postprocess-smoke-workflows.ts
  • Test on a PR touching both setup-iptables.sh and squid-config.ts
  • Compare next 5 active runs vs baseline (target: ≤130K tokens/active run)
  • Add Anthropic cache_read_input_tokens logging to verify cache amortization

Generated by Daily Claude Token Optimization Advisor ·

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Fields

    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions