AWSを利用していると、気になるのが毎月のコストですね。
本記事では、AWS Cost Explorer API + Claude 3 Haiku (Amazon Bedrock) を用いて、
AIによるコストアドバイスがもらえないかと思い、試してみました。
やりたいことは以下の通りです。
・AWS CLI/Pythonで月次コストを自動取得
・Claude 3 Haiku にデータを渡し、コスト削減や構成改善のアドバイスを受け取る
・エンジニア目線で改善ポイントの参考にする
今回Claude 3 Haiku を使いますが、モデルアクセスを有効化やAWS CLI のコンフィグファイル設定などは割愛します。
スクリプト全体(Python)
以下のコードで、コストの取得からAIによる提案までが完結します。
import boto3
import datetime
import json
# === 1. AWSコストデータ取得 ===
def get_monthly_costs(start_date, end_date):
ce = boto3.client('ce')
response = ce.get_cost_and_usage(
TimePeriod={
'Start': start_date,
'End': end_date
},
Granularity='MONTHLY',
Metrics=['UnblendedCost'],
GroupBy=[
{'Type': 'DIMENSION', 'Key': 'SERVICE'}
]
)
results = {}
for group in response['ResultsByTime'][0]['Groups']:
service = group['Keys'][0]
cost = float(group['Metrics']['UnblendedCost']['Amount'])
results[service] = cost
return results
# === 2. Claude向けプロンプト生成 ===
def build_prompt(cost_data):
prompt = "以下は、あるAWSアカウントの今月のサービス別コストです。\n\n"
for service, cost in cost_data.items():
prompt += f"- {service}: ${cost:.2f}\n"
prompt += (
"\nこのコストデータをもとに、以下を含む改善提案をください:\n"
"- 無駄なコストが発生している可能性があるサービス\n"
"- リザーブドインスタンスやSavings Plansの適用検討\n"
"- サービス統合・構成変更によるコスト削減案\n"
"- 可能であればアーキテクチャ改善も含めたアドバイス\n"
)
return prompt
# === 3. Claude 3 Haikuへ送信(Messages API) ===
def call_bedrock_claude(prompt):
bedrock = boto3.client(
service_name="bedrock-runtime",
region_name="ap-northeast-1" # 対応リージョン(例: us-east-1)
)
body = {
"messages": [
{
"role": "user",
"content": prompt
}
],
"anthropic_version": "bedrock-2023-05-31", # anthropic バージョン
"max_tokens": 800, # 生成されるテキストの最大長を指定
"temperature": 0.5 # レスポンスに注入されるランダム性の量
}
response = bedrock.invoke_model(
modelId="anthropic.claude-3-haiku-20240307-v1:0",
body=json.dumps(body),
contentType="application/json",
accept="application/json"
)
response_body = json.loads(response['body'].read())
return response_body["content"][0]["text"]
# === 実行 ===
if __name__ == "__main__":
today = datetime.date.today()
start = today.replace(day=1).isoformat()
end = today.isoformat()
print(f"[+] Fetching cost data from {start} to {end}...")
cost_data = get_monthly_costs(start, end)
prompt = build_prompt(cost_data)
print("\n[+] Prompt for Bedrock:\n")
print(prompt)
print("\n[+] Asking Bedrock (Claude 3 Haiku)...\n")
result = call_bedrock_claude(prompt)
print(result)
上記スクリプトを実行してみると。
[+] Fetching cost data from 2025-05-01 to 2025-05-19...
[+] Prompt for Bedrock:
以下は、あるAWSアカウントの今月のサービス別コストです。
- AmazonEC2: $132.45
- AmazonS3: $23.67
- AWSLambda: $0.00
...
このコストデータをもとに、以下を含む改善提案をください:
...
[+] Asking Bedrock (Claude 3 Haiku)...
→ Claudeからの自然言語による提案が返ってきます
終わりに
Bedrock経由でClaudeにコストデータを渡し、
回答が返ってくることは実現できました。
想定はしていましたが、今月のコスト感だけでより良い改善提案内容は返ってこないので、
過去の月別コストデータや、Cloudwatchで取得している各インスタンスのリソース状況等の情報も渡してみて
より良い改善案が返ってくるか検証してみようと思います。
【参考記事】
https://aws.amazon.com/jp/builders-flash/202405/awsgeek-amazon-bedrock/
https://docs.aws.amazon.com/ja_jp/bedrock/latest/userguide/getting-started.html
https://blog.denet.co.jp/cloudwatch-cpu-graph-bedrock-analysis/