☰
万亿Token级大模型推理系统对外开放实战:从内部平台到多租户服务
2026/10/12 4:04:39 网站建设 项目流程

你可能没意识到,一个内部每天烧掉近万亿 token 的推理系统,真正对外开放时,要过的关卡远比“把模型跑起来”多得多。我最近就在做这件事:把跑了好几年的内部推理平台 Prime Inference 产品化,第一个对外开放的端点,给了当前团队内部综合效果最稳的主力模型 GLM-5.3。

这个选择在当时看来有些反直觉。外面很多团队开放推理能力时,通常挑一个小模型先试水,降低风险和成本。但我们最终把首个对外端点押在了体量最大、推理成本最高、调用最频繁的 GLM-5.3 上。

这篇东西不是官方公告,也不是产品文档,而是一个一线参与者的实操复盘。我尽量把“为什么要开放”“万亿 token 级别到底意味着什么”“一个端点背后要改哪些东西”“开放初期踩了哪些坑”讲清楚。适合正在做模型服务化、推理平台建设或想要把内部 AI 能力对外输出的技术团队参考。哪怕你不是搞推理系统的,看完也能理解为什么大模型对外服务这件事,工程比重远大于模型本身。

1. 内部推理系统对外开放:先弄明白这盘棋是什么

1.1 从“内部自用”到“对外开放”,最核心的变化是什么

内部推理系统通常有一个天然优势:环境可控。业务方是自家团队,调用方是谁、请求长什么样、峰值在哪个时间段,基本心里有数。系统挂了,大家习惯了,可以等恢复;指标波动了,可以内部协调错峰。这种“容忍度”是内部系统的隐形福利,但也是对外服务最大的敌人。

Prime Inference 在内部承担的角色,不是简单的“一个模型 API”,而是一整套推理调度体系。它把若干主力模型服务化,内部每天的算力消耗接近万亿 token。这些 token 来自客服、写作助手、代码生成、数据分析等场景,请求形态差异非常大。有的请求是短 prompt 快速回答,有的则动不动塞进几十 KB 的上下文。这种复杂的流量结构,反而让系统在吞吐优化、显存管理、请求调度上积累了很强的工程能力。

对外开放后,最核心的变化有三点。

第一,用户变了。之前内部用户能容忍偶发超时和抖动,外部用户不会。SLA 是写在合同里的,P99 延迟超标一次,可能就要写事故报告。

第二,安全边界变了。内部系统默认信任调用方,外部环境必须把每个请求当成潜在攻击。鉴权、限流、内容审核、Prompt 注入防护,一个都不能少。

第三,资源模型变了。内部可以不计费,外部必须计量、计费、配额管理。准确到每个用户、每个模型、每个端点的 token 消耗,这是一套独立于推理引擎的计量系统。

我刚开始接手外部化改造时,一个很深的体会是:大家总以为“推理系统对外 = 多配几个 API Key + 套个负载均衡”,实际上这么做连第一轮压测都过不了。

1.2 为什么第一个开放端点给了 GLM-5.3

这可能是整个项目里被讨论最多的问题。

GLM-5.3 在内部并不是最新的实验模型,而是当前规模最大、跑得最稳、训练后验证最充分的一个版本。我们内部给它起代号时就明确了一点:它是要在生产环境长期服役的模型。推理优化在它身上沉淀得最完整,比如 KV Cache 前缀命中率高、量化后效果损失可接受、部署模板成熟。很多新模型还没来得及把这些配套补齐,贸然开放出去,用户看到的是“不好用”,而不是“新版本”。

还有一个很务实的考量:首个端点代表平台的门面。第一个端点开放一个效果一般的模型,开发者试用后直接流失,之后再想挽回口碑成本极高。反过来,第一个端点直接给旗舰模型,哪怕推理成本偏高,只要能稳住质量和响应速度,就有机会形成“这个平台有实力”的第一印象。

从工程角度看,拿 GLM-5.3 做首个端点还有一层含义:用最难啃的骨头验证整套外部化体系。如果连内部最重、调用最频繁的模型都能稳定对外服务,那么后续接入更多模型就是复制流程。这是一种“先难后易”的路径选择。

值得一提的是,我们没有用端到端自动评测某几个指标分高就直接上,而是先在内部流量里挑了一部分真实业务请求,模拟外部调用模式,跑了两周灰度。灰度期间暴露的问题,比任何离线评测都有价值。这个经验在后面章节会详细展开。

