Claudeのstrict tool useが保証すること・しないこと
strict: trueが保証するのはinput_schema準拠とツール名の妥当性だけです。additionalProperties:false必須化とpatternの部分対応、複雑さ上限まで仕様で確認します。
strict: trueを付けると、ツール呼び出しの何が変わるか
通常のツール定義では、引数の型はモデルの推論任せです。passengersがintのはずでも、Claudeが"2"という文字列や"two"という単語を返すことがあります。型が合わなければ、呼び出し側は実行時エラーで落ちるか、バリデーションと再試行のコードを抱えることになります。
ツール定義にstrict: trueを足すと、この不確実性が構造的に消えます。仕組みはグラマー制約サンプリング(grammar-constrained sampling)です。モデルのトークンサンプリング自体を、スキーマに合う出力だけに絞り込みます。「型を守ってください」とプロンプトで頼むのとは別物で、スキーマ違反のトークン列がそもそも生成されません。
同じ基盤は、構造化出力(output_config.format)がレスポンス全体をスキーマに固定するときにも使われています。Agent SDKの構造化出力がエージェントの最終応答を固定するのに対し、strict tool useは個々のツール呼び出しの入力だけを固定します。対応するJSON Schemaのサブセットと複雑さの上限は、2機能で共通です。Claude Codeの--json-schemaでスキーマが大きすぎるときに出る診断は、schema too largeの読み方にまとめてあります。
strict: trueを有効にする3ステップ
- 1
input_schemaを対応サブセットで書く
サブセットの範囲は後の節で扱います。オブジェクトには
additionalProperties: falseが要ります。 - 2
ツール定義に strict: true を足す
name・description・input_schemaと同じ階層、つまりトップレベルに置きます。 - 3
返ってきた input をそのまま使う
tool_useブロックのinputはスキーマに従い、nameも常に妥当です。型チェックと再試行のコードは要りません。
curl https://api.anthropic.com/v1/messages \
-H "content-type: application/json" \
-H "x-api-key: $ANTHROPIC_API_KEY" \
-H "anthropic-version: 2023-06-01" \
-d '{
"model": "claude-opus-5-5",
"max_tokens": 1024,
"messages": [{"role": "user", "content": "What is the weather in San Francisco?"}],
"tools": [{
"name": "get_weather",
"description": "Get the current weather in a given location",
"strict": true,
"input_schema": {
"type": "object",
"properties": {
"location": {"type": "string"},
"unit": {"type": "string", "enum": ["celsius", "fahrenheit"]}
},
"required": ["location"],
"additionalProperties": false
}
}]
}'computer useとbrowser useのツールセット(computer_toolset_20260801とbrowser_toolset_20260801)はstrict: trueを受け付けません。どちらかのエントリに付けたリクエストは拒否されます。
保証の内側と外側 — 何を信じてよいか
保証が及ぶのは、ツールのinputとnameの2つだけです。それ以外の場面では、strictを付けても通常の生成と同じ落とし穴が残ります。
strict: true の保証が届く範囲
保証される
inputがinput_schemaに厳密に従う(型の不一致・必須フィールドの欠落・スキーマに無いプロパティが出ない)nameが、渡したツール一覧かサーバーツールの中から選ばれる
保証されない
- 拒否:
stop_reasonがrefusalになり、出力がスキーマに従わないことがある max_tokens到達: 出力が途中で切れるenumとconstの大文字小文字- ツールが呼ばれること自体
拒否は200ステータスで返り、生成されたトークン分の課金も発生します。拒否メッセージがスキーマ制約より優先されるためです。思考過程や段階的な推論を求めるプロパティをスキーマに置くとreasoning_extractionの拒否を招くことがあり、短い説明を求める形が案内されています。
max_tokensで切れた出力を完全にするには、max_tokensを増やして再試行します。enumの値は、主にスペースの後の単語の先頭文字で、大文字小文字だけが違う形で返ることがあります。エラーにも特別なstop_reasonにもならず、200で正常終了します。大文字小文字を無視して比較し、大文字小文字だけが違うenum値を並べないでください。
実装側ではstop_reasonの分岐にtool_useだけでなくrefusalとmax_tokensも入れます。この2つではinputをスキーマ準拠として扱わない作りにします。
strictだけでは、ツールは呼ばれない
「ツールが呼ばれること」は、strictとは別の仕組み(tool_choice)の領分です。tool_choiceがauto(既定)のままなら、Claudeはツールを呼ばずに直接答えることがあります。strictが保証するのは、呼ぶと決めたときの引数の形です。
tool_choiceをanyかtoolにすると呼び出しを強制できます。対応モデルでは、anyとstrictの併用で「いずれかのツールが呼ばれる」と「入力がスキーマに従う」が両方成立します。ただし強制した場合、APIがアシスタントメッセージを事前に埋めるため、tool_useの前に自然言語の説明は出ません。
強制が使えない組み合わせもあります。
| モデル・設定 | any / tool | 代わりの手段 |
|---|---|---|
手動の拡張思考(thinking: {type: "enabled"}) | any / toolエラー | 代わりの手段autoかnone |
| Claude Opus 5.5・Sonnet 5.5・Fable 5.1・Mythos 5.1 | any / tool400エラー | 代わりの手段autoとstrictの併用、または構造化出力 |
適応的思考(adaptive thinking)そのものは強制を妨げず、Claude Opus 5は思考オンのまま強制に対応します。上の表のモデルでは、autoにstrictを組み合わせても、どのツールを選ぶかはプロンプトの影響を受けます。入力の形は保証され、呼び出しの有無と選択は保証されない、という分担です。
スキーマが通らないとき — additionalPropertiesとpatternの壁
strictが受け付けるのは、JSON Schemaのうち構造化出力と共通の一部サブセットです。対応する要素は次のとおりです。
- 基本型 — object / array / string / integer / number / boolean / null
enum(文字列・数値・真偽値・nullのみ)とconstanyOf/allOf(ただしallOfと$refの組み合わせは不可)$ref/$def/definitions(同一ドキュメント内に限る)- 全型の
default、required、additionalProperties(false固定) - 文字列フォーマット —
date-time/time/date/duration/email/hostname/uri/ipv4/ipv6/uuid - 配列の
minItems(0と1のみ)
対応しないのは、再帰スキーマ、enum内の複合型、外部$ref、数値制約(minimum / maximum / multipleOf)、文字列長制約(minLength / maxLength)、minItemsの0・1以外、false以外のadditionalPropertiesです。非対応の機能を使うと、400エラーと詳細メッセージが返ります。
additionalPropertiesは、オブジェクトにfalseを明示しないと通りません。省略もtrueも非対応です。既存のスキーマにstrictを後付けするときは、ネストしたオブジェクトも含めてfalseの抜けを1つずつ探します。複数ツールでスキーマの一部を共有したいときは、外部ファイルへの$refではなく、同一スキーマ内の$defにまとめる必要があります。
pattern(正規表現)は、完全非対応ではありません。通る機能と通らない機能が分かれています。
| pattern | 内容 |
|---|---|
| 対応 | 内容完全一致・部分一致(^...$)、量指定子(* + ?、単純な{n,m})、文字クラス([] . \d \w \s)、グループ((...)) |
| 非対応 | 内容後方参照(\1など)、先読み・後読み((?=...) (?!...))、単語境界(\b \B)、大きな範囲の{n,m} |
非対応の機能を使うと、Unsupported regex feature in pattern field: ...という400エラーが返り、どの機能で引っかかったかが本文に出ます。メールアドレスや郵便番号のような単純な形式チェックは書けます。「特定の単語を含まない」のような先読みに頼る正規表現は、strictの外で検証することになります。
400エラーを避ける複雑さの上限
コンパイル時間を守るため、strict: trueとoutput_config.formatのどちらを使うリクエストにも、次の上限がかかります。
strictの明示的な上限
strictなツール
20個
strictを付けないツールは数えない
省略可能パラメータ
24個
requiredに無いものを全スキーマ合計で数える
union型のパラメータ
16個
anyOfや型配列(string, null)を使うもの
数字は1ツール単位ではなくリクエスト単位の合計です。省略可能パラメータが6個ずつの4ツールなら、どのツールも単純に見えるのに合計が24に達します。strictのツールと構造化出力を同じリクエストで併用する場合も、省略可能パラメータは両方のスキーマを合わせて数えます。
上限を超えるか、超えなくてもコンパイル後のグラマーが大きすぎると、Schema is too complex for compilationという400エラーが返ります。内部にはグラマーサイズの上限もあり、省略可能パラメータ・union型・ネスト・ツール数が掛け合わさって膨らむためです。表の数字をすべて満たしていても失敗することがあります。コンパイルには180秒のタイムアウトもあります。
省略可能パラメータは1個ごとにグラマーの状態空間の一部をおよそ倍にし、union型は指数的なコンパイルコストを生みます。複雑さを削る順序は、次の4段階が案内されています。
- 本当に重要なツールだけを
strict: trueにする - 省略可能パラメータを減らして
requiredに寄せる(妥当な既定値があるなら、Claudeにその値を明示させる) - ネストしたオブジェクトを浅くする
- リクエストやサブエージェントを分けて、strictなツールを分散させる
症状から選ぶ — strictか、input_examplesか
トラブルシューティングガイドは、ツール呼び出しの症状ごとに対処を並べています。strictが効く症状と、別の手が要る症状は混ざっています。
| 症状 | 想定される原因 | 対処 |
|---|---|---|
| 引数の型が違う | 想定される原因曖昧なスキーマをモデルが推測している | 対処strict: true(スキーマがサブセットに収まるとき)かinput_examples |
| スキーマに無いパラメータが付く | 想定される原因strictなしでの過剰な生成 | 対処strict: true |
enumに無い値が入る | 想定される原因strictなし、またはenumが大きすぎる | 対処enumを縮めるかinput_examples |
| ツールが一向に呼ばれない | 想定される原因ツール名の衝突や、汎用的すぎるスキーマ | 対処名前の重複を確認し、input_examplesを足す |
最後の行にstrictが出てこない点が肝心です。呼び出しの有無は、スキーマの厳密さでは変わりません。
スキーマがサブセットに収まるなら、strict: trueのほうが構造的に確実で、再試行のコードが要りません。数値の範囲制約や複雑な正規表現が必須でサブセットに収まらないときは、input_examplesに頼ります。input_examplesの各例は、そのツールのinput_schemaに対して有効な入力でなければなりません。例を足すのはモデルへの手がかりで、出力を縛る保証ではありません。
ツールが多すぎて困るケースの工夫は、Advanced Tool Useで扱っています。strictが効くのは単発の呼び出しの型安全性で、呼び出し件数やコンテキストの圧迫は対象外です。
初回の遅延とスキーマの保持 — 運用で効いてくる性質
グラマーのコンパイルは、初めて使うスキーマのリクエストに追加の遅延を生みます。コンパイル済みのグラマーは、最後に使ってから24時間キャッシュされ、以降のリクエストは速くなります。
キャッシュが無効になるのは、スキーマの構造を変えたときと、構造化出力とツール使用を併用していてツールの集合を変えたときです。nameとdescriptionだけの変更では無効になりません。ツール定義を頻繁に組み替えるアプリでは、変更のたびに遅延が戻ると考えておきます。
保持にも注意点があります。ツールのinput_schemaはグラマーとして最大24時間キャッシュされますが、プロンプトとレスポンスはAPI応答の後に保持されません。strict tool useはHIPAAの対象になり得ますが、スキーマ定義にPHI(保護対象の医療情報)を含めてはいけません。キャッシュされたスキーマは、メッセージ本文と同じ保護を受けないためです。プロパティ名・enum値・const値・patternの正規表現にもPHIを入れません。PHIはメッセージ本文にだけ置きます。
構造化出力を併用すると、Claudeにはレスポンス形式を説明する追加のシステムプロンプトが自動で渡され、入力トークンがわずかに増えます。output_config.formatを変えると、その会話スレッドのプロンプトキャッシュも無効になります。citationsはoutput_config.formatとの併用で400エラーになります。
まとめ
strictが固定するのは、呼ぶと決まったツールの引数の形と名前だけです。呼び出しの有無・拒否・打ち切り・enumの大文字小文字は別に設計します。導入前に、additionalProperties: falseの抜けと外部$ref、省略可能パラメータの合計をリクエスト単位で数えると、400エラーでの手戻りが減ります。