メインコンテンツまでスキップ

Usage & Cost Analytics API: 1 ドルずつ帰属させる

上級
What you'll learn
  • usage_report と cost_report に何が取って代わったのか、そして新しい形が時間バケットではなく行である理由
  • 行の契約: starting_at / ending_at、group、usage または cost — そして、グループ化しない限りディメンションが null になる理由
  • group_by[] は 5 つのディメンションを取る — ただし cost エンドポイントの 2 つは数に含まれず、limit にも従わない
  • actor モデル: ユーザー、サービスアカウント、フェデレーテッドなクラウド ID、または API キー自体 — そして api_key_ids[] と actor_ids[] が異なる問いに答える理由
  • セントの落とし穴: amount は「セント」単位の 10 進数文字列で、"41280.000000" は $412.80 であり、素朴なダッシュボードは 100 倍間違える
  • 当日のダッシュボードを無効にするデータ鮮度のルールと、呼び出し間で結果が変わらないようにするコツ
  • ユーザーごとの Claude Code コストを求める 1 行のレシピ

2 つのエンドポイントで、1 つの仕事: Claude の支出が実際にどこへ行ったかを教えます。

  • GET /v1/organizations/analytics/usage — トークン数とリクエスト数。
  • GET /v1/organizations/analytics/cost — USD でのコスト。

Claude Console 組織では、Console の Usage と Cost ページが表示する内容とほぼ同じで、彼らが選んだディメンションの代わりに自分で選んだディメンションが使えます。重要な理由は、Console からは誰も答えられない問いです: 上がった行の原因は、どの顧客、エージェント、API キーなのか?

これはレポーティングであり、強制ではありません

ここにあるものは請求を止めません。それには Hard Spend Caps を参照してください — 両者は補完関係にあります。上限は支出が発生するかどうかを決め、この API は誰がそれを引き起こしたかを教えます。

組織の種類別の認証情報​

組織使うもの
Claude ConsoleAdmin API キー、または org:admin スコープ付きの OAuth ベアラートークン(x-api-key ではなく authorization: Bearer として送信)
Claude Enterpriseread:analytics スコープ付きのキー。組織で Analytics API が有効になった後に、claude.ai でプライマリオーナーが作成

コレクターサービスには専用のキーを与え、シークレットマネージャーに保管し、キーの有効期限を設定して、ローテーションを記憶頼みではなく強制にしてください。利用できる場合は、org:admin を持つ Workload Identity Federation ルールの方が確実に優れています — 短命のトークンで、漏えいし得る長命のシークレットがありません。Admin API 全般と同じ考え方です。

クイックスタート​

モデル別の日次トークン使用量、1 週間分

curl --globoff "https://api.anthropic.com/v1/organizations/analytics/usage?\
starting_at=2026-09-01T00:00:00Z&\
ending_at=2026-09-08T00:00:00Z&\
time_bucket_width=1d&\
group_by[]=model&\
limit=100" \
-H "anthropic-version: 2023-06-01" \
-H "anthropic-beta: analytics-usage-cost-2026-08-24" \
-H "x-api-key: $ANTHROPIC_API_KEY"

--globoff は重要です: これがないと、curl は group_by[] の [] を glob の範囲として解釈しようとします。

行の契約​

従来のエンドポイントから移行する人がつまずくのがここです。レスポンスの形は意図的に異なっています。

Guided walkthrough1 of 6
  1. starting_at と ending_at は行が対象とする期間を示し、group はすべてのディメンションを保持し、usage(cost エンドポイントでは cost)はメトリクスを保持します。ディメンションとメトリクスは別々のオブジェクトにあります — 従来のレポートのように横並びではありません。

usage エンドポイントの order_by は、total_tokens(デフォルト)、output_tokens、uncached_input_tokens、requests、time を受け付けます。cost エンドポイントでは amount(デフォルト)、list_amount、time です。

ランク順がデフォルトなのは、ダッシュボードのサイレントバグ