2. 万亿 token 级推理系统的硬指标:吞吐、延迟与成本怎么同时保住

2.1 “日均万亿 token”到底是什么量级

先说个直观感受。我们内部实际统计中,单个请求的 token 消耗并不均匀,有的请求只需要几百 token,有的长上下文请求一次就能吃掉几万 token。粗略按全局平均每次请求消耗 1500 token 算,日耗万亿 token 对应每天大约 6~7 亿次请求。这个数字乍一听很吓人,但放在一个覆盖多业务线、全天候运行的大平台上,是真实存在的。

换算成资源需求更有感觉。假设单张主流加速卡在优化后的输出吞吐约 3000~5000 token/s,单一模型满负荷跑满 24 小时,一天也只能处理几亿 token。万亿 token 这个量级靠单卡跑是完全不现实的,背后必然是数百甚至上千张加速卡组成的资源池,而且这个池子还得按流量峰谷做弹性伸缩。更关键的是,这些卡并不是只跑一个模型,而是多个模型、多个任务在同一个调度体系里争夺资源。

所以我一直觉得,内部烧万亿 token 的真正价值不是“烧得多”,而是“烧出了经验”。模型推理领域很多常规文档里写不到的东西,比如显存碎片化、KV Cache 膨胀、批量请求排队导致的尾延迟,只有在高负载下才会暴露。没有这个体量的流量逼着,系统不会进化到能对外服务的状态。

2.2 高吞吐推理的关键三板斧:连续批处理、KV Cache 管理与模型并行

我在排查很多自建推理服务时发现,吞吐上不去往往是调度策略的问题,而不是 GPU 不够。这就好比电影院只有一个影厅,每场电影必须全场一起进一起出,那么即使一个观众只看五分钟,也得等到整场结束才能安排下一批。传统的静态批处理就是这么干活。

Prime Inference 之所以能撑住万亿 token,第一板斧就是连续批处理。它把“整批进场整批离场”改成“动态加座”:批里每个请求一旦结束,位置立即释放,新请求随时插入。这样 GPU 利用率可以稳定拉高,而不是被最慢的那个请求拖住。实现上需要调度器和推理内核深度配合,不是简单改个循环就能做好的。

第二板斧是 KV Cache 管理。生成式模型每一步都要保存历史 token 的注意力缓存,长上下文请求会把这些缓存撑得很大。如果按最大可能长度预分配显存,一个并发都跑不了几路。我们借鉴操作系统的虚拟内存思路,把 KV Cache 分页管理,按需分配,显存碎片大幅减少,同样的卡能多跑不少并发。

第三板斧是模型并行。GLM-5.3 这类大规模模型,单张卡根本装不下权重,必须做张量并行和数据并行组合。这里有一个经验:对于混合专家结构,专家并行(Expert Parallel)非常关键,它能让不同专家的计算分散到多张卡上并行处理,否则通信开销会把并行收益吃掉大半。正式对外开放前,我们专门调过并行策略和通信拓扑,效果差异能到 20% 以上。

2.3 延迟与稳定性的平衡:先保首字延迟,再谈总吞吐

吞吐和延迟在推理优化里经常打架。高吞吐要求请求尽量多打包,延迟要求请求尽快响应。Prime Inference 的取值逻辑是:交互式应用优先保障首字延迟,离线任务用剩余的算力填谷。

具体落地时,我们把 Prefill(预填充)和 Decode(逐字生成)拆成两个阶段来调度。因为一个超长 prompt 的 Prefill 阶段非常吃算力,如果让它和其他请求挤在同一批,很容易把别人正在生成的稳态节奏打乱,造成 P99 延迟飙升。细节上,我们给 Prefill 设置了 chunked 模式,把长 prompt 切成多个小段处理,避免单个请求独占 GPU。同时给 Decode 请求更高的调度优先级,因为它直接影响用户体验。

成本控制方面,我们大量使用 FP8/INT8 量化。GLM-5.3 量化为 FP8 后,显存占用降低接近一半,推理速度提升明显,效果损失在可接受范围内。这里的前提是要充分验证量化后的效果,不同任务表现不一样,代码生成和数学推理对精度更敏感,必须有针对性测试。

3. 首个对外开放端点:从模型加载到请求路由的完整链路

