📎 配套脚本附件正文未内嵌 · 共 5 个 · 点开可在线查看
📚 另需公共库(正文未重复内嵌,点名字直接看):_bootstrap.py、_config.py
📂 查看全部 761 个脚本附件 →
⚠️ 脚本内含明文凭据(与本页正文一致),请勿在公网环境直接运行。
集成环境 · 网关

LiteLLM 统一 OpenAI 网关

对接 vLLM + Xinference;Master Key / 路由 / 负载均衡学习案例。

LiteLLM 部署与使用

环境:192.168.110.207:4000

用途:统一 OpenAI 兼容网关,转发到 vLLM(对话)与 Xinference(向量)

进阶:密钥 / 路由 / Fallback / 成本 / 指标 → LiteLLM 高级功能与用法

HTML:docs/html_cursor/LiteLLM部署_cursor.html


1. 访问信息

项值
Base URLhttp://192.168.110.207:4000
Master Keysk-litellm-bocheng-207(patches_cursor/LiteLLM部署/.env)
对话模型qwen3.6-27b(别名 qwen、学习示例 demo-chat)
向量模型bge-m3
学习:负载均衡demo-lb(自动选机);钉机别名 demo-lb-a / demo-lb-b(上游为模拟端口,调用会失败属预期)
上游对话http://116.62.10.183:8000/v1(vLLM)
上游向量http://192.168.110.207:9997/v1(Xinference)

2. 一键部署 / 验收

在 Windows 项目根:

bash
python scripts_cursor/00_部署_workbuddy到207.py
python scripts_cursor/LiteLLM部署/LiteLLM_01_部署.py
python scripts_cursor/LiteLLM部署/LiteLLM_02_验收.py

207 本机也可:

bash
bash /opt/workbuddy/scripts_bash_cursor/LiteLLM部署/LiteLLM_01_部署.sh

3. 调用示例

列模型

bash
curl -s http://192.168.110.207:4000/v1/models \
  -H "Authorization: Bearer sk-litellm-bocheng-207"

对话

bash
curl -s http://192.168.110.207:4000/v1/chat/completions \
  -H "Authorization: Bearer sk-litellm-bocheng-207" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "qwen3.6-27b",
    "messages": [{"role": "user", "content": "你好"}],
    "max_tokens": 128
  }'

向量

bash
curl -s http://192.168.110.207:4000/v1/embeddings \
  -H "Authorization: Bearer sk-litellm-bocheng-207" \
  -H "Content-Type: application/json" \
  -d '{"model":"bge-m3","input":"测试文本"}'

Python(OpenAI SDK)

python
from openai import OpenAI

client = OpenAI(
    api_key="sk-litellm-bocheng-207",
    base_url="http://192.168.110.207:4000/v1",
)
print(client.chat.completions.create(
    model="qwen3.6-27b",
    messages=[{"role": "user", "content": "你好"}],
    max_tokens=64,
).choices[0].message.content)

4. 如何新增一个可用模型(学习步骤)

源头文件:patches_cursor/LiteLLM部署/config.yaml 运行时文件:/opt/litellm/config.yaml

步骤

  1. 在 model_list: 下增加一段(示例已加 demo-chat):
yaml
  - model_name: demo-chat          # 客户端调用名
    litellm_params:
      model: openai/qwen3.6-27b    # openai/ + 上游真实模型 id
      api_base: http://116.62.10.183:8000/v1
      api_key: "123456"
      timeout: 300
      extra_body:
        chat_template_kwargs:
          enable_thinking: false
  1. 同步到 207 并重启:
bash
# Windows 项目根
python scripts_cursor/00_部署_workbuddy到207.py
# 拷贝到运行目录并重启(或跑 LiteLLM_01_部署.py)

207 上也可:

bash
cp /opt/workbuddy/patches_cursor/LiteLLM部署/config.yaml /opt/litellm/config.yaml
sed -i 's#http://host.docker.internal:9997/v1#http://127.0.0.1:9997/v1#g' /opt/litellm/config.yaml
systemctl restart litellm
  1. 验证:
bash
curl -s http://192.168.110.207:4000/v1/models \
  -H "Authorization: Bearer sk-litellm-bocheng-207"

curl -s http://192.168.110.207:4000/v1/chat/completions \
  -H "Authorization: Bearer sk-litellm-bocheng-207" \
  -H "Content-Type: application/json" \
  -d '{"model":"demo-chat","messages":[{"role":"user","content":"你好"}],"max_tokens":64}'

/v1/models 里能看到 demo-chat,且 chat 有回复,即新增成功。


5. 配置文件位置

文件说明
patches_cursor/LiteLLM部署/config.yaml模型路由(源头)
/opt/litellm/config.yaml运行时配置(systemd 读这份)
/etc/systemd/system/litellm.service服务单元;含 LITELLM_MASTER_KEY
patches_cursor/LiteLLM部署/docker-compose.yml容器编排(备用;当前未用 Docker 跑)
patches_cursor/LiteLLM部署/.envLITELLM_MASTER_KEY(与 systemd 应对齐)
端口4000

改 config.yaml 后重新执行 LiteLLM_01_部署.py(或拷贝到 /opt/litellm/ 再 systemctl restart litellm)即可生效。


6. 部署方式说明

当前 207 采用 pip + systemd(因 Docker 拉 ghcr/docker.litellm.ai 不稳定):

项值
服务systemctl status litellm
虚拟环境/opt/litellm-venv
配置/opt/litellm/config.yaml(从 patches_cursor/LiteLLM部署/config.yaml 同步)
版本litellm[proxy]==1.74.15(兼容系统 Python 3.10)

常用命令:

bash
systemctl status litellm
journalctl -u litellm -n 80 --no-pager
systemctl restart litellm

改模型路由后:同步 config.yaml 到 /opt/litellm/ 再 systemctl restart litellm。


7. 排错

现象处理
chat 超时 / 502检查 183 vLLM:curl -H "Authorization: Bearer 123456" http://116.62.10.183:8000/v1/models
chat content 为空但有 reasoning_contentQwen3 thinking 占满 token;配置已默认 enable_thinking: false,或加大 max_tokens
embeddings 失败检查 Xinference:curl -H "Authorization: Bearer xf-..." http://127.0.0.1:9997/v1/models
401确认 Header 使用 Bearer sk-litellm-bocheng-207
服务挂了journalctl -u litellm -n 100 --no-pager

8. 学习案例问答(Master Key / 路由 / Xinference / 负载均衡)

以下按「提出问题 → 详细回答」整理,便于对照 config.yaml 与 curl 实操。

案例 1:sk-litellm-bocheng-207 是什么?怎么定义 / 生成?

问题:这串 Key 是什么?怎么来的?

回答:它是 LiteLLM Proxy 的 Master Key(管理员级 API Key),用来校验「谁可以调用 :4000 网关」。不是算法自动生成的,而是部署时人手写死的共享口令。命名只是方便记:sk-(OpenAI 风格)+ litellm + bocheng + 207。

定义链路:

  1. 环境变量(真正生效):LITELLM_MASTER_KEY=sk-litellm-bocheng-207
  1. config.yaml 引用环境变量,不直接写死字符串:
yaml
general_settings:
  master_key: os.environ/LITELLM_MASTER_KEY

若要自己换一把(示例生成方式,任选其一):

bash
openssl rand -hex 24
# 或
python -c "import secrets; print('sk-' + secrets.token_urlsafe(24))"

改 .env + systemd 的 LITELLM_MASTER_KEY 后执行:

bash
systemctl daemon-reload
systemctl restart litellm

所有客户端 Bearer 也要一起改。

和上游 Key 别混:

Key给谁用例子
Master Key客户端 → LiteLLM(:4000)sk-litellm-bocheng-207
上游 api_keyLiteLLM → vLLM / Xinference123456、xf-...

案例 2:现有的 Master Key 在哪里查看?

问题:已经配好的那把 Key,我去哪看?