範囲をリクエストして、届いた順に行をプロットすると、大きさ順に並んだ棒グラフができあがり、それが時系列に見えてしまいます。行が時系列順になるのは、time_bucket_width と order_by=time の両方を設定したときだけです。

すべてのディメンションがあなたに当てはまるわけではない​

model と actor はすべての組織に当てはまります。api_key_id は Console 専用です。slack_channel_id は Enterprise 専用です。当てはまらないディメンションはすべての行で null になり、そのフィルターは何もマッチしません(エラーも出ません)。唯一の例外は rbac_group_id で、組織でチームが利用できない場合はエラーを返します。

そして、壁に貼っておく価値のある挙動の変更があります: 従来の API では、未知の API キーやワークスペース ID はエラーを返していました。ここでは、スペルミスした models[] の値も含めて何もマッチしません。空の結果が、タイプミスに対する通常のレスポンスになったのです。

Actor: 誰に課金されるか​

actor ディメンションは、リクエストが誰に帰属するかを示します — ユーザー、サービスアカウント、フェデレーテッドなクラウド ID(クラウドプラットフォーム経由で Claude に到達する組織の AWS または Google Cloud プリンシパル)、あるいはそれらのいずれも背後にない場合はAPI キー自体です。actor でグループ化すると、各行の actor はオブジェクトになり、その type が種類を示します。どの ID にも帰属できない使用量は actor: null です。

マッピングのルール:

  • 個人キーとサービスアカウントキーは、リンクされているユーザーまたはサービスアカウントとして動作します: ID は actor に、キーは api_key_id に表示されます。
  • レガシーのワークスペースキーは ID にリンクされていないため、キーは actor と api_key_id の両方に現れます。
  • サインイン時に Claude Code がメンバーのために作成するキーは Claude Code ワークスペースに存在し、その使用量はそのメンバーに帰属します。
  • API キーがまったくないリクエスト — Console から、API キーなしでサインインした後の Claude Code から、または Workload Identity Federation トークンを使ったもの — は api_key_id: null になります。actor は依然としてサインインしたメンバー、またはフェデレーテッドなワークロードの場合はそのサービスアカウントです。
2 つのフィルター、2 つの異なる問い

api_key_ids[]=apikey_… は、誰に帰属するかにかかわらず、そのキーが認証したすべてのリクエストにマッチします。actor_ids[]=apikey_… は、キー自体に帰属するリクエストだけにマッチします。両者は交換できず、混同すると監査の結果が足りなくなります。api_key_ids[] フィルターにキーなしの使用量も含めるには、空のエントリを追加します: api_key_ids[]=。

cost エンドポイントと 100 倍の落とし穴​

cost エンドポイントは、/usage と同じフィルター、ディメンション、時間バケットを取ります。各行の cost オブジェクトには次が含まれます:

フィールド意味
amount割引後で、クレジット適用前のコスト
list_amount定価でのコスト
currency常に "USD"
requestsリクエスト数
amount はドルではなく「セント」単位

currency は "USD" と言っていますが、数値は小数点以下 6 桁のセント単位の 10 進数文字列です。"41280.000000" は $41,280 ではなく $412.80 です。従来のコストレポートは "123.45" のようなドル相当の文字列を返していましたが、同じ値がここでは "12345.000000" になります。何かを表示する前に 100 で割り、テストを書いてください — フィールド名が amount で、通貨フィールドがドルと言っているために、コードレビューをすり抜ける 100 倍のエラーです。

2 つのディメンションは cost エンドポイントだけに存在し、どちらも通常のルールをあなたに有利な形で破ります: group_by[]=cost_type は各行をコストの種類ごとに分割し、group_by[]=token_type はトークンコストをトークンの種類ごとに分割します。どちらも 5 ディメンションの制限に数えられず、どちらも limit に従いません — そのため、1 ページが limit より多くの行を正当に含むことがあります。

お金の行き先: 1 か月分のモデル別、コスト種別、トークン種別のコスト

