模型能力
持久化生成输出
在任何 Imagine 请求中使用 storage_options 将生成的资源持久化到您的 Files API 存储中,之后您可以通过经过身份验证的 Files API 检索它。此外,设置 storage_options.public_url 来为资源额外生成一个永久的、可共享的公共 URL—一个任何人都可以打开且在您撤销前一直有效的未经验证的链接。
存储和公共 URL 的创建是独立的:您可以在没有公共 URL 的情况下私有存储,或者使用公共 URL 存储。无论哪种方式,响应中还包括默认情况下始终返回的临时生成 URL。
快速开始
生成图像,将其持久化到 Files,并获取可共享的公共 URL — 所有操作在一次调用中完成:
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
response = client.image.sample(
prompt="A serene Japanese garden in winter",
model="grok-imagine-image-quality",
storage_options={"filename": "garden.jpg", "public_url": True},
)
# Ephemeral, short-lived URL.
print(f"Ephemeral: {response.url}")
# Persistent file in your Files API storage.
print(f"File ID: {response.file_output.file_id}")
# Permanent, shareable public URL.
print(f"Public URL: {response.public_url}")curl -s -X POST https://api.x.ai/v1/images/generations \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-image-quality",
"prompt": "A serene Japanese garden in winter",
"response_format": "url",
"storage_options": {
"filename": "garden.jpg",
"public_url": true
}
}'响应体如下所示:
{
"data": [
{
"url": "https://imgen.x.ai/xai-imgen/xai-tmp-imgen-abc123.jpg",
"file_output": {
"file_id": "file_7de029f4-eb66-42ee-87f8-b2a9d9e7466a",
"filename": "garden.jpg",
"public_url": "https://files-cdn.x.ai/ZsqeMtdcSYWPPHTQdxXDKQ/file_7de029f4-eb66-42ee-87f8-b2a9d9e7466a.jpg"
}
}
]
}需要注意的关键点:
data[i].url是临时的 Imagine URL — 短期有效,适合立即使用。无论是否指定storage_options,它总是被返回。data[i].file_output.file_id是生成资源的稳定 Files API 标识符。data[i].file_output.public_url是永久的公共 URL。用于共享、嵌入和您的应用中的长期存储。
storage_options 参考
| 字段 | 类型 | 描述 |
|---|---|---|
filename | string (必需) | 存储文件的文件名。公共 URL 路径上的扩展名从此文件名派生。 |
expires_after | integer (可选) | 从现在起存储文件过期的秒数。必须在 3600(1小时)和 2592000(30天)之间。省略表示永久存储。 |
public_url | boolean 或 object (可选) | 设置为 true 以使用默认设置创建公共 URL,或传递对象进行配置。省略(或设为 false)表示私有存储。 |
public_url.expires_after | integer (可选) | 从现在起公共 URL 过期的秒数。必须在 3600(1h)和 2592000(30d)之间。参见 过期行为。 |
filename 是必需的。仅传递 storage_options={"filename": "..."} 而不传递其他字段会将资源私有存储:存储的文件不过期且没有公共 URL。如果您改变主意,之后可以随时对存储的 file_id 调用 create_public_url。
response = client.image.sample(
prompt="A red circle on a white background",
model="grok-imagine-image-quality",
storage_options={"filename": "circle.jpg"}, # store privately, no public URL
)
print(response.file_output.file_id) # file_...
print(response.file_output.filename) # circle.jpg
print(response.public_url) # None — public URL was not requestedcurl -s -X POST https://api.x.ai/v1/images/generations \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-image-quality",
"prompt": "A red circle on a white background",
"response_format": "url",
"storage_options": {"filename": "circle.jpg"}
}'过期行为
storage_options 暴露了两个独立的过期控制:storage_options.expires_after 控制存储文件的自动删除时间,storage_options.public_url.expires_after 控制公共 URL 的自动撤销时间。省略 public_url.expires_after,URL 将继承文件的过期时间(如果文件没有过期时间,则永不过期)。
公共 URL 的寿命永远不会超过其文件,且这两个值都必须在1小时和30天之间。完整的规则参见 公共 URL → 过期行为;下面的示例展示了这两个控制如何在 Imagine 请求中组合使用。
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
# Permanent file, public URL expires in 24h.
response = client.image.sample(
prompt="A futuristic city skyline at night",
model="grok-imagine-image-quality",
storage_options={"filename": "skyline.jpg", "public_url": {"expires_after": 86400}}, # 24h
)
print(response.file_output.file_id) # file_...
print(response.public_url) # https://files-cdn.x.ai/<token>/file_....jpg
print(response.file_output.public_url_expires_at) # protobuf Timestamp, ~24h from now
# File and public URL both expire in 2h (URL inherits the file's expiry).
response = client.image.sample(
prompt="A futuristic city skyline at night",
model="grok-imagine-image-quality",
storage_options={"filename": "skyline.jpg", "expires_after": 7200, "public_url": True},
)
print(response.file_output.file_id) # file_...
print(response.public_url)
print(response.file_output.expires_at) # ~2h from now
print(response.file_output.public_url_expires_at) # matches file's expires_at
# File expires in 24h, public URL expires in 1h (independent, shorter).
response = client.image.sample(
prompt="A futuristic city skyline at night",
model="grok-imagine-image-quality",
storage_options={
"filename": "skyline.jpg",
"expires_after": 86400,
"public_url": {"expires_after": 3600},
},
)
print(response.file_output.file_id) # file_...
print(response.public_url)
print(response.file_output.expires_at) # ~24h from now
print(response.file_output.public_url_expires_at) # ~1h from now (URL dies before file)# Permanent file, 24h public URL
curl -s -X POST https://api.x.ai/v1/images/generations \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-image-quality",
"prompt": "A futuristic city skyline at night",
"response_format": "url",
"storage_options": {
"filename": "skyline.jpg",
"public_url": {"expires_after": 86400}
}
}'
# 2h file, public URL inherits the same expiry
curl -s -X POST https://api.x.ai/v1/images/generations \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-image-quality",
"prompt": "A futuristic city skyline at night",
"response_format": "url",
"storage_options": {
"filename": "skyline.jpg",
"expires_after": 7200,
"public_url": true
}
}'file_output 响应
每个设置了 storage_options 的 Imagine 响应在每个生成资源上都包含一个 file_output 块:
| 字段 | 是否始终存在 | 含义 |
|---|---|---|
file_id | yes | 稳定的 Files API 标识符。用于 client.files.* 操作。 |
filename | yes | 您在 storage_options 中提供的文件名。 |
expires_at | 仅在文件设置了过期时间时 | 文件过期的 Unix 时间戳。 |
public_url | 仅在设置了 storage_options.public_url 且创建成功时 | 永久的可共享 URL。 |
public_url_expires_at | 仅在公共 URL 有过期时间时 | 公共 URL 失效的 Unix 时间戳。永久 URL 不存在此字段。 |
public_url_error | 仅在部分失败时 | 资源已存储但公共 URL 创建失败时的人类可读错误。参见 公共 URL 错误。 |
Python SDK 还在 ImageResponse 和 VideoResponse 上将 response.public_url 和 response.public_url_error 作为顶级快捷方式提供。
多个输出 (n > 1)
当您在一次调用中请求多个图像时,每个图像都有自己的 file_id 和带有唯一令牌的自己的 public_url。这些文件是完全独立的 — 撤销或删除一个不会影响其他文件。
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
responses = client.image.sample_batch(
prompt="A cat wearing a hat, four different art styles",
model="grok-imagine-image-quality",
n=4,
storage_options={"filename": "cat-styles.jpg", "public_url": True},
)
for r in responses:
print(r.file_output.file_id, r.public_url)curl -s -X POST https://api.x.ai/v1/images/generations \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-image-quality",
"prompt": "A cat wearing a hat, four different art styles",
"n": 4,
"response_format": "url",
"storage_options": {"filename": "cat-styles.jpg", "public_url": true}
}'存储图像编辑输出
storage_options 在 /v1/images/edits 上的工作方式与 /v1/images/generations 相同。编辑后的结果存储为新文件。
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
response = client.image.sample(
prompt="Add a party hat to the dog",
model="grok-imagine-image-quality",
image_url="https://docs.x.ai/assets/api-examples/images/style-realistic.png",
storage_options={"filename": "party-dog.png", "public_url": True},
)
print(response.file_output.file_id) # new file, not the input
print(response.public_url)curl -s -X POST https://api.x.ai/v1/images/edits \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-image-quality",
"prompt": "Add a party hat to the dog",
"image": {
"url": "https://docs.x.ai/assets/api-examples/images/style-realistic.png"
},
"response_format": "url",
"storage_options": {"filename": "party-dog.png", "public_url": true}
}'存储视频输出
视频端点(/v1/videos/generations、/v1/videos/edits、/v1/videos/extensions)使用相同的 storage_options 结构。由于视频生成是异步的,file_output.public_url 在视频生成完成后在已完成的响应中填充。
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
# SDK handles polling automatically and returns the completed video.
response = client.video.generate(
prompt="A ball bouncing slowly on a flat surface",
model="grok-imagine-video-1.5",
duration=5,
storage_options={"filename": "bouncing-ball.mp4", "public_url": True},
)
print(response.url) # ephemeral vidgen URL
print(response.file_output.file_id) # file_...
print(response.public_url) # https://files-cdn.x.ai/<token>/file_....mp4# Start the generation
REQUEST_ID=$(curl -s -X POST https://api.x.ai/v1/videos/generations \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "grok-imagine-video-1.5",
"prompt": "A ball bouncing slowly on a flat surface",
"duration": 5,
"storage_options": {"filename": "bouncing-ball.mp4", "public_url": true}
}' | jq -r '.request_id')
# Poll until done
while true; do
RESULT=$(curl -s "https://api.x.ai/v1/videos/$REQUEST_ID" \
-H "Authorization: Bearer $XAI_API_KEY")
STATUS=$(echo "$RESULT" | jq -r '.status')
if [ "$STATUS" = "done" ]; then
echo "$RESULT" | jq '.video.file_output'
break
fi
sleep 5
done图像转视频、视频编辑和视频扩展都以相同的方式接受 storage_options。
公共 URL 错误
在极少数情况下,即使资源生成和存储成功,公共 URL 的创建也可能失败 — 例如,在临时基础设施问题或团队达到其 活跃 URL 配额 时。整个请求不会被中止,响应仍包含有效的 file_output.file_id 和原始资源 URL,只有 public_url 被 public_url_error 替换:
{
"data": [
{
"url": "https://imgen.x.ai/.../xai-tmp-imgen-abc123.jpg",
"file_output": {
"file_id": "file_abc123",
"filename": "poster.jpg",
"public_url_error": "Public URL creation timed out. The file was stored successfully."
}
}
]
}如果您看到 public_url_error,文件仍在您的存储中 — 您可以直接通过 Files API 重新尝试公共 URL 创建,而无需重新生成资源:
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
response = client.image.sample(
prompt="A vintage poster",
model="grok-imagine-image-quality",
storage_options={"filename": "poster.jpg", "public_url": True},
)
if response.public_url_error:
# The image is stored — just retry the public URL on the file directly.
resp = client.files.create_public_url(response.file_output.file_id)
public_url = resp.public_url
else:
public_url = response.public_url
print(public_url)管理通过 Imagine 创建的文件
通过 storage_options 创建的文件是完整的 Files API 一级文件。使用 Files API 来列出、检索、更新和删除它们,并使用公共 URL 端点在事后撤销或重新创建 URL:
import os
import xai_sdk
client = xai_sdk.Client(api_key=os.getenv("XAI_API_KEY"))
response = client.image.sample(
prompt="A futuristic city",
model="grok-imagine-image-quality",
storage_options={"filename": "city.jpg", "public_url": True},
)
file_id = response.file_output.file_id
# Inspect file metadata
file = client.files.get(file_id)
# Stop sharing publicly (keeps the file in your storage)
client.files.revoke_public_url(file_id)
# Generate a new public URL later with a different expiry
client.files.create_public_url(file_id, expires_after=604800) # 7 days
# Delete the file entirely (also tears down any active public URL)
client.files.delete(file_id)FILE_ID="<file_output.file_id from the generation response>"
# Stop sharing publicly (file stays in your storage)
curl -s -X POST "https://api.x.ai/v1/files/$FILE_ID/public-url/revoke" \
-H "Authorization: Bearer $XAI_API_KEY"
# Re-create with a 7-day expiry
curl -s -X POST "https://api.x.ai/v1/files/$FILE_ID/public-url" \
-H "Authorization: Bearer $XAI_API_KEY" \
-H "Content-Type: application/json" \
-d '{"expires_after": 604800}'
# Delete the file (also revokes the public URL)
curl -s -X DELETE "https://api.x.ai/v1/files/$FILE_ID" \
-H "Authorization: Bearer $XAI_API_KEY"限制
- 每个团队最多 1,000 个活跃公共 URL。 达到上限会在响应中设置
public_url_error;撤销未使用的 URL 以释放插槽。 - 过期限制(参见 过期行为):
- 两个
expires_after值都必须在1小时和30天之间。 public_url.expires_after必须 ≤ 文件的expires_after。
- 两个
- 自定义文件名影响公共 URL 路径。 传递
storage_options.filename = "my-cover.png"会使公共 URL 以.png结尾。存储的内容类型仍由生成的资源决定,而非文件名。 response_format不影响存储。 无论您请求url还是b64_json,storage_options都会执行。- 公共 URL 与临时 URL 是独立的。 两者都在同一响应中返回,但有各自的生命周期。撤销公共 URL 不会影响临时 URL。
- 所有验证都是同步的。 无效的存储配置在生成开始前会被拒绝,因此您永远不会因格式错误的请求而浪费计算资源。
相关
- Files API 集成 — 概述 + 完整示例,展示输入和输出。
- 将文件作为输入引用 — 输入端:用存储的
file_id替代 URL。 - 文件 → 公共 URL — 任何文件的公共 URL 生命周期,无论其创建方式。
- 管理文件 — 上传、列出、检索、更新和删除文件。