コスト集計
コストの値は、どこから来たかを言えて初めて意味があります。ここにあるのは、トークン数から画面上の数字までの、すべての段です。
値付けは取り込み時に一度だけ
モデル id とトークン数を持つスパンが届くと、mcpd はそのモデルを価格表で 引き、その呼び出しの費用を計算して、結果をスパンに保存します。読み出しの ときに計算し直すものは、何もありません。
これが、このページで重要な決定です。価格は変わります。もしコストを、 クエリの時点で、その日たまたま読み込まれていた価格表から導いていたら、 来月の値下げが先月のコストを黙って書き換え、あなたが誰かに報告した数字は、 その人が確かめに行ったときにはもう無い、ということになります。取り込み時に 値付けすることで、その値は、呼び出しの時点で正しかった単価に対して固定 されます。保存されたコストは、それを生んだ価格表の id も記録するので、値 からその裏にある単価までたどれます。
すでにコストを持って届いたスパンは、届いたそのままにされます。プロバイダー
が実際の金額を返し、それをあなたが記録したなら、mcpd はあなたの値を残し、
その上から値付けし直すことはしません。is_estimated フラグが、
この 2 つを分けます。mcpd が価格表から導いたものは推定として印が付きます。
実際に推定だからです。
単価は 100 万トークンあたり
価格表の単価はどれも、100 万トークンあたりの通貨単位です。どのプロバイダーも
その形で公表しています。価格ページから写した単価は、そのまま価格表に入り
ます。午前 3 時に割り算を間違える余地はありません。1 つの計測項目の計算は
tokens × rate ÷ 1,000,000 です。
コストは実行ではなく、ステップに載ります
モデル呼び出しは、それぞれ自分の値を持ちます。実行の合計はスパンの和で あり、mcpd はカウンターを足していくのではなく、スパンが 1 つ届くたびに、 スパンから合計を計算し直します。スパンは順序が入れ替わって届き、リトライされ、 その場で更新されます。足していく合計は、この 3 つのどれでもずれます。下に 並ぶ行と一致しない見出しの数字は、そのページの他のすべての数字への信頼を 壊します。
- agent support_agent fail
- model chat
- tool returns_policy
- model chat
- tool returns_policy
- model chat
- tool returns_policy
The model called one tool three times and never answered. That is visible in four seconds here, and invisible in a log file.
上の 3 つのモデル呼び出しは、$0.00015、$0.00018、$0.00021 と値付けされて います。ヘッダーにある実行の合計は、それらの和であって、それ以外は含み ません。ツール呼び出し、メモリーの参照、ガードレールはトークンを消費して いないので、コストを持たず、合計にも寄与しません。
計測項目
モデル呼び出しは、1 つのトークン数ではありません。プロバイダーは複数の 計測項目をそれぞれ違う単価で課金し、価格表は、その 1 つずつに単価を与えます。
| 単価 | 対象 | 価格表にない場合 |
|---|---|---|
input | 通常の入力トークン。 | 必須です。 |
output | 通常の生成トークン。 | 必須です。 |
cache_read | プロンプトキャッシュから返されたトークン。 | input で課金します。 |
cache_write | プロンプトキャッシュに書き込まれたトークン。 | input で課金します。 |
cache_write_5m | 5 分キャッシュへの書き込み。プロバイダーが TTL ごとに値付けする場合です。 | cache_write、次いで input にフォールバックします。 |
cache_write_1h | 1 時間キャッシュへの書き込み。 | cache_write、次いで input にフォールバックします。 |
audio_input | 音声の入力トークン。 | input で課金します。 |
audio_output | 音声の出力トークン。 | output で課金します。 |
reasoning | 隠れた推論トークン。プロバイダーがこれを別に課金する場合です。 |
フォールバックはありません。プロバイダーが別に text の
数も報告していないかぎり、出力の合計の一部として
output で課金されます。主要なプロバイダーの課金の仕方が
それです。下を見てください。
|
キャッシュされたトークンは、一度だけ課金されます
請求額を多く見せる古典的なやり方は、キャッシュされたトークンを二度課金する ことです。一度はキャッシュの単価で、もう一度は、それをすでに含んでいる報告 済みの入力合計の一部として数えるのです。そのため、プロバイダーが内訳を報告 している場合は、その内訳が優先されます。mcpd は各計測項目をそれぞれの単価 で値付けし、残りだけを通常の入力の単価で課金します。
入力トークン 100 万、うち 90 万がキャッシュから読まれたと報告する
claude-sonnet-4 の呼び出しは、同梱の価格表に対して次のように
値付けされます。
- キャッシュ読み取り 900,000 を 100 万あたり $0.30 で、$0.27。
- 残りの入力トークン 100,000 を 100 万あたり $3.00 で、$0.30。
- 入力のコストは $0.57。報告された合計だけから出したなら $3.00 に なっていたところです。
プロバイダーが明示的な text の数を返す場合、その数がそのまま
残りとして使われます。返さない場合、残りは、報告された合計から計測項目の
フィールドをすべて引いたものです。
ここに、名前を挙げておく価値のある穴が 1 つ残ります。価格表が単価を持たない
計測項目は、残りの一部としてしか課金されないので、プロバイダーが
text の数も送っていた場合は、まったく課金されません。推論
トークンは、価格表がそれ自身の単価を与えていないときに、いつでもここに
落ちます。単価を 1 つ書けば直ります。画像トークンは常にここに落ちます。
価格表に与えられる画像の単価が無いからです。マルチモーダルの比重が大きい
処理では、この値は正確な額ではなく、低めの額として読んでください。
未知のモデルにはコストがありません。コストがゼロなのではありません
価格表にそのモデルの単価が無ければ、mcpd はコストのフィールドをまったく 付けずにスパンを保存します。ゼロを保存することはしません。
ゼロは主張です。この呼び出しは無料だった、という主張です。無いことは告白 です。この呼び出しの費用は分からない、という告白です。この 2 つは違う判断に つながり、後者を前者として報告する道具は、請求について嘘をついています。 同じ規則は読み出し経路にも通っています。スパンの合計が何も出ない実行は、 コストがゼロではなく、コストの値を持たないまま返されます。だからコストの 列が空欄なら、それは値付けされていないという意味であり、 無料という意味には決してなりません。
実務上の帰結は、身につけておく価値があります。価格表に無いモデルは、どの
合計からも抜けます。その支出は /v1/api/analytics/cost に現れ
ず、その実行は、正の min_cost フィルターから除外されます。週の
合計が低すぎるように見えるときは、たいてい暇な週だったのではなく、解決でき
ていないモデル id があります。
モデル id の解決
スパンに載る id は、あなたのクライアントが送ったそのままであり、 クライアントはそこに飾りを付けます。ゲートウェイはベンダー名を前に付け、 クラウドはリージョンを前に付け、プロバイダーはリリース日を後ろに留めます。 価格表は素のモデル名を鍵にしているので、検索は 4 つを順に試し、最初に当たった ところで止まります。
| 段階 | 例 |
|---|---|
| 与えられたままの id、大文字小文字をそろえたもの | GPT-4o は gpt-4o に当たります |
| 最後のスラッシュより後の部分 | openai/gpt-4o は gpt-4o に当たります |
| クラウドの id の、ドットで区切られた末尾 | us.anthropic.claude-sonnet-4 は
claude-sonnet-4 に当たります
|
| 末尾の日付を取り除いた id。接頭辞は、有っても無くてもかまいません | openai/gpt-4o-2024-08-06 は gpt-4o に当たります
|
-YYYY-MM-DD と -YYYYMMDD のどちらの接尾辞も認識
します。4 つの段階すべてに外れることは、エラーではなく普通の結果です。上に
書いたとおり、コストが無いという意味になります。
同梱の価格表
mcpd は小さな組み込みの価格表を持っています。設定を 1 つもしなくても
docker run が実際の値を出すためです。名前は
builtin、通貨は USD で、そこから出たコストはすべて、その名前を
記録します。
| モデル | 入力 | 出力 | キャッシュ読み取り | キャッシュ書き込み、5 分 | キャッシュ書き込み、1 時間 |
|---|---|---|---|---|---|
claude-opus-4 | 15.00 | 75.00 | 1.50 | 18.75 | 30.00 |
claude-opus-4-1 | 15.00 | 75.00 | 1.50 | 18.75 | 30.00 |
claude-opus-4-5 | 5.00 | 25.00 | 0.50 | 6.25 | 10.00 |
claude-sonnet-4 | 3.00 | 15.00 | 0.30 | 3.75 | 6.00 |
claude-sonnet-4-5 | 3.00 | 15.00 | 0.30 | 3.75 | 6.00 |
claude-haiku-4-5 | 1.00 | 5.00 | 0.10 | 1.25 | 2.00 |
claude-3-5-haiku | 0.80 | 4.00 | 0.08 | 1.00 | 1.60 |
gpt-4o | 2.50 | 10.00 | 1.25 | 入力と同じ | 入力と同じ |
gpt-4o-mini | 0.15 | 0.60 | 0.075 | 入力と同じ | 入力と同じ |
gpt-4.1 | 2.00 | 8.00 | 0.50 | 入力と同じ | 入力と同じ |
gpt-4.1-mini | 0.40 | 1.60 | 0.10 | 入力と同じ | 入力と同じ |
o3 | 2.00 | 8.00 | 0.50 | 入力と同じ | 入力と同じ |
o4-mini | 1.10 | 4.40 | 0.275 | 入力と同じ | 入力と同じ |
gemini-2.5-pro | 1.25 | 10.00 | 0.31 | 入力と同じ | 入力と同じ |
gemini-2.5-flash | 0.30 | 2.50 | 0.075 | 入力と同じ | 入力と同じ |
text-embedding-3-small | 0.02 | 0.00 | 入力と同じ | 入力と同じ | 入力と同じ |
text-embedding-3-large | 0.13 | 0.00 | 入力と同じ | 入力と同じ | 入力と同じ |
100 万トークンあたりの USD で、第三者のモデルカタログと最後に突き合わせた
時点の価格表の状態です。その日付は、価格表が as_of として記録
しています。Anthropic の項目が両方のキャッシュ書き込み単価を持っているのは、
デーモンが 1 時間の単価から 5 分の単価へフォールバックするからで、長いほうを
省いた価格表は、黙って過少請求になります。OpenAI はキャッシュへの書き込みに
課金しないので、そこでのキャッシュ書き込みは入力の単価で計算します。
gemini-2.5-flash は、音声入力の単価 1.00 も持っています。それ
以外の項目は、音声をテキストの単価で値付けします。
claude-haiku-4 はありません。Anthropic が提供している id は
claude-haiku-4-5 であり、何にも解決しない id は、推測せずに
未値付けのままにします。
これは公開された定価であって、あなたの価格ではありません。交渉した単価が ある場合や、この表に無いモデルを動かしている場合、mcpd が見せる数字は推定 であり、推定として読むべきものです。価格表が短いのは意図したことです。長い 表は、より多くの箇所で古びていき、それに値するより強い正確さの印象を 与えます。
自分の価格表を渡すためのコマンドラインのフラグは、まだありません。価格表は
サーバーの状態の一部で、今のところ差し替える方法は、mcpd をライブラリとして
組み込み、AppState::with_price_book に 1 つ渡すことです。価格表
は、id と、ISO 4217 の通貨と、モデル id から単価への対応表です。そこから出た
値にはすべて価格表の id が刻まれるので、後から 2 つの価格表を見分けられます。
1 つのプロジェクトの中では、価格の通貨をそろえてください。mcpd は実行の
スパンをそのまま足し合わせ、通貨の換算はしません。
使った金額を読み出す
GET /v1/api/analytics/cost は、ある期間で金額がどこに使われた
かに答えます。表計算ソフトへ何かを書き出す必要はありません。
curl -s 'http://localhost:4317/v1/api/analytics/cost?from=-7d&group_by=model' | パラメーター | 意味 |
|---|---|
from、to | 期間。RFC 3339、または相対表記の短縮形です。既定は、今を終端とする 直近 7 日間です。 |
group_by |
既定は model。ほかに provider、
entity_name、environment、
status、session_id、user_id、
service_name、name が使えます。
|
bucket | 30s、5m、1h、1d の
いずれか。省略すると合計だけになり、指定すると合計に加えて時系列も
返ります。
|
project | どのプロジェクトを読むか。既定は、デーモンの既定のプロジェクトです。 |
どこに使われたか
# 先週の支出を、モデル別に。
curl -s --get http://localhost:4317/v1/api/analytics/cost \
--data-urlencode 'from=-7d' \
--data-urlencode 'group_by=model'
# 同じ週を日ごとの時系列で。変わった日が見えます。
curl -s --get http://localhost:4317/v1/api/analytics/cost \
--data-urlencode 'from=-7d' \
--data-urlencode 'group_by=model' \
--data-urlencode 'bucket=1d' import { Mcpd } from '@mcpd/sdk'
const mcpd = new Mcpd()
const spend = await mcpd.analyticsCost({
from: '-7d',
to: '-0s',
groupBy: 'model',
bucket: '1d',
})
console.log(`${spend.currency} ${spend.totalCost.toFixed(4)} over the window`)
for (const group of spend.groups) {
console.log(group.key, group.totalCost, group.inputTokens, group.outputTokens)
} from mcpd import Mcpd
mcpd = Mcpd()
spend = mcpd.analytics_cost("-7d", "-0s", group_by="model", bucket="1d")
print(f"{spend.currency} {spend.total_cost:.4f} over the window")
for group in spend.groups:
print(group.key, group.total_cost, group.input_tokens, group.output_tokens) グループは大きい順に返り、上限は 100 行です。バケットに分けた時系列の上限は 5,000 点です。
レスポンス
{
"from": "2026-08-20T09:00:00Z",
"to": "2026-08-27T09:00:00Z",
"currency": "USD",
"total_cost": 12.418264,
"groups": [
{
"key": "claude-sonnet-4",
"count": 1841,
"error_count": 12,
"total_cost": 9.612055,
"input_tokens": 2903118,
"output_tokens": 214477,
"latency": { "mean": 1840.2, "max": 24193.0 }
},
{
"key": "gpt-4o-mini",
"count": 6204,
"error_count": 3,
"total_cost": 2.806209,
"input_tokens": 9114882,
"output_tokens": 388310,
"latency": { "mean": 612.4, "max": 8801.0 }
}
]
} count に、細かい点が 1 つあります。model、
provider、entity_name でまとめる場合はスパンを
読むので、count はモデル呼び出しの数です。それ以外でまとめる
場合は実行の射影を読むので、count は実行の数です。どちらも役に
立ちますが、同じ数ではありません。片方をもう片方と比べることが、ここで
いちばんしやすい間違いです。
このレスポンスの、グループごとのレイテンシは、平均と最大だけを持ちます。
パーセンタイルは GET /v1/api/analytics/summary から得られます。
こちらが、期間全体で計算します。
次に読むもの
コストは実行の一覧の 1 列であり、調査が実際に始まるのは、その一覧です。
実行を探す が
min_cost と、支出による並べ替えを扱っています。値付けの前に
ペイロードが捨てられているせいで数字がおかしく見える場合は、
サンプリング を見て
ください。そもそも何が記録されるかを決めているのは、こちらです。この
ページに出てくるフィールドはすべて、
データモデル
に載っています。