回答(任选一处核对即可,值应一致):

位置说明
patches_cursor/LiteLLM部署/.env源头:LITELLM_MASTER_KEY=...
/etc/systemd/system/litellm.service运行中的环境变量
scripts_cursor/_config.py脚本常量 LITELLM_MASTER_KEY
本文档 §1 访问信息表文档备份

查看 systemd:

bash
cat /etc/systemd/system/litellm.service
# 关注:Environment=LITELLM_MASTER_KEY=sk-litellm-bocheng-207

案例 3:systemd 里定义好之后,所有接口都用这把 Key 吗?

问题:litellm.service 里写了 LITELLM_MASTER_KEY,是不是调 LiteLLM 所有接口都带它?

回答:对,在当前部署方式下(未单独建虚拟 Key),客户端调 LiteLLM(:4000)的鉴权就是这把 Master Key:

text
Authorization: Bearer sk-litellm-bocheng-207

适用于 /v1/chat/completions、/v1/embeddings、/v1/models 等。

注意:

典型 service 片段:

ini
[Service]
Environment=LITELLM_MASTER_KEY=sk-litellm-bocheng-207
WorkingDirectory=/opt/litellm
ExecStart=/opt/litellm-venv/bin/litellm --config /opt/litellm/config.yaml --port 4000 --host 0.0.0.0

案例 4:Xinference 完整 curl 有哪些?头从哪里来?

问题:直连 Xinference 时,请求长什么样?Header 从哪获取?

回答:直连 :9997,只用 Xinference API Key(xf-...),与 LiteLLM 的 sk-... 无关。

项值来源
地址http://192.168.110.207:9997(本机可用 127.0.0.1:9997)容器端口映射
Keyxf-K8H3LiS27H4188XdOyWJj74MWMOlIR9tZbiybDbxbSas7eAIXinference 创建;仓库 scripts_cursor/_config.py 的 XF_KEY;LiteLLM config.yaml 里 bge-m3 的 api_key
AuthorizationBearer <xf-...>同上,需自己抄进 curl
Content-Typeapplication/jsonPOST 时自己写,不是接口下发的

列模型:

bash
curl -s http://192.168.110.207:9997/v1/models \
  -H "Authorization: Bearer xf-K8H3LiS27H4188XdOyWJj74MWMOlIR9tZbiybDbxbSas7eAI"

Embedding(bge-m3):

bash
curl -s http://192.168.110.207:9997/v1/embeddings \
  -H "Authorization: Bearer xf-K8H3LiS27H4188XdOyWJj74MWMOlIR9tZbiybDbxbSas7eAI" \
  -H "Content-Type: application/json" \
  -d '{"model":"bge-m3","input":"测试文本"}'

Rerank(bge-reranker-v2-m3):

bash
curl -s http://192.168.110.207:9997/v1/rerank \
  -H "Authorization: Bearer xf-K8H3LiS27H4188XdOyWJj74MWMOlIR9tZbiybDbxbSas7eAI" \
  -H "Content-Type: application/json" \
  -d '{
    "model": "bge-reranker-v2-m3",
    "query": "加班费怎么算",
    "documents": ["加班费按300%计算", "今天天气不错"]
  }'

头没有「自动下发接口」可抄:Key 在 Xinference 管理端创建后记在配置里;model 名来自 GET /v1/models 或 launch 时的 -u。


案例 5:走 LiteLLM 时,还要不要带 xf-...?

问题:xf-... 已写在 config.yaml 里,那 embeddings 的 curl 是否只带 sk-litellm-... 即可?

回答:对。走 LiteLLM(:4000)时:

调用链:

text
你的 curl → LiteLLM(验 master key)→ Xinference(用 config 里的 xf- key)
bash
curl -s http://192.168.110.207:4000/v1/embeddings \
  -H "Authorization: Bearer sk-litellm-bocheng-207" \
  -H "Content-Type: application/json" \
  -d '{"model":"bge-m3","input":"测试文本"}'

案例 6:config 里很多条,只写一把 sk-...,怎么对应上某一条?