3.1 理解 Endpoint:端点到底是一个什么东西

很多开发者把 Endpoint 简单理解为“一个 URL”。实际上,在 Prime Inference 的设计里,Endpoint 是一组服务化配置的组合:绑定的模型版本、默认的推理参数模板、路由规则、可用实例池、配额限制和计量标识。

首个对外开放的 Endpoint 内部代号为“GLM-5.3-default”。它做的事情很简单:用户拿一个 API Key,通过标准接口把消息传进来,系统自动选择最优实例,调用 GLM-5.3 生成回复,再按流式或非流式方式返回。这背后的链路却很长。

一次请求从外部到达模型的完整路径大致是:客户端发起请求 -> API 网关 -> 密钥校验 -> 基础限流 -> 请求参数标准化 -> 路由模块选择合适的实例组 -> 推理引擎调度执行 -> 流式返回。任何一个环节出现瓶颈,最终都会体现在用户可感知的延迟和成功率上。

这里有一个设计心得:不要把模型推理参数写死在代码里,而是建模成“端点模板”。比如某个端点固定 temperature 为 0.7,那么用户传 0.3 也是无效的,模板优先。这样平台就能保证同一端点的输出稳定,售后排查时也不用拿用户的一个随机参数去复现问题。

3.2 模型部署与参数选型:不是所有“最佳参数”都能直接对外

对外开放的实例部署,和内部自用有一个显著区别:外部用户请求的上下文长度不可控。内部系统可以对单个业务方说“上下文别超过 32K”,外部不行,用户随时可能传一个超长文档进来。

所以我们给“GLM-5.3-default”端点做了一个折中:默认开放 32K 上下文,后台保留扩展通道,对已验证的开发者开放 128K。这个决策背后是显存和交付成本的考量,长上下文会让 KV Cache 占用暴涨,如果不限制,很容易被一些极端请求把整个实例拖垮。

部署参数上,我们使用 Tensor Parallel 并行度 8,即把模型切片到 8 张加速卡协同推理。这个参数不是越大越好,张数太多通信开销会抵消计算加速。经过实测,8 卡在这个模型规模上性价比最高。

推理参数方面,默认值最终定为:temperature 0.7,top_p 0.9,max_tokens 4096,禁止指定 seed。内部测试时发现,允许用户自定义 seed 会给结果复现带来额外承诺,当前阶段不适合开放。

3.3 一次标准推理调用长什么样

调用协议我们选择了现在最常见的 Chat Completions 风格,方便开发者直接用成熟的 SDK 接入。以下是一个非流式请求示例:

curl -X POST https://api.example.com/v1/chat/completions \ -H "Content-Type: application/json" \ -H "Authorization: Bearer your_api_key_here" \ -d '{ "model": "glm-5.3-default", "messages": [ {"role": "system", "content": "你是一个擅长代码审查的助手。"}, {"role": "user", "content": "请帮我看看这段 Python 代码有什么问题。"} ], "stream": false, "max_tokens": 1024 }'

响应结构包含了模型生成的文本,以及 token 消耗明细。实现上,我们专门区分了输入 token 和输出 token 的计量,因为计费口径和成本核算都需要分开统计。输入 token 会在请求进入时由 Tokenizer 预先计算,输出 token 则按生成结果统计,这里要特别注意不要直接用字符数近似,中英文平均 token 密度差异很大,乱估会造成账目混乱。

对于延迟敏感的应用,流式模式是必须的。流式将生成结果逐块返回,用户看到的“第一个字出来”的时间会大幅提前。在服务端,我们把流式回推做成增量编码,避免每次重复发送整个消息体。

4. 从内部系统到多租户服务:对外开放绕不开的五个技术改造点

4.1 多租户隔离与鉴权,不能只靠 API Key

内部系统按业务线划分权限,本质上是“熟人社会”。对外开放后,租户之间可能互不认识甚至存在竞争关系,隔离必须做实。

我在平台里落地了三级隔离:账户维度、项目维度、API Key 维度。每个 API Key 可以绑定特定项目,项目归属账户,账户绑定组织。模型实例池按重要程度划分,重要租户可以独占实例组,普通租户共享公共实例池。这样既控制了成本,又给高价值客户提供了稳定性的选择。

