资讯详情

LiteLLM:一套 API 接入所有大模型供应商的 OpenAI 兼容网关

📅 2026/10/21 16:02:32 | 华诺云谱 👁 阅读
LiteLLM:一套 API 接入所有大模型供应商的 OpenAI 兼容网关
1. 项目概述这个工具到底在解决什么问题如果你最近在写大模型相关的应用一定会遇到一个绕不开的尴尬今天用某个厂商的接口明天换个供应商代码里到处是换接口、改签名、调参数的补丁。明明大家的功能长得都差不多都是“给一句话返回一句话”但各家SDK、鉴权方式、返回字段、限流策略却各不一样接一个还好接三四个就让人头皮发麻。LiteLLM这个项目本质上就是干这件事的用一个统一的标准来对接几乎所有主流大模型供应商把“每个厂商一套SDK”变成“一套SDK全部搞定”。它提供了一个OpenAI格式兼容的统一入口你可以用完全相同的代码去调通不同提供商的模型无论是闭源商业模型还是开源自部署模型都能以几乎一致的方式接入。它不仅仅是“封装”这么简单项目还内置了代理服务器、密钥管理、预算控制、限流、缓存、重试、负载均衡和故障转移这些生产环境必备的能力。也就是说当你不满足于只在本地跑实验而是想把大模型能力真正做成一个服务提供给团队、给业务方使用的时候LiteLLM能帮你省掉非常多的基建时间。适合谁来用如果你是一个独立开发者需要快速把多个模型接进自己的应用里LiteLLM能帮你省掉大量对接时间。如果你是一个小团队的技术负责人想把各种大模型能力统一管理给组内不同项目分配好额度LiteLLM的代理网关几乎是开箱即用的。如果你只是纯粹想知道怎么把一个多模型接入层做得干净、可维护这个项目本身也是一份很不错的参考实现。它不是某个厂商的亲儿子所以不会被绑定在一家生态里反而成了连接各家服务的“万能插座”。2. 为什么值得选它先解决“要不要自己写一层”的问题很多团队遇到多模型接入问题时第一反应是“我们自己封装一层不就行了”这个思路本身没问题但你得看清要自己动手的话实际要解决的问题清单有多长。2.1 自己写适配层你面临的远不止接口转换你以为自己封装只是写几个函数把请求参数翻译成不同厂商的格式。但真正做下去就会发现统一调用只是最表层的问题。更深层的还有各家模型返回的流式格式不一样SSEServer-Sent Events服务端推送事件流的字段名和数据结构天差地别错误码体系也完全不同有的返回HTTP 429代表限流有的返回500也可能是限流重试策略不能一刀切某些模型对重复请求的容忍度很低盲目重试反而会烧掉更多额度还有token计费规则差异不同厂商和自部署模型的计价维度甚至不是同一个概念。这些还只是“技术线程”上的问题紧接着是“管理层”的问题团队里不同项目要用不同模型每个项目的调用量预算怎么控制新同事拿到账号后密钥怎么分配、怎么回收某个上游供应商临时挂了怎么优雅地把流量切到备用模型而不是让业务报错日志和调用统计怎么做这些都是一个成熟接入层必须回答的问题而LiteLLM基本都已经内置好了。2.2 LiteLLM的核心设计思路以OpenAI格式作为中间标准LiteLLM聪明的地方在于它没有搞一套自己的全新格式而是直接把OpenAI的请求/响应结构作为“世界语”。OpenAI的SDK本来就是目前普及度最高的接口范式大量的开源项目和工具链都已经兼容它。LiteLLM做的事情是把其他所有提供商的格式“翻译”成OpenAI格式这样你的业务代码只需要认识一种标准就够了。可以说这是目前权衡之下最好的选择成本低因为OpenAI格式的资料多、工具多通用性强因为已经有很多生态在用它迁移平滑即便以后不再用LiteLLM你写的那些基于OpenAI格式的代码依然能在原生环境中运行不会被锁死在某一个中间层里。2.3 它当仓库与当网关的两种姿势LiteLLM有两种主流使用形态很多人一开始没分清。第一种是SDK形态直接在你的Python/Node.js项目里依赖它把它当做一个封装库来调用适合单应用、无服务化的场景简单直接。第二种是代理网关Proxy Server形态你先把LiteLLM起成一个独立服务你的业务代码像调OpenAI一样调这个服务再由它去调度背后的真实供应商适合多应用共享、需要集中治理密钥和预算的团队。像我自己的经验一开始用SDK形态写实验代码很顺手但一旦服务上线给业务方用就立刻切到了网关形态。因为网关模式才真正把“资源管理”和“业务开发”分开了做应用的人不用关心上游是谁、配额还剩多少只管像调OpenAI一样发请求就行负责基建的人统一在网关层控制一切。提示如果只是本地跑实验SDK形态就够了。如果要多人、多项目共用模型建议直接上网关形态。两种可以同时用并不冲突。3. 核心细节解析安装、配置与关键参数3.1 环境要求与安装方式LiteLLM基于Python所以最基本的门槛是有一个可用的Python环境。通常建议Python 3.8及以上我日常使用的是3.10和3.11都比较稳。建议使用虚拟环境避免把依赖装乱。python -m venv venv source venv/bin/activate pip install litellm[proxy]上面的命令会把LiteLLM的核心库连同代理服务相关的依赖一起装上。如果你只需要SDK功能不想装代理相关的部分可以直接pip install litellm其他语言的SDK是社区维护的如果要用可以在官方文档里找对应的包。但主力的Python版本是更新最快、功能最全的如果遇到行为不一致以Python版本为准。3.2 环境变量配置让各家密钥各归其位LiteLLM支持从环境变量里读取各家供应商的API密钥这是它推荐的密钥管理方式。你需要去各个供应商平台申请密钥然后把它们配置成环境变量。下面是一个典型的配置示例把“某个商业模型服务商A”和“某个模型服务商B”的密钥放好export SAMPLE_A_API_KEYsk-xxxx export OTHER_B_API_KEYsk-yyyy在代码里你可以指定某个模型具体走哪个供应商的接口LiteLLM会自动去找对应的密钥。比如要调用商A的某模型和商B的某模型from litellm import completion response completion( modelsample-a/model-x, messages[{role: user, content: 你好}], )如果模型名带公司前缀比如sample-aLiteLLM就知道从环境变量去找对应的密钥类型。如果没有显式前缀LiteLLM会把模型名当成OpenAI的模型来处理这个细节很容易踩坑。3.3 核心调用方式统一的completion接口LiteLLM的SDK核心就是一个completion方法它会根据你传入的model参数自动路由到相应的供应商。对于已经是OpenAI格式的接口来说你的代码看起来与直接调用OpenAI SDK没有明显区别只是在import那行换成了litellm。这里重点讲几个容易忽略的细节。第一是消息格式必须遵循大型语言模型API的常见规范比如系统级提示语、用户内容、历史会话记录这些要素role和content字段是必须的。第二是流式响应用法和OpenAI类似response litellm.completion( modelsample-a/model-x, messages[{role: user, content: 用一句话介绍杭州}], streamTrue, ) for chunk in response: print(chunk.choices[0].delta.content or , end)第三是返回结构LiteLLM对外统一返回OpenAI兼容结构哪怕背后实际调用的是另一家的接口。这意味着你的下游逻辑只需要处理一套返回字段。3.4 代理网关把模型能力做成一个服务当你把LiteLLM跑成代理网关后所有团队成员的调用都统一走一个接口地址密钥、预算、频率限制都在这一层统一管控业务代码干净权限也清晰。启动网关的方式很直观litellm --model sample-a/model-x --port 4000更常用的做法是写一个配置文件把多个供应商、多个模型、多个密钥都定义好然后启动litellm --config config.yaml --port 4000比如这样一份配置内容model_list: - model_name: gpt-abc litellm_params: model: sample-a/model-x api_key: os.environ/SAMPLE_A_API_KEY - model_name: claude-like litellm_params: model: sample-b/model-y api_key: os.environ/SAMPLE_B_API_KEY启动网关后你的业务代码只需把base_url指向这个网关口并配置一个任意可用密钥然后就可以像调用OpenAI那样使用了from openai import OpenAI client OpenAI( api_keysk-any-key, base_urlhttp://localhost:4000, ) response client.chat.completions.create( modelgpt-abc, messages[{role: user, content: 你好}], )这里有一点需要特别留意网关通过model_name这个字段来做路由你在配置文件里给它取什么名字业务端就调用什么名字它不一定要和上游的真实模型名一致。这是方便做模型切换的也是常用的“金丝雀发布”手段比如改一下路由规则就能让流量从旧模型平滑切到新模型业务端完全无感知。注意代理端口默认很多是4000如果你的环境里4000被占了记得换端口。另外不要用默认密钥暴露到公网网关最好只在内网访问外面套一层API管理和权限认证。4. 实操过程从单模型试跑到多模型统一接入前面讲了概念和配置这一节实际动手把流程走一遍。我自己当初第一次用LiteLLM的时候从安装到接通到第一个模型只花了不到十分钟。整个链路并不复杂关键是你得知道每一步在干什么。4.1 第一步验证SDK通路安装好LiteLLM并配置好某个供应商的密钥后先跑一个最简单的请求确认环境没问题import litellm resp litellm.completion( modelsample-a/model-x, messages[{role: user, content: 你好}], ) print(resp)如果这一跑通了后面的网关部署只是流程问题。如果这里就报错优先排查两项第一项模型格式是否写对了注意前缀是否匹配环境变量前缀第二项环境变量是否真的加载到了运行环境里建议用os.environ.get(SAMPLE_A_API_KEY)打印一下确认非空。4.2 第二步写一个正式的网关配置文件单模型验证通过后我们把多模型场景配置到网关里。假设现在需要接入三个模型一个商用闭源模型一个开源自部署模型一个备用模型作为降级方案。配置文件如下model_list: - model_name: chat-main litellm_params: model: sample-a/model-x api_key: os.environ/SAMPLE_A_API_KEY rpm: 30 - model_name: chat-backup litellm_params: model: sample-b/model-y api_key: os.environ/SAMPLE_B_API_KEY rpm: 10 - model_name: chat-local litellm_params: model: ollama/llama3 api_base: http://localhost:11434 rpm: 60在模型参数配置中参数文件里支持的键非常丰富比如rpm每分钟请求数限制和tpm每分钟token数限制都有专门用途。我给每个模型单独设定了流量上限防止某个业务方的异常流量波及其他人这在小团队阶段不是刚需但上了代理之后顺手就做了。4.3 第三步启动网关并验证路由启动网关后先用curl做一次快速连通性测试curl http://localhost:4000/v1/models如果能看到你在配置里定义的模型列表说明网关已经起来了。然后发一个真实请求验证路由是否正确curl http://localhost:4000/v1/chat/completions \ -H Content-Type: application/json \ -d { model: chat-main, messages: [{role: user, content: 说一句问候}] }这时观察网关日志会看到请求实际打到了哪家上游供应商。日志里会有模型名、耗时、状态码以及token用量。这个日志本身就是一份很好的调用审计数据我后来就靠它做月度成本分析。4.4 第四步把业务代码切到网关业务端不需要引入任何LiteLLM的依赖只需要用你熟悉的任一OpenAI兼容SDK把base_url指向网关即可。比如在Python里client OpenAI(base_urlhttp://localhost:4000, api_keyany-key)网关会对传入的api_key做校验如果没配虚拟密钥任意非空字符串都能过如果配置了虚拟密钥就必须输入真实存在的虚拟密钥。我强烈建议生产环境把虚拟密钥机制打开否则谁拿到你的网关地址都能直接消耗上游额度。这里有一个相当大的心智切换点加了网关之后业务团队完全不再需要碰上游真实密钥所有密钥都只存在网关服务的环境变量里。这是个不小的安全收益。4.5 第五步加入缓存、重试与降级规则如果只做到上面这步你已经拥有了一个统一接入服务但这种状态的系统还很脆弱。接下来值得配置的是缓存、重试和故障转移相当于给接入层加上“自我保护机制”。LiteLLM支持用Redis做缓存对于重复的请求可以显著减少上游调用压力。比如启用响应缓存后同样的提示词在缓存生命期内直接走Redis不消耗上游额度。我这里建议至少开启缓存尤其是同一批提示词会被反复调用的情况下。配置也很简单general_settings: redis_host: localhost redis_port: 6379 cache: true故障转移配置也很有意思。你可以定义一组备用模型当主模型失败或限流时自动切换。比如这样配置router_settings: fallbacks: [{model: chat-backup}]含义是当chat-main失败时就自动去调chat-backup。对于对外提供服务的应用来说这个功能可以让模型供应商短暂故障时业务不中断用户感知到的可能只是一次稍长的响应时间。4.6 实操过程中发现的几个经验点实际跑通整套流程后你会发现几个之前不容易注意到的体验点。比如日志里会记录每次请求的模型、成本估算和延迟。这个功能非常有用不需要自己做一套复杂的埋点系统就能拿到相对合理的调用统计数据。再比如网关支持动态添加模型不用重启进程通过管理接口就能热加载新的模型配置对模型迭代很快的团队来说这是刚需。真实踩过一次坑我一开始把配置里model_name直接写成上游真实模型名看起来更直观但后来换模型时前端应用也需要改完全失去了隐蔽和灰度价值。后来我改成“业务别名上游真实模型”分离切换上游时业务端完全无改动舒服很多。5. 项目背后的技术机制拆解5.1 请求路由与模型别名的实现逻辑LiteLLM的路由核心是一个模型注册表的概念。在网关模式里你配置的model_name就是这张注册表里的逻辑名而litellm_params里定义了它实际对应哪个上游供应商的哪个模型。请求进来时LiteLLM只看model_name查出对应的上游配置然后把请求做一次适配转发。这个逻辑模型让“换模型”变成了一次纯运维操作你只需要修改注册表里的映射关系业务代码完全不动。比如“chat-main”这个逻辑名下昨天还是商A的模型今天换成商B的模型对下游应用来说没有任何变化请求结构、返回结构都一样。据我了解这个设计思路和很多企业内部自建的模型平台一致只是LiteLLM帮你开源实现好了。5.2 限流与配额防止某个调用方把预算烧光多业务方共用网关时最怕的就是一个调用方的bug把整月预算烧没。LiteLLM的限流机制分两层第一层是按模型层面的rpm/tpm限流直接在模型配置里指定第二层是按虚拟密钥层面配置配额比如给某业务方每月设置限额。网关会把请求发生前先检查当前速率是否达到阈值超过就返回429限流错误码而不会真把请求发给上游这样就避免了一个业务方的突发流量拖垮全组。配额控制这块更贴近预算管理配置好虚拟密钥后可以给它关联固定额度的预算比如general_settings: master_key: sk-master database_url: postgresql://... # 持久化记录用量严格的预算控制需要配数据库用持久化存储来计时用量否则网关一重启配额统计就清零了。这一点在初期实验阶段可以忽略但真要进生产环境数据库是必须的。5.3 重试与超时细节里藏着稳定性重试策略我个人的看法是要分供应商、分错误码去设计不能一概而论。LiteLLM默认会针对429限流、5xx服务器错误、超时等情况进行重试但重试次数和退避算法可以调整。比如litellm.set_verbose True # 开启调试日志又或者通过配置字段设置超时时间。比如给某个模型单独指定较长的超时因为自部署模型在某些负载下响应确实慢。关于重试这里有个容易被忽视的坑无脑重试在供应商限流时反而会加重问题因为你的重试请求也在消耗配额和流量。正确的做法是对429做指数退避并限制最大重试次数对认证失败的401/403不要重试那通常不是暂时性问题。LiteLLM的默认参数偏保守但我建议你在生产环境仔细调一下自己的重试策略。注意自部署模型比如通过Ollama、vLLM这类方式搭建的本地模型服务通常没有复杂的速率限制但它们的超时表现往往比商业API更不稳定健康检查与超时时间要放宽一些。5.4 缓存机制让重复请求不再重复烧钱缓存的核心思路很简单同一个请求如果之前已经生成过答案且还没过期直接从缓存返回。LiteLLM支持内存缓存和Redis缓存。内存缓存适合单实例部署多实例部署一定要用Redis否则每台机器缓存各自为政命中率低数据也不一致。我一直认为缓存策略要区分场景对于内容完全相同的请求比如固定模版的问答、高频查询类缓存收益极其明显但对于创意写作、开放聊天这类场景命中率很低缓存价值有限。更实用的思路是做“语义缓存”或者“前缀摘要缓存”但LiteLLM内置的主要是精确匹配缓存你可以理解成一个按请求内容哈希取结果的KV存储。5.5 成本追踪每一个token都算得清成本一直是多模型接入最头疼的事情。各家供应商计费维度不同有的按输入输出分开计有的按调用次数计有的自部署模型是按GPU时长算成本。LiteLLM内置了模型成本数据库它在每次请求结束后自动根据模型名和用量估算出本次调用成本并记录在日志里。这个能力对预算管控很重要它让成本数据自动汇总不需要自己再去对账。你可以按月、按日、按模型、按虚拟密钥维度去查历史调用与成本再结合自己的业务分摊到各个团队或项目上。这个功能把“模型成本治理”从手工记账变成自动采集对要写汇报材料的人来说省下的是实打实的时间。6. 常见问题与排查技巧实录无论怎么小心实际使用中总会遇到一些奇怪问题。我把这段时间踩过的、以及社区里高频出现的问题整理成一个速查表方便你和团队在遇到类似情况时快速定位。问题现象可能原因排查建议报401错误密钥无效环境变量没有正确加载或模型前缀不匹配先打印环境变量确认非空确认模型名前缀与密钥变量一致模型名自带OpenAI前缀结果被误路由没有显式指定供应商映射在模型名上加上正确的前缀或使用litellm_params里的api_base来指定接入地址请求一直等待直到超时上游响应慢、网络不通或模型负载过高查看网关日志的上游调用耗时对自部署模型单独设置更长超时429限流频繁网关限流设置过严或上游真实限流先看是网关返回429未发出上游请求还是上游返回429前者查配置阈值后者要降低并发数缓存未命中每次请求都打到上游使用了内存缓存但网关是多实例部署检查是否改为Redis缓存检查缓存key是否因为消息顺序变化而未命中日志里看不到调用明细与成本verbose未开启或未配置持久化存储开启verbose生产环境配置数据库使用了OpenAI的客户端连网关返回格式异常base_url路径不对或网关版本过旧确认base_url是否完整包含/v1路径检查LiteLLM版本并升级6.1 最常见的低级别问题密钥不生效这类问题平时最多。很多时候你明明export了环境变量运行时却还是401。原因往往是你在一个终端窗口里export了变量但启动Python进程或网关是在另一个终端窗口环境变量根本没传过去。解决办法是在同一个终端里先确认echo $SAMPLE_A_API_KEY确认能打印出内容后再启动脚本或网关。推荐的做法是在代码里加入环境加载逻辑或者用一个.env文件由启动命令加载。这一点在部署到服务器或容器里时尤其重要环境变量的传递经常是配置事故的重灾区。6.2 模型名映射不清晰的坑有些情况下LiteLLM会通过模型名自动推断供应商但如果你用的是自部署且兼容OpenAI格式的服务模型名没法让人一眼看出是哪个供应商。这个时候不要指望LiteLLM自动识别而应该在配置文件里显式写明api_base。我们团队后来统一约定所有非公共供应商的模型都在配置文件中显式指定api_base和model的完整映射宁可多写两行也不让路由靠猜。6.3 网关请求超时但上游服务正常还有一个很容易被误解的场景业务端通过网关请求某个模型经常性超时但你直接去请求上游却正常。排查下来要么是网关所在机器到上游的网络有问题比如容器网络策略、防火墙要么是网关默认的超时设置太短。如果上游是自部署模型冷启动和长思考链路的响应时间天然比较长你需要在配置里给这个模型单独设置更宽松的超时。6.4 升级某个模型供应商的版本后行为变化还有一种情况某家上游服务更新了模型行为响应内容变长、格式变化导致下游解析出错。这不是LiteLLM的问题但通过它加一层缓冲后你可以更从容地处理。做法是在网关层面先让新模型路由到一个测试用的别名供少数人试用验证没问题再切主别名。这个灰度流程因为LiteLLM支持热更新配置实操起来非常顺。7. 我的实操心得与建议整套用下来LiteLLM最打动我的不是它的功能数量而是它在“抽象层次”上做得比较对它没有去定义一套全新的、华而不实的标准而是选择站在OpenAI格式这个已经广泛普及的接口上做翻译和补充。这就大幅降低了学习和接入成本。如果你想从零开始用这个项目我建议按这样的节奏推进先本地用SDK形态跑通一个模型感受一下API风格然后写配置文件把第二个模型也接进去用网关跑起来最后再逐步打开缓存、限流和故障转移。不要一开始就想把所有功能都配上那样你根本分不清是自己在踩坑还是配置在打架。先做小闭环再扩张整个系统会顺很多。如果你打算拿它做内部基础设施我建议从一开始就把虚拟密钥和数据库配额打开。很多团队初期图省事先不开配额等业务大了再补结果发现历史调用数据没有记录预算无法追溯只能硬着头皮重新搭建这其中的返工成本很高。同样的道理也适用于Redis缓存和日志持久化生产环境早早上比事后补要省心得多。最后再分享一个小技巧遇到奇怪问题先开调试日志。很多使用问题根本不是LiteLLM的bug而是配置细节没有对齐。打开调试日志之后你会看到请求实际发往了哪个上游、发了什么参数、返回了什么错误90%的问题都能在日志里找到答案。掌握了这个方法你自己排查问题的能力会上一个台阶。
📝

华诺云谱内容团队

资深建站顾问 · 行业研究员

10年+企业数字化服务经验,专注智能建站、SEO优化与品牌营销,持续输出建站技巧、行业洞察与营销干货,已帮助5000+企业实现数字化增长。

你可能需要的服务

订阅华诺云谱资讯周报

每周一封,精选建站技巧、SEO与营销干货,直达邮箱。已有 8,000+ 企业主订阅,助你少走弯路。

↑