3行でいうと

  • 3社とも、決めた形(JSONスキーマ)に沿った文字列を返す機能があります。ただし保証されるのは形で、値の意味の正しさは別です。
  • 拒否(安全上の理由)や、出力が上限で途中切れしたときは、形に合わない出力が返ることがあります。必ず状態を見てから読みます。
  • Anthropicはスキーマの複雑さに数値の上限(厳密な道具20個など)を公開しています。OpenAIとGoogleは、読んだ文書に数値が見つかりませんでした。

この記事は、実際に使って確かめた記録ではありません。この記事は公式の文書を読んでまとめたものです。情報は2026年10月22日に確認しました。変わることがあります。

先に結論

前提:何の話か

APIは、アプリの中からAIを呼び出す開発者向けの窓口です。通常、AIの返事は自由な文章なので、そこから必要な値を取り出すのは面倒で、形が崩れることもあります。

JSONは、{"name": "田中", "age": 30}のような、名前と値の組でデータを表す書式です。JSONスキーマは、そのJSONがどんな形であるべきか(どの項目があり、文字か数字か、必須か)を書く決まった書式です。構造化出力は、このスキーマを渡して、返事がそれに合うようにする機能です。

似たものに「JSONモード」があります。OpenAIの文書によると、JSONモードは有効なJSONを返すところまでで、スキーマへの一致は保証しません。構造化出力はその進化形とされ、スキーマに合うことが保証される、と書かれています。

3社の比較

OpenAI Anthropic(Claude) Google(Gemini)
返事の形を固定 text.formatにjson_schemaとstrict: true(Responses API)。Chat Completionsはresponse_format output_config.formatにjson_schema 生成設定のresponse_formatにMIMEタイプapplication/jsonとスキーマ
道具の引数を固定 関数定義にstrict: true 道具の定義にstrict: true 道具との併用はプレビュー(Gemini 4系と3系のみ)
対応モデル GPT-4o以降。新規にはgpt-6-astraを推奨 Fable 5/5.1、Mythos、Opus 4.5〜5.5、Sonnet 4.5〜5.5、Haiku 4.5/5.5 文書に一覧あり(Gemini 4 Argon、3.8 Flash、3.1 Pro Preview、2.5系など)
拒否の検出 応答にrefusalの項目 stop_reason: "refusal"(HTTP 200で返る) 文書に記載なし
途中切れ statusがincomplete、理由はmax_output_tokens stop_reason: "max_tokens" 文書に記載なし
スキーマの初回の遅れ あり(初回のみ) あり(文法のコンパイル。24時間キャッシュ) 文書に記載なし
バッチとの併用 構造化出力はBatch APIでも使える 使える(50%割引) 読んだ文書では確認できていません
SDKの補助 Pydantic(Python)、Zod(JavaScript)など messages.parse()にPydanticモデルを渡す Pydantic、Zod(z.fromJSONSchema())

各社の中身

OpenAI

公式のStructured Outputsの文書によると、次の通りです。

Anthropic

公式のStructured outputsの文書によると、次の通りです。

公式文書の例の一部です(この記事では実行していません)。

output_config={
    "format": {
        "type": "json_schema",
        "schema": {
            "type": "object",
            "properties": {"name": {"type": "string"},
                           "demo_requested": {"type": "boolean"}},
            "required": ["name", "demo_requested"],
            "additionalProperties": False,
        },
    }
},

Google(Gemini)

Geminiの構造化出力の文書(generateContent版とInteractions版)によると、次の通りです。

OpenAIの関数呼び出しの`strict`と、道具の呼び出しの流れ

OpenAIの関数呼び出しの文書によると、strictは「関数呼び出しを厳密モードにするか」を示す項目で、例では"strict": trueと、"additionalProperties": false、全項目をrequiredに入れる書き方が使われています。ただし、これらを必須条件として明記した文はありませんでした。

呼び出しの流れは、次の5段階です。

  1. 呼べる道具の一覧を付けてモデルに送る。
  2. 応答のoutputにfunction_callが入る。中身はcall_id、name、JSON文字列のarguments。
  3. 自分のプログラムで関数を実行する。
  4. 道具の出力を、call_idで元の呼び出しに結びつけて、2回目のリクエストで返す。
  5. 最終の応答、または次の道具の呼び出しを受け取る。

応答は、道具の呼び出しがゼロ、1つ、複数のどれにもなりうるので、複数ある前提で書くのがよい、と文書にあります。一度に使える道具の数に厳密な上限は書かれておらず、「ターンの開始時に20個未満が目安」という弱い提案があります。

道具の呼び出しの仕組みそのものは、別記事「ツール呼び出し」で扱います。

選び方・判断の基準

見立てです。次の考え方が無難だと思います。

よくある失敗・つまずき

Anthropicのスキーマの複雑さの上限(公式の数値)

Anthropicの文書によると、output_config.formatまたはstrict: trueを使うリクエストには、次の上限があります。

項目 上限
1リクエストの厳密な道具 20個
任意の(必須でない)パラメータ(全スキーマの合計) 24個
共用体型(anyOfや型の配列)を持つパラメータ 16個
コンパイルのタイムアウト 180秒

上限を超えると、400エラー「Schema is too complex for compilation」が返ります。対策として、本当に必要な道具だけを厳密にする、パラメータを必須にする、ネストを平らにする、道具をリクエストやサブエージェントに分ける、が挙げられています。

また、SDKの補助機能は、minimum、maximum、minLength、maxLengthなどの非対応の制約をスキーマから外して、項目の説明文に移す、と書かれています。SDKが検証するときには、元の制約で確認します。

OpenAIとGoogleの文書では、これに相当する数値の上限は、読んだ範囲に見つかりませんでした。

気をつけること

出典

更新履歴

一部の出典は読めなかったため、その部分は前のままです。