跳到正文
Agent 工程实践LLM Gateway
返回课程/Agent 工程实践
第 15 / 15 章 约 6 分钟

LLM Gateway

统一模型调用、用量、限流和降级。

这个模块在 Agent 里的位置

LLM Gateway 是业务代码和模型供应商之间的统一入口。它决定:

  • 业务代码调用哪个模型抽象。
  • 供应商协议如何适配。
  • 请求是否超时、重试或降级。
  • usage 和成本如何归因。
  • 租户和模型如何限流。
  • 供应商错误如何保留。

如果没有 LLM Gateway,业务代码会逐渐和某个供应商强耦合。

先记住几个概念

概念含义为什么重要
ModelKindfast / main / visual 等抽象模型业务不绑定供应商
Provider adapter供应商协议适配换模型不改业务
Usage输入、输出、缓存 token成本归因
Quota租户或模型级配额控制资源
Rate limit请求频率限制保护下游
Fallback降级模型降低故障影响
Provider error供应商原始错误保留排障信息

从一个真实问题开始:换一个模型,业务代码改了 40 处

一个系统最初直接调用某个模型供应商:

await provider.chat({
    model: 'vendor-main-model',
    messages,
});

后来要做三件事:

  1. 换供应商。
  2. 增加便宜模型处理简单任务。
  3. 支持图片理解。

结果:

  • 40 处业务代码写死了模型名。
  • 20 处处理了供应商特有错误。
  • 10 处自己估算 token。
  • 5 处无法知道真实成本。

根因是业务层直接理解了供应商细节。

网关应该提供的接口

业务层只关心:

type ModelRequest = {
    modelKind: 'fast' | 'main' | 'visual';
    messages: Message[];
    tools?: ToolDefinition[];
    timeoutMs: number;
    runId: string;
};

网关负责:

  1. 将 modelKind 映射到具体供应商模型。
  2. 处理认证和 endpoint。
  3. 适配请求格式。
  4. 统一超时和重试。
  5. 归一 usage。
  6. 记录 provider error。

模型路由

任务模型原因
检索规划fast简单、低延迟
综合分析main强推理
图片理解visual多模态
引用校验fast结构化检查

模型路由不能写死在业务代码里,应该由网关配置:

{
    "fast": {
        "provider": "a",
        "model": "model-a"
    },
    "main": {
        "provider": "b",
        "model": "model-b"
    },
    "visual": {
        "provider": "c",
        "model": "model-c"
    }
}

这样换供应商只改配置,不改业务。

usage 和 cost

真实 token 和 cost 只能来自模型响应。

不能由工具层或前端自行估算。

一个 usage 记录:

{
    "runId": "run-9f27",
    "turnId": "turn-103",
    "modelKind": "main",
    "provider": "provider-b",
    "usage": {
        "inputTokens": 48200,
        "outputTokens": 1800,
        "cacheReadTokens": 12000,
        "cacheWriteTokens": 3000
    },
    "cost": {
        "input": 0.048,
        "output": 0.018,
        "cacheRead": 0.002,
        "cacheWrite": 0.003,
        "total": 0.071
    },
    "latencyMs": 4200,
    "usageMissing": false
}

如果 provider 没返回 usage:

{
    "usageMissing": true
}

不要伪造成 0。

数据库设计

create table agent_model_usage (
  id bigint primary key,
  run_id bigint not null,
  turn_id bigint not null,
  model_kind text not null,
  provider text not null,
  input_tokens bigint,
  output_tokens bigint,
  cache_read_tokens bigint,
  cache_write_tokens bigint,
  total_cost numeric,
  usage_missing boolean not null,
  latency_ms int not null,
  created_at timestamptz not null
);

create index agent_model_usage_run_idx
  on agent_model_usage (run_id, created_at);

用途:

  1. 按 run 归因成本。
  2. 比较模型质量、延迟和成本。
  3. 发现异常调用。
  4. 支撑租户计费。

限流和降级

在峰值 500 QPS、10 万 session / 天的规模下,网关至少要有:

  1. 租户级限流。
  2. 模型级配额。
  3. 熔断。
  4. 降级策略。
  5. 超时控制。

降级要谨慎:

任务是否可降级原因
简单检索规划可以低风险
报告综合谨慎质量影响大
引用校验不建议影响可信度
视觉分析视情况需要多模态能力

不要为了省钱把关键校验任务降级到弱模型。

常见工程错误

错误实际后果正确做法
业务直连供应商难替换、难观测统一网关
业务写死模型名换模型要改代码modelKind 抽象
usage 丢失不标记成本失真usageMissing
所有任务用 main成本高模型路由
供应商错误被吞排障困难保留 provider error
没有租户限流单租户拖垮系统per-tenant quota

上线前检查

  1. 密钥不出网关。
  2. 模型路由显式。
  3. usage 可归因到 run。
  4. usage missing 显式标记。
  5. 有租户级限流。
  6. 有超时和熔断。
  7. 模型变更有质量、延迟和成本对比。