鉴权不能只校验 Key 是否存在,还要校验资源权限。曾经出现过内部某个测试 Key 拿到生产环境权限的配置事故,排查后我们把权限策略改成拒绝优先,未显式授权的一律不可访问。这个原则对外开放时必须咬死。

4.2 限流与配额,用令牌桶挡住流量尖峰

开放当天,我们预判过流量会来,但实际峰值仍然超出了预期。好在上线前给每个账户都配置了烧杯限流,否则网关先倒一片。

限流采用令牌桶算法:每个账户有一个桶,容量为突发允许的最大请求数,填充速率对应持续稳定的调用频率。同时在三个层级做控制:全局限流、账户限流、模型端点限流。这样任何一个账户疯狂刷量,都不会影响其他租户。

实践证明,限流策略必须提前预留“弹性余量”,不能卡在理论峰值。因为我们发现外部调用模式非常不稳定,有时候是五分钟内千级 QPS 的脉冲,这种流量如果用固定窗口限流,会误杀很多正常用户。令牌桶天然允许一定突发,更适合这种场景。

4.3 可观测性与灰度发布:没有全链路追踪,故障排查寸步难行

内部系统出问题,开发者可以直接找负责同事问;外部用户不会,他们只会在工单里贴一个 request ID。所以对外开放前,我们把全链路可观测性补齐了。

每个请求从网关开始就生成全局唯一的 request ID,日志、指标、调用链全部带上这个 ID。核心指标分四类:QPS 与成功率、TTFT(首 Token 延迟)、TPOT(每个 Token 的生成耗时)、GPU 利用率和显存水位。这几个指标能覆盖绝大多数服务质量问题。

发布策略上也做了严格管控:任何端点配置变更先走影子实例,也就是新实例和旧实例同时跑,但是新实例只接少量真实请求,观察分位数指标。确认没有恶化后,再切 5% 流量、25%、50%、100%,每个阶段至少稳定 10 分钟。这套流程看起来繁琐,但开放初期救了我们很多次,因为模型服务化配置经常出现“看起来没问题,跑起来就崩”的情况。

4.4 计量与计费:按 Token 计量,按维度分摊

对外开放的真实需求是付费能力。计量系统是我认为整个项目里最容易低估的部分。

token 计量必须从请求入口到模型内核全链路埋点。我们选择在推理引擎层做精确 token 计数,而不是靠网关统计字符数。因为同一个字符串在不同模板下 token 数量不同,从网关粗算会有误差。计费报表按小时粒度输出,按账户、项目、模型、端点四个维度汇总。

账单数据写入独立的存储队列,绝不与在线推理链路耦合。刚开始有人建议直接写业务数据库,被否了。计费数据量非常大,一天的 token 明细记录就有几亿条,如果实时写库,主库压力暴增,会影响在线推理的稳定性。现在我们是异步批量入库,数据延迟五分钟左右,完全够用。

4.5 内容安全与请求防滥用:外部环境必须有系统级兜底

这一块是真正区分“内部平台”和“对外产品”的分界线。

输入侧,我们增加了内容审核网关,对文本做分类检测,拦截违规内容。输出侧,模型生成内容同样要过一遍审核,防止模型被恶意诱导输出不合规内容。审核服务本身用独立实例,不能因为审核模块故障拖垮推理主链路。

Prompt 注入防护也不能指望提示词本身,需要在网关层做行为检测。比如一个用户短时间内提交大量“忽略以上规则”的样本,就要触发风控策略。同时要限制单次请求的内容大小和上下文长度,防止有人故意塞入超大 payload 导致实例资源被耗尽。公网环境里,每秒都有机器扫描端口和尝试无效 Key,这些流量全部要在进入推理引擎之前被挡掉。

5. 开放初期踩坑实录:常见故障与排查手册

5.1 故障案例:压测时 P99 延迟从 800ms 飙到 8 秒

开放前的性能压测,第一轮就出问题。并发请求一多,P99 延迟从 800 毫秒直接飙到 8 秒,界面上看就像卡死。

排查后发现,问题出在一个超长 prompt 请求上。这个请求有接近 3 万 token,在 Prefill 阶段占用了大量计算资源,同一批 GPU 上的其他 Decode 请求全部被阻塞。虽然我们有连续批处理,但 Prefill 的算力分配没有和 Decode 隔离,一个大家伙进来了,周围的人全遭殃。