curl --globoff "https://api.anthropic.com/v1/organizations/analytics/cost?\
starting_at=2026-09-01T00:00:00Z&\
ending_at=2026-10-01T00:00:00Z&\
group_by[]=model&\
group_by[]=cost_type&\
group_by[]=token_type" \
-H "anthropic-version: 2023-06-01" \
-H "anthropic-beta: analytics-usage-cost-2026-08-24" \
-H "x-api-key: $ANTHROPIC_API_KEY"

この 1 つのクエリは、どの組織でも最初に実行する価値があります。多くのチームが推測で済ませている問いに答えるからです: 請求のうち、推論ではない部分はどれだけか。 cost_type で分割するとトークン支出とサーバー側ツールが分かれ、token_type で分割するとキャッシュ読み取りと非キャッシュ入力、出力が分かれます。入力の行でキャッシュ読み取りが支配的なら、次に見るのはプロンプトキャッシュとキャッシュ診断です。出力トークンが支配的なら、トークン使用量を削減するです。

ユーザーごとの Claude Code コストを 1 つのクエリで

curl --globoff "https://api.anthropic.com/v1/organizations/analytics/cost?\
starting_at=2026-10-01T00:00:00Z&\
ending_at=2026-11-01T00:00:00Z&\
products[]=claude_code&\
group_by[]=actor" \
-H "anthropic-version: 2023-06-01" \
-H "anthropic-beta: analytics-usage-cost-2026-08-24" \
-H "x-api-key: $ANTHROPIC_API_KEY"

Console 組織には、この目的のためのもう 1 つの選択肢があります — 専用の Claude Code Analytics API で、ユーザーごとの Claude Code アクティビティを推定コストとともに報告します。

日付範囲と、誰も予想しない丸め​

  • タイムスタンプは UTC オフセット付きの RFC 3339(2026-09-01T00:00:00Z)です。starting_at は含み、ending_at は含みません。
  • starting_at は 2026 年 1 月 1 日以降で、かつ過去 365 日以内でなければなりません。
  • 1 回のリクエストが対象とするのは最大 31 日です。ending_at のデフォルトは starting_at の 31 日後か現在のうち早い方です。それより長い範囲は複数のリクエストに分割してください。
  • time_bucket_width を設定する場合、ending_at は必須で、time_bucket_width=1m では期間は最大 24 時間です。
  • 両端とも切り捨てられます — バケットの境界へ、time_bucket_width が未設定のときは時間単位へ。1h バケットでは、starting_at=2026-09-01T10:43:00Z は 10:00:00Z に、ending_at=2026-09-01T15:43:00Z は 15:00:00Z になるため、レスポンスは 10:00–15:00 UTC を対象とします。素朴に書いた「直近 90 分」のクエリは 1 時間分を返します。

ダッシュボードを壊すのはデータの鮮度​

すべてのレスポンスには data_refreshed_at タイムスタンプが付きます。それ以降の使用量は欠けているか、部分的です。範囲のどの部分にもまだデータが存在しない場合、data_refreshed_at は null で data は空です。

プロパティ値
典型的な更新の遅れ元の使用量から 4 時間以内
最悪の場合最大 24 時間
改訂ウィンドウ遅れて届くイベントや照合により、暦月の終了から約 7 日後まで値が変わることがある
ページネーション1 つのページ分割クエリのすべてのページが同じスナップショットを読むため、data_refreshed_at はページ間で同一

実際には、10 月 1 日の数値は 11 月 7 日頃まで変わり得ます。

これは、データが通常 5 分以内に現れていた従来の API からの実質的な後退であり、構築できるものを変えます。そこから 2 つのルールが直接導かれます:

  • 呼び出し間で結果が変わらないようにするには、すでに見た data_refreshed_at 以前に ending_at を設定します。
  • 確定した合計が必要なら、終了から少なくとも 7 日経った月だけをクエリします。
これを使ってリアルタイムのアラートを作らないでください