问题:model_list 有多条,鉴权又只有一把 Master Key,它怎么知道走哪条上游?

回答:靠的不是 Key 对应某一条,而是请求体里的 model 字段。

  1. 鉴权:Bearer Master Key → 证明能进门(所有已配置模型共用)。
  2. 路由:JSON 里 "model":"xxx" → 在 model_list 找 model_name == xxx → 用那条的 api_base / api_key 打上游。
客户端 model命中配置上游
bge-m3model_name: bge-m3Xinference + xf-...
demo-chatmodel_name: demo-chatvLLM + 123456
demo-lb同名多条由 router 在多台里选

Key 管“能不能进门”,model 管“进门后走哪条配置”。 写错或不存在的模型名会报找不到模型,与 Key 无关。


案例 7:所有 model_name 必须全局唯一吗?

问题:配置里每个 model_name 能不能重复?

回答:不一定。

情况含义
每个名字一条(日常默认)qwen、demo-chat、bge-m3 各走自己的上游,最清晰
同一个 model_name 多条当成同一逻辑模型的多台部署 → 负载均衡 / 故障切换

想当不同接口用 → 名字要不同。 想同一名字打多台机器 → 故意写成同一个 model_name。


案例 8:同名多机负载均衡——真实配置形态(可模拟)

问题:同一名字打多台机器怎么写?

回答:config.yaml 里已加学习示例(上游端口故意不存在,调用失败属预期,只演示形态)。核心:

yaml
  # ① 自动负载均衡:同名两条 → 客户端 model=demo-lb
  - model_name: demo-lb
    litellm_params:
      model: openai/fake-qwen-a
      api_base: http://127.0.0.1:18001/v1
      api_key: "fake-key-machine-a"
      timeout: 10
      max_retries: 0

  - model_name: demo-lb
    litellm_params:
      model: openai/fake-qwen-b
      api_base: http://127.0.0.1:18002/v1
      api_key: "fake-key-machine-b"
      timeout: 10
      max_retries: 0

router_settings:
  routing_strategy: simple-shuffle   # 随机选一台

客户端只写一个逻辑名:

bash
curl -s http://192.168.110.207:4000/v1/chat/completions \
  -H "Authorization: Bearer sk-litellm-bocheng-207" \
  -H "Content-Type: application/json" \
  -d '{"model":"demo-lb","messages":[{"role":"user","content":"hi"}],"max_tokens":16}'

/v1/models 对外只显示 一个 demo-lb(逻辑名去重);配置里却是两条部署。生产把两个 api_base 换成两台真实 vLLM 即可。

完整片段见:patches_cursor/LiteLLM部署/config.yaml(含下方钉机别名)。


案例 9:可以手动指定是哪一台吗?

问题:负载均衡很好用,但排障时能否钉死某一台?

回答:可以。最实用做法是:均衡名 + 唯一别名钉机(同一台既参与 demo-lb,又单独挂 demo-lb-a / demo-lb-b)。

客户端 model行为
demo-lb自动负载均衡,在 A/B 里由 simple-shuffle 选
demo-lb-a钉死 A 机(:18001)
demo-lb-b钉死 B 机(:18002)

配置片段:

yaml
  - model_name: demo-lb-a
    litellm_params:
      model: openai/fake-qwen-a
      api_base: http://127.0.0.1:18001/v1
      api_key: "fake-key-machine-a"
      timeout: 10
      max_retries: 0

  - model_name: demo-lb-b
    litellm_params:
      model: openai/fake-qwen-b
      api_base: http://127.0.0.1:18002/v1
      api_key: "fake-key-machine-b"
      timeout: 10
      max_retries: 0
bash
# 自动选机
... -d '{"model":"demo-lb", ...}'

# 指定 A / B(排障、灰度、压测)
... -d '{"model":"demo-lb-a", ...}'
... -d '{"model":"demo-lb-b", ...}'

LiteLLM 还有按 tag 路由等高级写法;当前场景用唯一别名钉机已够用。