高级 API 用法

上下文压缩

查看 Markdown

当对话增长到数千个 token 以上时,每次后续调用都会重新发送此前的全部消息,并为它们支付输入 token 费用。上下文压缩可将这些消息压缩为一个不透明项目;它保留关键状态,包括 system prompt、附件、此前的推理和各轮对话的压缩记录,同时舍弃冗长的 tool 输出和来回对话。

随后将该压缩项目原样传入下一次请求,模型会像完整历史仍然存在一样继续对话。

  • 降低输入成本 — 下一次调用只需为压缩后的上下文付费,而非原始消息。

  • 降低延迟 — 请求负载更小,首个 token 的返回时间更短。

  • 响应更聚焦 — 更紧凑的上下文让模型专注于当前任务,避免受到过时 tool 输出和旧轮次的干扰。

  • 支持更长对话 — 让持续数小时的 agent 循环远低于模型的上下文窗口限制。


何时压缩

全部条件全部满足时进行压缩:

  • 对话已增长到每次调用的 input_tokens 会拖累成本或延迟的程度。

  • 你仍希望模型记住先前轮次(否则直接开始新对话即可)。

  • 当前上下文仍未超过模型的上下文限制(压缩能缩短对话,但无法挽救已经超出限制的请求)。

典型做法是在 agent 循环中每 N 轮调用一次 Compaction API,或在记录显示渲染后的上下文超过你为当前工作负载设定的阈值时调用。


Compaction API

发送要压缩的对话。响应包含一个代表此前完整对话的单一压缩项目;你可以安全地从客户端状态中删除原始消息,将该压缩项目置于下一次请求的开头,并在其后追加新的用户轮次。

# Step 1 — compact the long conversation
curl -s https://api.x.ai/v1/responses/compact \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $XAI_API_KEY" \
  -d '{
    "model": "grok-4.7",
    "input": [
      {"role": "system", "content": "You are a concise and knowledgeable science tutor."},
      {"role": "user", "content": "What is the Higgs boson and why is it important?"},
      {"role": "assistant", "content": "The Higgs boson is an elementary particle..."},
      {"role": "user", "content": "How does the Higgs mechanism actually work?"},
      {"role": "assistant", "content": "The Higgs mechanism works through spontaneous symmetry breaking..."}
    ]
  }'

# Step 2 — continue the conversation using the compacted output
curl -s https://api.x.ai/v1/responses \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer $XAI_API_KEY" \
  -d '{
    "model": "grok-4.7",
    "input": [
      {
        "type": "compaction",
        "id": "cmp_abc123",
        "encrypted_content": "<paste encrypted_content from step 1>"
      },
      {"role": "user", "content": "Based on our earlier conversation, what gives particles their mass?"}
    ]
  }'

xAI SDK 还提供 AsyncClient,其中的 await client.chat.compact_context(...)await chat.sample() 可在 asyncio 下实现相同流程。

响应结构

REST endpoint(POST /v1/responses/compact)返回兼容 OpenAI 的压缩对象:

JSON

{
  "id": "cmp_01HZ9P0V8M2YQK3F7C4G6N5R2A",
  "object": "response.compaction",
  "created_at": 1748895600,
  "model": "grok-4.7",
  "output": [
    {
      "type": "compaction",
      "id": "cmp_01HZ9P0V8M2YQK3F7C4G6N5R2A",
      "encrypted_content": "<opaque blob>"
    }
  ],
  "usage": {
    "input_tokens": 12000,
    "input_tokens_details": { "cached_tokens": 0 },
    "output_tokens": 800,
    "output_tokens_details": { "reasoning_tokens": 240 },
    "total_tokens": 12800,
    "dropped_message_count": 45
  }
}
字段说明
id此次压缩的稳定 ID(cmp_<uuid>),内部压缩项目中也会返回此值。
object始终为 "response.compaction" 下实现相同流程。
output包含单个 个压缩项目的数组。请将其原样传入下一次请求。
output[].type始终为 "compaction" 下实现相同流程。
output[].encrypted_content包含压缩后对话的不透明 blob。
usage.input_tokens压缩前对话中的 token 数量。
usage.output_tokens为压缩记录生成的 token 数量。模型会在下一次调用中恢复该 blob,其内容大致为保留的 system prompt 加上这些 token。
usage.dropped_message_count折叠到压缩记录中的输入消息数量。

xAI SDK 中的原地压缩

对于长时间运行的 agent 循环,xAI SDK 在活动 Chat 对象上提供了便捷方法:chat.compact()会对 Chat 当前的消息执行压缩,并用压缩项目替换原地替换它们。之后仍可像以前一样继续调用 chat.sample();服务器会在下一次请求时恢复压缩后的前缀。

Python

import os
from xai_sdk import Client
from xai_sdk.chat import system, user

client = Client(api_key=os.environ["XAI_API_KEY"])

# use_encrypted_content=True preserves the model's reasoning content across
# turns, recommended when using reasoning models.
chat = client.chat.create(model="grok-4.7", use_encrypted_content=True)
chat.append(system("You are a helpful assistant. Keep answers brief."))

compact_every = 5
for turn in range(1, 100):
    chat.append(user(input("You: ")))
    response = chat.sample()
    print(f"Grok: {response.content}")
    chat.append(response)

    if turn % compact_every == 0:
        before = len(chat.messages)
        compact = chat.compact()
        print(
            f"[compacted {before}{len(chat.messages)} messages | "
            f"dropped {compact.dropped_message_count} | "
            f"tokens used: {compact.usage.total_tokens}]"
        )

同一方法也可用于 AsyncClient 视为await chat.compact() 下实现相同流程。


限制与注意事项

  • 要压缩的对话必须仍能装入上下文。 压缩会缩短对话,但无法挽救超出限制的请求。如果对话已经超过 context_length_exceeded,则需先裁剪或拆分,再调用压缩方法。

  • 每次调用最多进行一次压缩。该 endpoint 每个请求只执行一次压缩。

  • encrypted_content 是不透明内容。 不要解析、编辑或手动合并多个 blob。始终将完整的 output 数组(或 CompactContextResponse)原样传回。

  • 可再次压缩。你可以稍后再次压缩已经压缩过的对话,例如当对话在上一次压缩之后再次变长时。

  • 压缩调用的 token 用量。压缩本身会使用 token(可在 usage.input_tokens / usage.output_tokens 中查看)。如果频繁压缩,请选择更小、更快的模型。



最后更新:2026 年 9 月 2 日