4〜24 時間遅れるコスト急増アラートはアラートではありません。この API は帰属、チャージバック、トレンドのレポートに使ってください。数分で反応が必要な部分には支出上限を、ほぼリアルタイムのリクエスト単位の可視性には OpenTelemetry トレーシングを使います — ただしトレースはベストエフォートかつ at-least-once なので、台帳はトレースではなく Analytics API であることを忘れないでください。

usage_report と cost_report からの移行​

引き継がれるもの: Admin API キー、anthropic-version ヘッダー、starting_at / ending_at、バケット幅の値(1m、1h、1d)、ブラケット記法、ページネーションのフィールド名、トークンとコストのフィールド名。変わるもの:

従来の Usage & Cost APIUsage & Cost Analytics API
ベータヘッダーなしすべてのリクエストに anthropic-beta: analytics-usage-cost-2026-08-24
データは約 5 分以内通常 4 時間、最大 24 時間、月末から約 7 日間は改訂
data は時間バケット(古い順、空のバケットも含む)で、それぞれがディメンションとメトリクスが混在する results リストを持つdata は order_by でランク付けされた行で、それぞれが独自の starting_at / ending_at を持ち、ディメンションは group、メトリクスは usage または cost に入る。空の組み合わせの行はない
bucket_width、デフォルトは 1dtime_bucket_width、デフォルトなし — 日次の行を維持するには 1d を渡し、範囲全体の合計が欲しければ省略
limit は 1 ページあたりの時間バケット数を数えるlimit は 1 ページあたりの行を数える(1〜1,000、デフォルト 20)ため、ページ数はデータのある組み合わせの数に依存する
任意の日付範囲で、バケット単位で前方へページ送りstarting_at ≥ 2026 年 1 月 1 日かつ 365 日以内。1 リクエストあたり 31 日以内。バケットを使う場合 ending_at は必須。1m では 24 時間以内
account_ids[]、service_account_ids[]、group_by[]=account_id、group_by[]=service_account_id同じタグ付き ID を使う actor_ids[] と、group_by[]=actor または actor_type。actor.user_id または actor.service_account_id を読む
context_window[]context_windows[](複数形になった)
cost レポートの group_by[]=description(description 文字列付き)廃止。 代わりに構造化されたディメンションでグループ化する — model、cost_type、token_type、context_window、service_tier、inference_geo、speed。すべて 1 回のリクエストに収まる
未知の API キーやワークスペース ID → エラー何もマッチしない。スペルミスした models[] の値も同様
workspace_id: null はデフォルトのワークスペースを意味したデフォルトのワークスペースは実際の wrkspc_ ID を持つ
どちらもない使用量で inference_geo: "not_available"、service_tier: "standard"両方とも null。inference_geos[]=not_available は引き続き geo なしの行にマッチする
コストの service_tier は standard か batch。amount は "123.45" のような形実際のティア。amount は小数 6 桁("123.450000")で、list_amount も加わる
コード実行は usage レポートに存在せず、リクエスト数もないコード実行は model: null の使用量行として現れる。両エンドポイントに requests、usage の行に total_tokens

従来の日次レポートを正確に再現するには: 同じ group_by[] で time_bucket_width=1d をリクエストし、limit=1000 でページを送り、日付順にするため order_by=time&order=asc を追加し、行を starting_at でグループ化して、欠けている日を自分でゼロ埋めします。

デフォルトのワークスペースは null ではなくなりました — グルーピングのコードを更新してください

従来の利用側は、workspace_id: null を「Default Workspace」として特別扱いしていることがよくありました。そのマッピングはもう間違いで、ここでの null は代わりに「それでグループ化していない」を意味します。デフォルトのワークスペースは通常の wrkspc_ ID を持ちますが、List Workspaces は include_default=true を渡さない限りそれを省略するため、行に現れる見慣れない ID がワークスペース表に載っていないことがあります。Get Workspace で解決してください: デフォルトのものは "name": "Default" を返します。

Claude API 以外​

