你的 AI 账单一夜之间翻了三倍。模型、流量甚至提示词的内容都没有变化;罪魁祸首仅仅是一行破坏了 OpenAI 提示词缓存(prompt cache)的代码。

为什么缓存至关重要

服务商的提示词缓存通过跳过对具有字节级完全相同前缀的请求进行重复处理,从而为你节省费用。如果前几个 token 与之前的调用相匹配,服务商会重用这些 token 已计算出的表示形式,并且仅针对新的后缀部分计费。规则非常严格:匹配必须是完全一致的,而不仅仅是相似。开头哪怕只有一个 token 不同,也会导致整个缓存命中失效。

导致命中率骤降的错误

在我们的智能体(agent)中,我们将当前时间戳放在系统提示词的最顶端,以赋予模型一种“当下”的概念。由于时间戳每秒都在变化,导致每次请求的首个 token 序列都是唯一的。缓存从未找到匹配项,因此每次调用都要为后续的 18,000 个静态 token 全额付费——包括工具架构(tool schemas)、文档片段、少样本示例(few-shot examples)和固定指令。结果是缓存命中率为 0%,账单也随之膨胀了三倍。

为了提高可缓存性而进行的重排序

解决方法很简单:将所有永不改变的内容放在提示词的最前面,并将任何易变数据推到最后。

静态前缀(可缓存)

  • 工具定义
  • 检索文档
  • 少样本示例
  • 固定系统指令

易变后缀(不可缓存)

  • 当前时间
  • 会话标识符
  • 用户消息
  • 实时上下文

如果模型需要时间,请将其附加在静态块之后,而不是将其置于开头。这样,缓存就可以重用庞大的静态部分,同时你仍然可以在末尾提供新鲜的上下文。

技术栈中的隐形杀手

即使模板看起来是正确的,中间件或 SDK 也可能在负载(payload)到达 API 之前,悄无声息地在前面添加元数据——如请求 ID、时间戳或其他标头。一些部署流水线在每次发布时也会重新排列工具定义。这些不可见的更改改变了字节序列,即使你没有更改自己的提示词构建器代码,也会破坏缓存。

密切关注缓存命中率

将缓存命中率视为任何 AI 智能体的主要健康指标。命中率突然下降预示着请求开头字节中的某些内容变得具有变量性。提供命中率百分比的监控工具可以让你在成本异常爆发前及时发现问题。

总结

提示词缓存取决于不可变的前缀。每次请求开头任何发生变化的内容——哪怕只是一个时间戳——都会使缓存失效,并可能让你的账单翻三倍。保持静态内容在前,易变内容在后;审计你的工具链是否存在隐藏的前置项;并密切关注缓存命中率。有条理的提示词布局既能保护性能,也能保护你的利润。