摘要:本文介绍如何通过 LiteLLM AI Gateway 实现 Amazon Bedrock 的实时成本控制、多维成本监控,并结合 AWS Budgets 构建平台级兜底保护,同时利用 AWS 原生安全服务防止 API Key 盗刷。方案覆盖”事前限额 → 事中监控 → 事后兜底 → 安全纵深”四个层面,帮助企业实现 AI 投入可预测、AI 资产不被盗。
Amazon Bedrock 按 Token 计费(输入 Token + 输出 Token),企业在享受 AI 能力的同时面临两大风险:
| 风险类型 | 典型场景 | 后果 |
|---|---|---|
| 成本失控 | 开发者调试时大量调用、Prompt 设计不当导致 Token 爆炸、死循环调用 | 月底收到意外高额账单 |
| 资产被盗 | API Key 泄露、内部人员滥用、凌晨异常调用 | 巨额费用 + 数据泄露风险 |
核心诉求:需要一套方案同时解决”花多少钱可控”和”谁在花钱可见”两个问题,并在应用层失效时有平台级兜底。
┌─────────────────────────────────────────────────────────────────────┐
│ 多层纵深防御体系 │
├─────────────────────────────────────────────────────────────────────┤
│ │
│ ┌──────────┐ ┌──────────────┐ ┌────────────────────────┐ │
│ │ 开发者 │───→│ LiteLLM Proxy │───→│ Amazon Bedrock │ │
│ │ 应用服务 │ │ │ │ (VPC Endpoint 内网访问) │ │
│ └──────────┘ │ • Virtual Key │ └────────────────────────┘ │
│ │ • Tag 花费追踪 │ │
│ │ • Rate Limit │ ┌────────────────────────┐ │
│ │ • Budget 限额 │───→│ PostgreSQL │ │
│ └──────────────┘ │ (花费 & 审计记录) │ │
│ └────────────────────────┘ │
│ │
│ ┌───────────────────────────────────────────────────────────────┐ │
│ │ AWS 原生安全与兜底层 │ │
│ │ │ │
│ │ 💰 成本兜底:AWS Budgets + Budget Action → 自动 Deny │ │
│ │ 🛡️ 网络层:VPC Endpoint + Source VPC 限制 + Security Group │ │
│ │ 🔑 身份层:IAM 最小权限 + Key 分离 + Secrets Manager │ │
│ │ 🔍 检测层:CloudTrail + GuardDuty + CloudWatch 异常检测 │ │
│ └───────────────────────────────────────────────────────────────┘ │
│ │
└─────────────────────────────────────────────────────────────────────┘
LiteLLM 的 Virtual Key 机制可以为每个用户/团队/应用创建独立的 API Key,并设置精确的预算上限和速率限制。超限请求被实时拒绝,无需等待 AWS Billing 延迟。
前置条件:本文假设你已部署 LiteLLM Proxy,部署方式参考 LiteLLM 生产级部署:基于 AWS ECS/EKS 的 AI Gateway 架构。
curl -X POST 'http://***litellm-gateway***.com/key/generate' \
-H 'Authorization: Bearer sk-1234' \
-H 'Content-Type: application/json' \
-d '{
"models": ["bedrock-claude-opus-4-6", "bedrock-claude-opus-4-7"],
"key_alias": "game1-qa",
"max_budget": 50,
"budget_duration": "1mo",
"tpm_limit": 100000,
"rpm_limit": 60,
"metadata": {"tags": ["team:qa", "project:game1"]}
}'LiteLLM 支持灵活的 Budget Window 机制,可同时设置多个时间窗口的预算限制:
| 配置项 | 说明 | 示例 |
|---|---|---|
| Max Budget (USD) | Key/User/Team 的总预算上限,超限立即拒绝 | $50 |
| Budget Duration | 预算重置周期 | 1mo(每月重置) |
| Budget Windows - Daily | 每日预算上限,每天 UTC 0 点自动重置 | $5/天 |
| Budget Windows - Monthly | 每月预算上限,每月 1 日自动重置 | $100/月 |
| TPM Limit | 每分钟 Token 数限制,防止瞬时大量消耗 | 100000 |
| RPM Limit | 每分钟请求数限制 | 60 |
多窗口组合策略示例: - 日限 $5 — 防止单日异常消耗(如死循环调用) - 月限 $100 — 控制整体预算 - TPM 100K — 防止瞬时 Token 爆炸
超过任一限额,LiteLLM 立即返回
429 Budget Exceeded,无需等待 AWS Billing 延迟。
Claude Opus 4.6 和 4.7 调用成功,超限后立即被拒绝
通过为 Virtual Key 打上业务标签(Tag),可以在 Dashboard 中按团队、项目、环境等维度查看花费分布。
在 LiteLLM UI 中创建 Key 时,可以直接在 Metadata 中设置 Tags:
也可以通过 API 创建:
# 游戏 QA 团队
curl -X POST 'http://localhost:4000/key/generate' \
-H 'Authorization: Bearer sk-1234' \
-d '{
"models": ["bedrock-claude-opus-4-6", "bedrock-claude-opus-4-7"],
"key_alias": "game1-qa",
"metadata": {"tags": ["team:qa", "project:game1"]},
"max_budget": 50
}'
# 生产服务
curl -X POST 'http://localhost:4000/key/generate' \
-H 'Authorization: Bearer sk-1234' \
-d '{
"models": ["bedrock-claude-opus-4-7"],
"key_alias": "prod-service",
"metadata": {"tags": ["team:prod", "env:production"]},
"max_budget": 200
}'在 LiteLLM Dashboard 中可按 Tag 维度查看花费:
| Tag | 花费 | 成功请求 | Token 消耗 |
|---|---|---|---|
| team:prod | $0.0019 | 2 | 96 |
| team:qa | $0.0059 | 6 | 312 |
| project:game1 | $0.0059 | 6 | 312 |
不同业务线可路由到不同模型版本(QA 用标准版、生产用高配版):
model_list:
- model_name: claude-opus
litellm_params:
model: bedrock/us.anthropic.claude-opus-4-6-v1
tags: ["tier:standard"]
- model_name: claude-opus
litellm_params:
model: bedrock/us.anthropic.claude-opus-4-7
tags: ["tier:premium"]
router_settings:
enable_tag_filtering: true为什么需要兜底? LiteLLM 提供实时限额,但作为应用层组件,存在服务中断、配置错误等风险。AWS Budgets 是平台级服务,即使所有应用层防护失效,它仍然是费用的最后一道防线。
Bedrock 服务产生花费
↓
AWS Billing 按服务汇总花费(有 4-8h 延迟)
↓
AWS Budgets 持续检查:Bedrock 服务花费 vs 预算阈值
↓
├── 达到 80% → 发送告警邮件
└── 达到 100% → 触发 Budget Action
↓
自动给用户附加 Deny Policy
↓
用户再调用 Bedrock → 被拒绝(403)
↓
下个月初自动移除 Deny Policy → 恢复访问
关键安全原理 — IAM Deny 优先原则:AWS 中 Deny
永远优先于 Allow。即使用户有
AmazonBedrockFullAccess,只要附加了 Deny Bedrock
的策略,就100% 无法访问。这是 AWS IAM
的底层机制,不可绕过。
aws iam create-policy \
--policy-name "DenyBedrockAccess" \
--policy-document '{
"Version": "2012-10-17",
"Statement": [{
"Effect": "Deny",
"Action": [
"bedrock:InvokeModel",
"bedrock:InvokeModelWithResponseStream",
"bedrock:Converse",
"bedrock:ConverseStream"
],
"Resource": "*"
}]
}'aws iam create-role \
--role-name "BudgetActionRole" \
--assume-role-policy-document '{
"Version": "2012-10-17",
"Statement": [{
"Effect": "Allow",
"Principal": {"Service": "budgets.amazonaws.com"},
"Action": "sts:AssumeRole"
}]
}'
aws iam put-role-policy \
--role-name "BudgetActionRole" \
--policy-name "BudgetActionPermissions" \
--policy-document '{
"Version": "2012-10-17",
"Statement": [{
"Effect": "Allow",
"Action": ["iam:AttachUserPolicy", "iam:DetachUserPolicy"],
"Resource": "arn:aws:iam::<YOUR_ACCOUNT_ID>:user/brclient"
}]
}'aws budgets create-budget \
--account-id <YOUR_ACCOUNT_ID> \
--budget '{
"BudgetName": "Bedrock-Monthly-Budget",
"BudgetLimit": {"Amount": "10", "Unit": "USD"},
"TimeUnit": "MONTHLY",
"BudgetType": "COST",
"CostFilters": {"Service": ["Amazon Bedrock"]}
}' \
--notifications-with-subscribers '[
{"Notification": {"NotificationType": "ACTUAL", "ComparisonOperator": "GREATER_THAN", "Threshold": 80, "ThresholdType": "PERCENTAGE"},
"Subscribers": [{"SubscriptionType": "EMAIL", "Address": "<YOUR_EMAIL>"}]},
{"Notification": {"NotificationType": "ACTUAL", "ComparisonOperator": "GREATER_THAN", "Threshold": 100, "ThresholdType": "PERCENTAGE"},
"Subscribers": [{"SubscriptionType": "EMAIL", "Address": "<YOUR_EMAIL>"}]}
]' --region us-east-1
aws budgets create-budget-action \
--account-id <YOUR_ACCOUNT_ID> \
--budget-name "Bedrock-Monthly-Budget" \
--notification-type ACTUAL \
--action-type APPLY_IAM_POLICY \
--action-threshold '{"ActionThresholdValue": 100, "ActionThresholdType": "PERCENTAGE"}' \
--definition '{"IamActionDefinition": {"PolicyArn": "arn:aws:iam::<YOUR_ACCOUNT_ID>:policy/DenyBedrockAccess", "Users": ["brclient"]}}' \
--execution-role-arn "arn:aws:iam::<YOUR_ACCOUNT_ID>:role/BudgetActionRole" \
--approval-model AUTOMATIC \
--subscribers '[{"SubscriptionType": "EMAIL", "Address": "<YOUR_EMAIL>"}]' \
--region us-east-1也可通过控制台操作,参考 AWS Budgets Actions 文档。
当花费超过预算后,Budget Action 自动执行:
{
"error": true,
"message": "User: arn:aws:iam::****:user/brclient is not authorized to perform: bedrock:InvokeModelWithResponseStream ... with an explicit deny in an identity-based policy: arn:aws:iam::****:policy/DenyBedrockAccess"
}| 项目 | 说明 |
|---|---|
| 延迟 | Billing 数据有 4-8 小时延迟,不是实时阻断,因此需要 LiteLLM 做实时限额 |
| 恢复 | 每月初自动重置,也可手动移除 Deny Policy 提前恢复 |
| 成本 | 前 2 个 Action-enabled Budget 免费,之后 $0.10/天 |
| 审批 | 可设为 MANUAL 模式,人工审批后才执行 |
即使设置了预算限额,API Key 泄露仍可能在限额内造成损失或数据泄露。以下通过 AWS 原生安全服务构建纵深防御。
通过 VPC Endpoint 确保 Bedrock 流量不经过公网,结合 IAM Condition 限制调用来源:
{
"Version": "2012-10-17",
"Statement": [{
"Effect": "Deny",
"Action": "bedrock:*",
"Resource": "*",
"Condition": {
"StringNotEquals": {"aws:SourceVpc": "vpc-xxxxxxxx"}
}
}]
}效果:即使 API Key 泄露,攻击者从 VPC 外部调用会被 IAM Deny 拦截返回 403。
| AWS 服务 | 用途 |
|---|---|
| CloudTrail | 记录所有 Bedrock API 调用(谁、何时、从哪里) |
| GuardDuty | 检测异常 API 调用模式(异常地理位置、异常时间) |
| CloudWatch Anomaly Detection | 自动发现用量突增 |
| 功能 | 说明 |
|---|---|
| Rate Limiting | 按 Key/User/Team 设置 TPM/RPM 限制 |
| IP 白名单 | allowed_ips 限制 Key 使用来源 |
| 模型白名单 | 每个 Key 只能访问授权的模型 |
| Key 过期 | 设置 duration,到期自动失效 |
| 请求审计 | 所有请求记录到数据库 |
除了 LiteLLM 实时监控外,还可以利用 AWS CloudTrail 记录的 Bedrock API 调用日志,结合 Athena 进行 SQL 分析,再通过 Amazon Quick 实现自然语言查询——无需写 SQL,直接用中文/英文提问即可获得成本洞察。
Bedrock API 调用
↓
CloudTrail 记录每次 InvokeModel 事件(含模型 ID、用户、时间)
↓
日志存储到 S3
↓
Athena 建表(结构化查询层)
↓
┌─────────────────────────────────────────────────┐
│ SQL 分析:Athena 直接查询 │
│ 自然语言分析:Amazon Quick(自然语言查询) │
│ (两者结合,技术人员用 SQL,管理层用自然语言提问) │
└─────────────────────────────────────────────────┘
通过 Athena 直接查询 CloudTrail 日志中的 Bedrock 调用记录,实现按用户、模型、时间维度的成本分析。
CREATE EXTERNAL TABLE cloudtrail_bedrock_logs (
eventTime STRING,
eventSource STRING,
eventName STRING,
userIdentity STRUCT<
type: STRING,
arn: STRING,
accountId: STRING,
userName: STRING
>,
requestParameters STRING,
responseElements STRING,
sourceIPAddress STRING,
userAgent STRING
)
ROW FORMAT SERDE 'org.apache.hive.hcatalog.data.JsonSerDe'
LOCATION 's3://<YOUR_CLOUDTRAIL_BUCKET>/AWSLogs/<ACCOUNT_ID>/CloudTrail/';SELECT
userIdentity.userName AS user_name,
eventName,
COUNT(*) AS call_count,
DATE(from_iso8601_timestamp(eventTime)) AS call_date
FROM cloudtrail_bedrock_logs
WHERE eventSource = 'bedrock.amazonaws.com'
AND eventName IN ('InvokeModel', 'InvokeModelWithResponseStream', 'Converse', 'ConverseStream')
GROUP BY userIdentity.userName, eventName, DATE(from_iso8601_timestamp(eventTime))
ORDER BY call_count DESC;SELECT
json_extract_scalar(requestParameters, '$.modelId') AS model_id,
COUNT(*) AS invocation_count,
COUNT(DISTINCT userIdentity.userName) AS unique_users
FROM cloudtrail_bedrock_logs
WHERE eventSource = 'bedrock.amazonaws.com'
AND eventName = 'InvokeModel'
GROUP BY json_extract_scalar(requestParameters, '$.modelId')
ORDER BY invocation_count DESC;Amazon Quick 支持自然语言提问,将 Athena 中的 CloudTrail 数据接入后,管理者无需编写 SQL,直接用自然语言即可获得成本洞察。
cloudtrail_bedrock_logs 表接入数据后,可以直接在 Amazon Quick 中用自然语言提问:
| 自然语言提问 | Amazon Quick 返回结果 |
|---|---|
| “上周哪个用户调用 Bedrock 最多?” | 自动生成用户调用排行榜 |
| “过去 30 天 Claude 模型的调用趋势” | 生成时间趋势折线图 |
| “哪些 IP 地址在非工作时间调用了 Bedrock?” | 筛选异常时段的来源 IP 列表 |
| “按模型对比本月和上月的调用量变化” | 生成模型维度的环比对比图 |
| “哪个团队的 InvokeModel 调用增长最快?” | 自动计算增长率并排序 |
核心优势:管理层和非技术人员无需学习 SQL,直接用自然语言即可完成成本分析和异常排查。
Amazon Quick 还可以自动生成可视化 Dashboard:
| 维度 | 可视化内容 |
|---|---|
| 时间趋势 | 每日/每周 Bedrock 调用量趋势图 |
| 用户分布 | 各 IAM 用户/角色的调用占比饼图 |
| 模型使用 | 不同模型的调用次数对比柱状图 |
| 异常检测 | 调用量突增的时间点标注 |
| 来源 IP | 调用来源地理分布 |
两者并非二选一,而是结合使用:
| 角色 | 使用方式 | 工具 |
|---|---|---|
| 开发/运维 | 编写精确 SQL 查询,深度排查问题 | Athena |
| 管理层/业务方 | 自然语言提问,快速获取成本概览 | Amazon Quick |
| 定期报表 | 自动生成周报/月报 Dashboard | Amazon Quick 定时刷新 |
| 维度 | LiteLLM(本文主方案) | CloudTrail + Athena | CloudTrail + Amazon Quick |
|---|---|---|---|
| 实时拦截 | ✅ 超限立即拒绝 | ❌ 仅分析 | ❌ 仅分析 |
| 查询方式 | Dashboard 界面 | SQL | 自然语言 |
| 分析深度 | 中 | ✅ 灵活 SQL | ✅ AI 辅助洞察 |
| 使用门槛 | 低 | 需要 SQL 能力 | ⭐ 零门槛(自然语言) |
| 额外成本 | LiteLLM 部署成本 | Athena 查询费用 | Amazon Quick 订阅费 |
| 适用阶段 | 实时管控 | 事后深度分析 | 日常成本洞察 |
推荐组合:LiteLLM 负责实时限额拦截 + CloudTrail + Athena 负责技术深度分析 + Amazon Quick 负责自然语言查询和管理层报表,形成”实时管控 + 深度分析 + 智能洞察”的完整闭环。
| 层次 | 方案 | 作用 | 时效性 |
|---|---|---|---|
| 实时限额 | LiteLLM Virtual Key + Budget | 超限立即拒绝 | 实时 |
| 成本归因 | LiteLLM Virtual Key Tag + Dashboard | 按业务线/团队追踪花费 | 实时 |
| 平台兜底 | AWS Budgets + Budget Actions | 超预算自动阻断 | 4-8h 延迟 |
| 安全防护 | VPC Endpoint + IAM Condition + GuardDuty | 防止 Key 泄露被盗刷 | 实时 |
核心设计原则:LiteLLM 实时拦截 + AWS Budgets 延迟兜底 = 双保险。即使 LiteLLM 服务异常,AWS Budgets 仍能确保费用不超限。