Claude Media
Compactionの発動しきい値の決め方 — モデル別の比率で考える

Compactionの発動しきい値の決め方 — モデル別の比率で考える

サーバーサイドcompactionのtrigger.valueをどう決めるか、モデルのコンテキストウィンドウに対する比率と予算管理の計算例で考えます。

trigger.valueが閾値そのもの

サーバーサイドcompactionでは、context_management.editscompact_20260112を指定するとき、triggerパラメータのvalueが要約を発動させる入力トークン数です。既定値は15万トークン、指定できる最小値は5万トークンです。この1つの数字だけで、会話がどれだけ育ってから要約に切り替えるかが決まります。

curl https://api.anthropic.com/v1/messages \
    --header "x-api-key: $ANTHROPIC_API_KEY" \
    --header "anthropic-version: 2023-06-01" \
    --header "anthropic-beta: compact-2026-01-12" \
    --data '{
        "model": "claude-opus-5",
        "max_tokens": 4096,
        "messages": [{"role": "user", "content": "Hello, Claude"}],
        "context_management": {
            "edits": [
                {"type": "compact_20260112", "trigger": {"type": "input_tokens", "value": 150000}}
            ]
        }
    }'

閾値が低いほど要約が頻繁に起き、アクティブなコンテキストは小さく保たれます。閾値が高いほど1回のリクエストで多くの文脈を保持できますが、コンテキストウィンドウの上限に近づくリスクも増えます。公式ドキュメントはこの2択を明記しているだけで、具体的にどの数字を選ぶべきかまでは決め打ちしていません。判断材料になるのは、使っているモデルのコンテキストウィンドウサイズです。

モデルのコンテキストウィンドウに対する比率で考える

同じ15万トークンという既定値でも、モデルによって意味がまったく違います。Claude Opus 5・Claude Sonnet 5・Claude Fable 5.1・Claude Mythos 5.1などは100万トークンのコンテキストウィンドウを持ち、Claude Sonnet 4.5など一部のモデルは20万トークンです。

モデルのコンテキストウィンドウ既定値15万トークンの比率最小値5万トークンの比率
100万トークン(Opus 5 / Sonnet 5等)既定値15万トークンの比率約15%最小値5万トークンの比率約5%
20万トークン(Sonnet 4.5等)既定値15万トークンの比率約75%最小値5万トークンの比率約25%

100万トークンのモデルでは、既定値のままだと会話が全体のわずか15%まで育った時点で要約が走ります。長時間のタスクを1回の会話で完結させたい場合、この既定値は保守的すぎることがあります。逆に20万トークンのモデルでは、既定値の75%というのはかなり深いところまで会話を伸ばしてから要約する設定で、モデルによってはcontext rotの影響で応答の精度が既に落ち始めている可能性があります。

閾値をモデルのコンテキストウィンドウサイズに対する比率で考え直すと、100万トークンのモデルでは30万〜50万トークン(全体の30〜50%程度)まで引き上げる、20万トークンのモデルでは既定値のままか、精度低下が気になるなら10万トークン程度まで下げる、といった調整の指針が立てられます。なお、サーバーサイドcompactionはベータ機能で対応モデルが限定されており、Claude Sonnet 4.5はそもそも対応モデル一覧に含まれていません。20万トークン枠での閾値調整を検討する前に、使っているモデルが対応リストに載っているかを確認しておく必要があります。長時間エージェントでコンテキストを扱う設計全般はEffective context engineeringでも扱っています。

compactionは1回では終わらない

閾値を決めるときに見落としやすいのが、長時間の会話では複数回のcompactionが起こる前提だという点です。要約が発動すると、レスポンスの先頭にcompactionブロックが返り、それより前の内容は生成された要約に置き換わります。会話がさらに伸びれば、その要約を起点に再びトークンが積み上がり、閾値に達すれば次のcompactionが発生します。複数回のcompactionが起きた場合、最後のcompactionブロックがプロンプトの最終状態を反映し、それより前のブロックはすでに要約に取り込まれています。

つまり閾値は「会話全体で1回だけ発動するスイッチ」ではなく、「会話が続く限り繰り返し発動する周期」として設計する値です。低い閾値は周期を短くして毎回の要約対象を小さく保ち、高い閾値は周期を伸ばして要約の呼び出し回数自体を減らします。後述する「compaction回数 × 閾値」での予算見積もりも、この繰り返し発動を前提にしています。

usage.iterationsで実際の挙動を確認する

閾値が意図通りに機能しているかは、レスポンスのusage.iterations配列で確認できます。compactionが発生したリクエストでは、type: "compaction"のエントリとtype: "message"のエントリが並び、それぞれのinput_tokensoutput_tokensが個別に記録されます。

{
  "usage": {
    "input_tokens": 23000,
    "output_tokens": 1000,
    "iterations": [
      {"type": "compaction", "input_tokens": 180000, "output_tokens": 3500},
      {"type": "message", "input_tokens": 23000, "output_tokens": 1000}
    ]
  }
}

トップレベルのinput_tokensoutput_tokensにはcompactionイテレーション分は含まれません。課金や利用量の追跡でトータルの消費トークンを出す場合は、usage.iterations配列の全エントリを合算する必要があります。このcompactionエントリのinput_tokensが実際に閾値付近でどれだけの値になっているかを見ることで、設定したtrigger.valueが意図通りの周期で発動しているかを検証できます。

