API Key 池化
API Key 池化允许你为同一个提供商配置多个 API Key,通过加权轮询 (Weighted Round-Robin) 分配请求,并在遇到限流或故障时自动切换到其他可用 Key。
何时使用
- 高并发场景:单个 Key 的速率限制不够用,需要多个 Key 分担流量
- 团队共享:每个成员使用自己的 Key 额度,分摊费用
- 免费额度叠加:多个免费账户的 Key 轮流使用
- 高可用:某个 Key 失效时自动切换到其他 Key,避免中断
- 测试与生产分离:不同权重分配正式 Key 与测试 Key 的使用比例
操作指南
添加 API Key
- 打开 设置 → 提供商管理
- 选择目标提供商(如 OpenAI)
- 找到 API Key 池 区域
- 点击 添加 Key 按钮
- 填写信息:
| 字段 | 必填 | 说明 |
|---|---|---|
| API Key | 是 | Key 值或环境变量引用($ 开头) |
| 标签 | 否 | 便于识别的名称,如「生产 Key #1」「测试 Key」 |
| 权重 | 否 | 1-100,默认为 1,数值越大被选中的概率越高 |
- 点击 确认 添加
设置权重
- 在 API Key 列表中找到目标 Key
- 修改 权重 值(1-100)
- 权重决定了该 Key 被选中的相对概率
启用/禁用单个 Key
- 在 API Key 列表中找到目标 Key
- 切换 启用 开关
- 禁用的 Key 不会被轮询选中,但配置保留
删除 Key
- 在 API Key 列表中找到目标 Key
- 点击 删除 按钮
- 确认删除(此操作不可恢复)
可配置项参考
| 配置项 | 类型 | 默认值 | 范围 | 说明 |
|---|---|---|---|---|
| API Key | 字符串 | (空) | -- | Key 值或 $ENV_VAR 引用 |
| 标签 | 字符串 | (空) | -- | 用于区分不同 Key 的备注名称 |
| 权重 | 整数 | 1 | 1-100 | 加权轮询的权重值 |
| 启用状态 | 布尔 | true | -- | 是否参与轮询 |
| 排序 | 整数 | 0 | -- | 列表显示顺序 |
行为说明
加权轮询 (Weighted Round-Robin)
Key 池中的每个 Key 根据其权重占据一定数量的「槽位」。Elftia 按固定顺序轮流使用这些槽位,从而实现按权重比例分配请求。
权重分配示例:
假设有 3 个 Key,权重分别为 3、2、1(总权重 = 6):
| Key | 权重 | 占比 | 每 6 次请求被选中次数 |
|---|---|---|---|
| Key A | 3 | 50% | 3 次 |
| Key B | 2 | 33% | 2 次 |
| Key C | 1 | 17% | 1 次 |
轮询顺序:A → A → A → B → B → C → A → A → A → B → ...
等权重示例:
3 个 Key 权重都为 1(总权重 = 3),则严格轮流:A → B → C → A → B → C → ...
会话亲和性 (Session Affinity)
同一个聊天会话内的所有请求会绑定到同一个 API Key。这个设计有两个重要原因:
- Prompt 缓存:部分提供商(如 Anthropic)支持 Prompt Cache,同一 Key 的连续请求可以命中缓存,显著降低延迟和成本
- 一致性:避免在同一对话中频繁切换 Key 导致的速率限制计数重置
会话绑定在以下情况下会被重新分配:
- 当前绑定的 Key 被禁用或删除
- 当前绑定的 Key 因错误进入冷却期
- 会话结束(关闭或删除)
自动故障转移
当请求遇到错误时,Key 池会根据错误类型采取不同的应对策略:
速率限制 (429/529)
收到 HTTP 429(速率限制)或 529(服务过载)响应时:
- 将当前 Key 放入 冷却期
- 自动切换到池中下一个可用 Key
- 使用新 Key 重试请求
冷却机制:
| 连续失败次数 | 冷却时长 | 计算公式 |
|---|---|---|
| 第 1 次 | 60 秒 | 60s x 2^0 |
| 第 2 次 | 120 秒 | 60s x 2^1 |
| 第 3 次 | 240 秒 | 60s x 2^2 |
| 第 4 次 | 480 秒 | 60s x 2^3 |
| 第 5 次及以上 | 900 秒(上限) | min(60s x 2^(n-1), 900s) |
冷却期间该 Key 不会被轮询选中。冷却结束后自动恢复可用。如果一次请求成功,该 Key 的连续失败计数器会被重置。
认证失败 (401/403)
收到 HTTP 401(未授权)或 403(禁止访问)响应时:
- 该 Key 被 永久禁用(数据库中标记为 disabled)
- 自动切换到下一个可用 Key
- 在设置界面中,该 Key 会显示为禁用状态
这是因为认证错误通常表示 Key 本身已失效(过期、被撤销、额度耗尽),不太可能通过等待恢复。
故障转移流程图
请求发送
|
v
使用会话绑定的 Key
|
+---> 成功 ---> 重置冷却计数器 ---> 返回响应
|
+---> 429/529 (限流)
| |
| v
| 当前 Key 进入冷却期
| (60s 起步, 指数退避, 上限 15 分钟)
| |
| v
| 池中是否有其他可用 Key?
| | |
| 是 否
| | |
| v v
| 切换到新 Key 请求失败, 返回错误
| 重新绑定会话 (所有 Key 均不可用)
| |
| v
| 用新 Key 重试
|
+---> 401/403 (认证失败)
|
v
永久禁用该 Key
|
v
池中是否有其他可用 Key?
| |
是 否
| |
v v
切换到新 Key 请求失败, 返回错误
重新绑定会话
Key 池与提供商级 API Key 的关系
- 当提供商同时配置了提供商级 API Key(Provider 配置中的
api_key字段)和 Key 池时,Key 池优先 - 如果 Key 池为空(没有任何条目),则使用提供商级 API Key
- 建议使用 Key 池替代提供商级 API Key,以获得负载均衡和故障转移能力
Troubleshooting
| 问题 | 可能原因 | 解决方案 |
|---|---|---|
| 所有 Key 都在冷却中,请求失败 | 所有 Key 同时触发了速率限制 | 等待冷却期结束(最长 15 分钟),或添加更多 Key 增大池容量 |
| 某个 Key 从不被选中 | 权重为 0 或其他 Key 权重远大于它 | 检查权重设置,确保至少为 1 |
| 某个 Key 自动变为禁用 | 收到了 401/403 认证错误 | 检查 Key 是否过期或被撤销,在提供商官网确认 Key 状态,修复后手动重新启用 |
| Key 池配置正确但请求仍使用旧 Key | 会话亲和性绑定了旧 Key | 开启新的聊天会话,或等待旧 Key 冷却后系统自动重新绑定 |
| 添加 Key 后未立即生效 | Key 缓存未刷新 | 保存配置后重试,系统会自动刷新缓存 |
| 环境变量 Key 无法解析 | 变量名错误或未设置 | 确认 $ 后的变量名与系统中设置的完全一致,注意大小写 |
| 冷却时间过长 | 连续多次触发限流导致指数退避 | 减少请求频率,或添加更多 Key 分散负载。冷却上限为 15 分钟 |
| 同一会话切换了 Key | 原绑定 Key 进入冷却或被禁用 | 这是正常行为,系统会自动选择最优的可用 Key |