解法就是之前提到的 chunked prefill,把超长 prompt 切分成多个小块处理,每块之间让出 GPU 给 Decode 请求。同时给 Decode 请求单独建了优先队列,即使 Prefill 还没完成,也保证已有生成的请求稳定输出。压测通过后,这个方案补丁写进了部署模板,后续所有新模型默认启用。

5.2 故障案例:同一个问题反复调用,回答质量时好时坏

对外开放一周后,有开发者反馈同一个 model_id 下,回答效果时好时坏。我们一开始怀疑模型量化出了问题,后来拉日志发现,用户请求里没有传 temperature,但网关在协议转换时默认填了一个随机值,而不是端点模板里配置的 0.7。

这个问题很隐蔽。模型服务化平台通常有参数覆盖机制,但我们在设计网关时允许客户端参数直接透传,导致内部的“默认参数兜底”没有生效。修复很简单,网关层做字段过滤,未显式传入的参数一律从端点模板取值,客户端参数优先级被降低。这个事故后来固化成一条规则:凡是会显著影响生成质量的参数,必须以端点模板为准。

5.3 故障案例:并发一高就显存 OOM,重启后还是复现

还有一次比较头疼的 OOM。单实例并发 128 时直接卡死,重启后恢复,但过一阵又出现。问题不是实例数量不够,而是显存中 KV Cache 和模型权重抢空间。

根源是请求上下文长度分布不均。有些长上下文请求会在推理过程中动态申请大量显存,再加上我们没有在一开始限制实例级的并发数,结果显存在高负载时被挤爆。修复分三步:第一,实例启动前计算显存预算,给 KV Cache 预留固定上限;第二,请求进入实例前先检查预计上下文长度,超限直接拒绝;第三,动态调整实例并发上限,不再盲目高并发。

这个案例提醒我:显存优化不能只靠 PagedAttention,实例级的资源治理同样重要。推理引擎再聪明,也要有上层配额约束。

5.4 排查速查表:开发者遇到问题可以直接对照

我把开放初期最常见的几类问题整理成了速查表,运维和开发者参考起来更高效,也减轻了工单压力。

现象可能原因排查思路修复建议
首 Token 延迟高Prefill 阶段排队阻塞看 TTFT 指标与 prefill 队列长度启用 chunked prefill,为 decode 单独设优先队列
整体吞吐上不去GPU 利用率低或批处理太小查连续批处理开关与动态批参数拉大 batch 上限,适当增加收集请求的等待时间
回答时好时坏采样参数被客户端覆盖对比请求参数与端点模板配置网关做参数过滤,缺失参数从模板兜底
高并发时 OOMKV Cache 超出显存预算查显存水位与实例并发数限制单请求上下文长度,设定实例级并发上限
偶发 5xx上游实例过载或队列满看网关错误分布和队列深度扩容或升级限流策略,必要时启用重试机制

5.5 预留重试策略这件事,细节比想象中多

对外开放后,我们最初的超时设置偏乐观,导致用户经常遇到连接中断。后来调整了超时策略:读超时设为 60 秒,写超时设为 90 秒,模型推理请求本身不做无条件重试。

为什么不做无条件重试?因为大模型生成是计算密集型的,如果用户的请求因为网络抖动超时了,我们在服务端已经把 token 算完了,客户端重发一次就意味着重复计算,成本翻倍。正确做法是客户端使用指数退避重试,并且只在明确拿到网络错误时才重发,不能一超时就重试。这个过程中的成本意识和内部系统完全不同,内部重试只是多花一点算力,外部重试是直接烧钱。

我个人在实际操作中体会最深的一点是:对外开放推理系统,真正的难点不在模型,而在于把一套为“自己人”设计的系统,改造成能让“陌生人”稳定使用的产品。内部每天烧万亿 token 的日子没有白过,如果没有那种高负载环境下逼出来的连续批处理、分页缓存、优先级调度,Prime Inference 根本不具备对外服务的底气。

最后分享一个小技巧:端点开放前,一定要先做一周的非生产实战演练。把内部真实请求录制下来,按外部调用模型重放,同时人为注入故障,比如杀掉几个实例、把网络延迟调高、压低 GPU 频率。这套演练跑完,你对系统的信心会比任何基准测试都实。开放之后,第一个端点的表现也验证了这个思路的价值。后续再上新模型,流程就可以直接复用了。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询