頻度とコストのトレードオフ

compactionには追加のサンプリングステップが必要で、レート制限と課金の両方に影響します。閾値を下げるほど要約の回数が増え、その都度、要約生成のための入力トークン(会話全体)と出力トークン(要約文)が課金対象になります。

さらに、要約に使うモデルを安価な別モデルに切り替えるオプションはサーバーサイドcompactionにはありません。リクエストで指定したモデルがそのまま要約にも使われます。Opusクラスの高価なモデルで低い閾値を設定すると、要約1回ごとのコストも高くなる点は見落としやすいところです。

閾値を上げる方向のリスクは、コンテキストウィンドウの上限に到達してしまうことです。入力だけで上限を超えるとinvalid_request_errorが返り、生成中に到達した場合はmodel_context_window_exceededというstop_reasonで応答が止まります(このstop_reasonはClaude 4.5世代以降のモデルの挙動で、それより前のモデルでは代わりに検証エラーが返ります)。閾値は「要約のコスト」と「上限到達のリスク」の間でバランスを取る値です。Claude Code側で似た文脈のエラーに遭遇した場合はError during compactionの意味と対処が扱う対処法が近いですが、そちらはCLIが内部で管理する/compactの挙動で、本記事のAPIレベルのtrigger.valueとは設定できる範囲が異なります。

予算管理と組み合わせた計算例

長時間タスクで累積トークン消費を見積もりたい場合、pause_after_compactionとcompaction回数のカウントを組み合わせます。公式ドキュメントが示す考え方は次の通りです。

TRIGGER_THRESHOLD = 100_000
TOTAL_TOKEN_BUDGET = 3_000_000
n_compactions = 0
 
# compactionが発生するたびに n_compactions を +1 し、
# n_compactions * TRIGGER_THRESHOLD が TOTAL_TOKEN_BUDGET 以上になったら
# タスクの締めくくりを促すメッセージを追加する

この式は「1回のcompactionまでにおよそtrigger.value分のトークンを消費する」という前提に立った概算です。閾値を10万トークンに設定し、タスク全体で300万トークンまで許容するなら、30回のcompactionが発生した時点で打ち切りの合図を出す、という見積もりになります。閾値を5万トークンまで下げると、同じ300万トークンの予算に到達するまでに必要な発生回数はおよそ60回まで増えますが、見積もる総トークン数自体は閾値によらずほぼ同じです。閾値を下げるほど、この概算の刻みが細かくなり、カウンタを確認する頻度は増える一方で、予算の見積もり精度そのものは変わらない点は押さえておきます。

サーバーサイドと廃止予定のSDK側設定を混同しない

compactionという言葉は2箇所で使われていて紛らわしいので、指す対象を確認しておきます。本記事で扱っているのはcontext_management.editscompact_20260112を指定するサーバーサイドcompactionで、Anthropicが長時間の会話管理における第一の選択肢として案内している機能です。

これとは別に、TypeScript / RubyのSDKにはtool_runnercompaction_controlというクライアントサイドの仕組みがあり、そちらにもcontextTokenThresholdという閾値パラメータがあります(既定10万トークン)。ただしこのcompaction_controlはTypeScript / Ruby SDKで非推奨、Python SDKではv1.0で削除済みです。ツールランナー経由でサーバーサイドcompactionを使うには、リクエストのcontext_managementパラメータにcompact_20260112エディットを渡します。閾値の選び方を調べていてcompaction_controlcontextTokenThresholdの説明に行き当たった場合、それは廃止予定の別機能の話である点に注意します。

閾値選びでハマりやすい点

  • 精度への影響を過小評価する: 閾値を高く取りすぎると、要約が発動する前にコンテキストが肥大化した状態が長く続きます。トークン数がコンテキストウィンドウの大部分を占める状態では、モデルの回答精度が落ちるcontext rotの影響を受けやすくなります。閾値は「上限に達しないための値」ではなく「精度が落ち始める前に要約するための値」として決めます
  • 1リクエスト中に複数回発動する: web検索のようなサーバーツールを使うリクエストでは、compactionの発動判定が各サンプリングイテレーションの開始時にチェックされます。出力が長くなるタスクでは、閾値と出力量の組み合わせ次第で1回のリクエスト中に複数回compactionが起きることがあり、想定より発動回数が増えることがあります
  • 要約中にツールが呼ばれて失敗する: リクエストにtoolsが含まれていると、要約生成の内部ステップでモデルがツールを呼び出してしまい、compactionブロックのcontentnullになることがあります。閾値を下げて発動頻度を上げるほどこの失敗に当たる回数も増えるため、instructionsで「要約中はツールを呼ばず本文だけで答える」よう明示する対策とセットで考えます

よくある質問

閾値を最小値の5万トークンより下げられるか

公式ドキュメントはtrigger.valueが5万トークン以上である必要があると明記しています。それより小さい値を指定した場合の挙動(エラーになるかクランプされるか)までは記載が無いため、5万トークン以上で設計するのが確実です。

公式の実装例で使われている閾値の数字は参考になるか

公式ドキュメントのサンプルコードでは15万・10万・5万トークンのいずれもが例として登場します。どれも動作を示すためのサンプル値であって、特定のワークフローに対する推奨値として提示されているわけではありません。実際の値は、使っているモデルのコンテキストウィンドウサイズと、要約のコスト許容度を踏まえて自分で決めます。

この記事を共有:XはてブLinkedIn