この記事は Qiita Advent Calendar 2025 - 時系列データ の5日目の記事です。
今日は時系列データとして AWS Cloud Watch のログを使います。
Strands Agents を AWS AgentCore にデプロイしたものを使いました。
ユーザー → API Gateway → Lambda → AgentCore (Claude)
↓
S3 (ツール)
Bedrock Model Invocation Logging
CloudWatch Metricsの標準メトリクス(Invocations や Duration)を見ても、解像度は基本「1分単位」です。しかし、AIエージェントの処理は数秒〜数十秒で終わります。
「ユーザーからの1回のリクエスト」の中で、エージェントがツールを使ったり、再考したりといった個別の挙動を追うには、メトリクスだけでは限界がありました。
そこで今回は、Bedrock Model Invocation Logging を有効化し、AIエージェントの挙動をイベント単位で可視化してみました。
1回のリクエストで何回もLLMは呼ばれる
AIエージェントに1回リクエストを投げると、内部では複数回のLLM呼び出しが発生します。
ユーザー「S3にファイルを保存して」
↓
エージェント: LLM呼び出し①(ツール使用判断・引数生成)
↓
エージェント: S3にファイル書き込み(ツール実行)
↓
エージェント: LLM呼び出し②(結果解釈・回答生成)
↓
ユーザーに回答
「どのリクエストで何回LLMが呼ばれたか」を追跡しよう というのが今回の試みです。
課題:CloudWatch Metricsの1分解像度
当初、AIエージェントのパフォーマンスをCloudWatch Metricsで監視しようとしましたが、うまくいきませんでした。
- 粒度が粗い: CloudWatch Metricsは1分間の集約データ
- 内部挙動が見えない: リクエストからレスポンスまでの時間はわかっても、「その中でBedrockが何回、どれくらいの時間をかけて呼ばれたか」までは分からない
MetricsとLogsの解像度
| データソース | 解像度 | 特徴 |
|---|---|---|
| CloudWatch Metrics | 1分 | 全体傾向把握。個別デバッグには不向き |
| CloudWatch Logs (Lambda) | ミリ秒 | アプリロジックは追えるが、LLMの中身は見えない |
| Bedrock Invocation Logs | イベント単位 | LLMリクエスト毎にトークン数・レイテンシを正確に記録 |
Bedrock Model Invocation Logging
AWS Bedrockには、推論リクエストの詳細をログとして出力する機能があります。
-
Converse,ConverseStream,InvokeModel,InvokeModelWithResponseStreamの操作をイベント単位で記録 - 入力/出力トークン数、レイテンシ、リクエストIDなどをJSON形式で保存
- 出力先はCloudWatch LogsまたはS3を選択可能
設定手順(AWS CLI)
Bedrock Model Invocationを使用するには設定が必要です
1. ロググループの作成
aws logs create-log-group \
--log-group-name /aws/bedrock/model-invocations
2. IAMロールの作成
Trust Policy (trust-policy.json)
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Service": "bedrock.amazonaws.com"
},
"Action": "sts:AssumeRole",
"Condition": {
"StringEquals": {
"aws:SourceAccount": "YOUR_ACCOUNT_ID"
},
"ArnLike": {
"aws:SourceArn": "arn:aws:bedrock:ap-northeast-1:YOUR_ACCOUNT_ID:*"
}
}
}
]
}
Permission Policy (permissions.json)
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"logs:CreateLogStream",
"logs:PutLogEvents"
],
"Resource": "arn:aws:logs:ap-northeast-1:YOUR_ACCOUNT_ID:log-group:/aws/bedrock/model-invocations:*"
}
]
}
ロール作成:
# ロール作成
aws iam create-role \
--role-name BedrockLoggingRole \
--assume-role-policy-document file://trust-policy.json
# ポリシーアタッチ
aws iam put-role-policy \
--role-name BedrockLoggingRole \
--policy-name BedrockLoggingPolicy \
--policy-document file://permissions.json
3. ロギングの有効化
aws bedrock put-model-invocation-logging-configuration \
--logging-config '{
"cloudWatchConfig": {
"logGroupName": "/aws/bedrock/model-invocations",
"roleArn": "arn:aws:iam::YOUR_ACCOUNT_ID:role/BedrockLoggingRole"
},
"textDataDeliveryEnabled": true
}'
実験:10リクエストの追跡
AgentCoreに10回のAPIリクエストを送信しました。
ツールとしては
- S3への入出力
- 時刻の取得
を用意しています。詳しくはレポジトリをみてください。
リクエスト内容
| # | Prompt | タイプ |
|---|---|---|
| 1 | What time is it in Tokyo? | Tool Use |
| 2 | What is 2+2? | Simple |
| 3 | List files in S3 | Tool Use |
| 4 | What time is it in New York? | Tool Use |
| 5 | Write hello world to S3 | Tool Use |
| 6 | What is the capital of Japan? | Simple |
| 7 | List S3 files again | Tool Use |
| 8 | Write a haiku about clouds to S3 | Tool Use |
| 9 | What is 10 times 5? | Simple |
| 10 | What time is it in London? | Tool Use |
取得できたデータ
CloudWatch Logsには以下のようなJSONが記録されます(抜粋):
{
"schemaType": "ModelInvocationLog",
"schemaVersion": "1.0",
"timestamp": "2025-12-04T18:27:02Z",
"accountId": "141633749676",
"region": "ap-northeast-1",
"requestId": "ac52319f-3608-4772-9cf5-053d2d3f8688",
"operation": "ConverseStream",
"modelId": "jp.anthropic.claude-haiku-4-5-20251001-v1:0",
"input": {
"inputTokenCount": 1011
},
"output": {
"outputTokenCount": 31,
"outputBodyJson": {
"stopReason": "end_turn",
"metrics": {
"latencyMs": 1509
}
}
}
}
inputTokenCount, outputTokenCount, latencyMs などがイベント単位で記録されています。
結果
10回のAPIリクエストに対して、合計17回のBedrock呼び出し が発生していました。
- 薄い色のバー: APIリクエスト全体の所要時間(開始→レスポンス)
- 濃い色のバー: その中でのBedrock invocations(LLM処理時間)
- 右側のラベル: 合計所要時間(秒)
ツール呼び出しの際は複数回LLMが呼ばれる
- Simple Query (2+2, 首都, 掛け算) → 1回のBedrock呼び出し
-
Tool Use (時刻取得, S3操作) → 2回のBedrock呼び出し
- 1回目:ツール使用判断・引数生成
- 2回目:ツール結果を受けて回答生成
今回は単純なツール使用だったので多くても2回でした。
まとめ
AIエージェントの挙動はブラックボックスになりがちですが、Bedrock Model Invocation Loggingを有効化することで:
- 正確なコール数の把握: 「10リクエストで17回推論」という実態が把握できます
- コスト構造の透明化: どの処理でトークンを多く消費しているか、イベント単位で特定が可能になります
- デバッグ効率の向上: レスポンスの遅延がLLMの応答によるのか、ツール実行によるのか切り分けが可能になります。
エージェント開発においてもオブザーバビリティは非常に重要になると考えています。Bedrock Model Invocation と時系列データ分析を活用していきたいですね。
参考
明日の Qiita Advent Calendar 2025 - 時系列データ 6日目は @kikuchan98 さんの 「時系列特化のグラフ描画ライブラリ(Timescope)の紹介」です!