プラットフォーム提供状況違い
Claude Platform on AWS両エンドポイントAdmin API キーの代わりにプラットフォームのベース URL と認証を使用。AWS IAM は ListAccountUsage と ListAccountCost アクションで認可する。各リクエストは、そのエンドポイントの AWS リージョン内のワークスペースだけを対象とする — 組織全体をカバーするにはすべてのリージョンを呼び出す。user_profile_id、claude_tag_category、claude_tag_user_id と Managed Agents のディメンション(agent_id、environment_id、deployment_id、session_id)はすべての行で null
Claude Models on Google Cloud(Anthropic 管理)両エンドポイントGoogle Cloud の認証情報で、組織レベルのベース URL を通じて呼び出す。/usage は usageAnalytics.list の IAM 権限、/cost は costAnalytics.list が必要

その user_profile_id ディメンションは、Claude API 自体で最も興味深いものです: ユーザープロファイルと組み合わせると、この API がプラットフォームや再販業者向けのエンドカスタマー単位のチャージバックになります — エンフォースメントの影響範囲を限定するのと同じ帰属が、各顧客があなたにいくらかかっているかも教えてくれます。

よくある間違い​

間違い実際に起こること
amount をドルとして表示するすべての数値が 100 倍大きくなる。小数 6 桁のセントである
レスポンスの順序のまま行を時系列としてプロットする行は範囲全体で order_by によりランク付けされている。time_bucket_width と order_by=time が必要
curl で --globoff を省くcurl が group_by[] の [] を glob として扱い、リクエストが書いたとおりには送信されない
ゼロ埋めされたバケットを期待するデータのないバケットや組み合わせは行を生成しない。隙間はクライアント側で埋める
これでコスト急増アラートを作るデータは 4〜24 時間遅れで、月末後も 1 週間は改訂される
異なる日に取得した月初来の合計を比較する値は月末の約 7 日後まで改訂される。ending_at をすでに見た data_refreshed_at に固定する
空の結果を「使用量なし」として扱う未知のワークスペース ID、API キー ID、スペルミスしたモデル名は、エラーではなく何もマッチしなくなった
workspace_id: null → 「Default」のマッピングを残すデフォルトのワークスペースは今や実際の wrkspc_ ID を持つ。null は「このディメンションでグループ化していない」を意味する
limit が 1 ページあたりの行数を制限すると仮定するcost_type と token_type は limit を完全に無視する
account_ids[] / service_account_ids[] を使い続けるgroup_by[]=actor または actor_type を伴う actor_ids[] に置き換えられた

クイズ​

Check yourself

0/3
  1. コストの行が cost.amount = "41280.000000"、cost.currency = "USD" で返ってきました。ダッシュボードには何を表示すべきですか?
  2. group_by[]=model で 7 日分の使用量をリクエストし、届いた順に行をプロットして日次の折れ線グラフを期待しました。得られたのは時系列順になっていないものでした。何が足りないのでしょう?
  3. 経理が 10 月の月初来コストを 10 月 2 日、10 月 20 日、そして 11 月 10 日に取得し、10 月 1 日について 3 つの異なる合計を得ました。ドキュメントに記された挙動と一致する説明はどれですか?
Key takeaways
  • 2 つのエンドポイント — /v1/organizations/analytics/usage と /cost — は、どちらも anthropic-beta: analytics-usage-cost-2026-08-24 が必要です。
  • amount を 100 で割ってください。currency が USD と読めても、小数 6 桁のセントです。
  • グループ化しない限りディメンションは null で、データのない組み合わせは行をまったく生成しません — そのためクライアント側でゼロ埋めしてください。
  • デフォルトはランク順: 本物の時系列には time_bucket_width と order_by=time の両方が必要です。
  • 鮮度は 4〜24 時間で、月末から約 7 日間は改訂されます。これは帰属とチャージバックのためのインフラであり、アラート用ではありません。
  • api_key_ids[](キーが認証したもの)と actor_ids[](キーに帰属するもの)は異なる問いに答えます — 意識して選んでください。
  • タイプミスはもうエラーになりません。未知のワークスペース、キー、モデル名は、黙って何もマッチしません。

次へ​