主题
语言

Files API 和 PDF

OpenAI 兼容的 GetVibe API Files API 和 PDF 输入:在 chat/completions、responses 和 messages 中使用 base64、链接或 file_id;哪些模型可以读取 PDF 内的图片;以及限制和错误。

兼容 OpenAI 的 Files API,用于上传、读取和删除文件。每项操作都需要 API key;文件只能由上传该文件的同一客户端账户访问。

上传文件

POSThttps://getvibeapi.com/v1/files

发送包含必需的 multipart/form-data、file 和 purpose 字段的请求。允许的用途:assistants、batch、fine-tune、vision 和 user_data。文件大小上限为 50 MiB(52 428 800 字节);超出后返回 413。

curl -X POST https://getvibeapi.com/v1/files \
  -H "Authorization: Bearer $GETVIBE_API_KEY" \
  -F "purpose=user_data" \
  -F "file=@./report.pdf"

获取元数据、内容或删除

GEThttps://getvibeapi.com/v1/files/{file_id}
GEThttps://getvibeapi.com/v1/files/{file_id}/content
DELETEhttps://getvibeapi.com/v1/files/{file_id}

上传会返回一个 file 对象,其中包含不透明的 id、名称、大小、用途和创建时间。不带 /content 的 GET 请求会返回这些元数据;GET /content 会下载原始字节。成功执行 DELETE 后,两个 GET 请求都会返回 404。其他账户已有的文件会返回 403,未知标识符会返回 404。

安全工作流

  1. 上传文件,并仅保留返回的 file_id。
  2. 使用相同的密钥验证元数据;使用 Responses 时,将此 id 传入 input_file.file_id。
  3. 不要上传机密信息,并在完成后删除文件。删除的文件无法恢复。

模型请求中的 PDF

所有文本模型都能在全部三种 API 格式中接收 PDF。简而言之:通过以下三种方式中的任意一种发送文件——默认情况下,我们会免费提取文本并将其传递给模型。模型可以读取文本和表格,但看不到 PDF 中的图片或扫描件。若图片、版式或扫描件很重要,请从下表中选择一个模型并关闭文本提取。本页所有内容均已于 November 2, 2026 通过实时请求验证,测试文件为一份包含文本、表格和图片的三页 PDF。

发送 PDF 的三种方式

方法如何适用场景
请求中的 base64Chat:{"type":"file","file":{"filename":"report.pdf","file_data":"data:application/pdf;base64,…"}};Responses:{"type":"input_file","filename":"report.pdf","file_data":"data:…"};Messages:{"type":"document","source":{"type":"base64","media_type":"application/pdf","data":"…"}}一次性文档。适用于全部三个端点。文件最大为 20 MiB。
公开链接Chat:"file":{"file_url":"https://…"};Responses:{"type":"input_file","file_url":"https://…"};Messages:"source":{"type":"url","url":"https://…"}文件已在线。我们会自行下载:仅支持 HTTPS,无需登录或密码,服务器必须返回 application/pdf,文件大小不超过 20 MiB,下载须在 10 秒内完成,最多允许 3 次重定向。
上传后 file_id使用 POST /v1/files 和 purpose=user_data 上传,然后使用:Chat "file":{"file_id":"file-pv-…"}、Responses {"type":"input_file","file_id":"file-pv-…"}、Messages "source":{"type":"file","file_id":"file-pv-…"}在多个请求中使用同一份文档:无需每次都重新发送数 MB 的文件,且相同的请求前缀会被缓存。文件会保留 7 天,且仅对你的账户可见。

可直接运行的示例

从 GETVIBE_API_KEY 环境变量读取 key。Python 示例原样使用官方 openai 和 anthropic SDK,只有地址不同。

/v1/chat/completions

# PDF inline (base64); jq builds the body so a large file does not hit the command-line length limit
# macOS: replace base64 -w0 report.pdf with base64 -i report.pdf
jq -n --rawfile b64 <(base64 -w0 report.pdf) '{model: "deepseek-v4.1-flash", messages: [{role: "user", content: [
    {type: "text", text: "Summarise the document"},
    {type: "file", file: {filename: "report.pdf", file_data: ("data:application/pdf;base64," + $b64)}}]}]}' |
curl https://getvibeapi.com/v1/chat/completions \
  -H "Authorization: Bearer $GETVIBE_API_KEY" -H "Content-Type: application/json" -d @-

/v1/responses

# FILE_ID comes from the upload, see the "curl · file_id" tab above
curl https://getvibeapi.com/v1/responses \
  -H "Authorization: Bearer $GETVIBE_API_KEY" -H "Content-Type: application/json" \
  -d '{"model":"gpt-6.1-sol","input":[{"role":"user","content":[
    {"type":"input_text","text":"What were the sales in Kazan in August?"},
    {"type":"input_file","file_id":"'"$FILE_ID"'"}]}]}'
# base64 instead of file_id:
#   {"type":"input_file","filename":"report.pdf","file_data":"data:application/pdf;base64,…"}

/v1/messages

curl https://getvibeapi.com/v1/messages \
  -H "x-api-key: $GETVIBE_API_KEY" -H "anthropic-version: 2023-06-01" -H "Content-Type: application/json" \
  -d '{"model":"claude-sonnet-5.5","max_tokens":1024,"messages":[{"role":"user","content":[
    {"type":"document","source":{"type":"file","file_id":"'"$FILE_ID"'"}},
    {"type":"text","text":"Summarise the document"}]}]}'
# other sources:
#   "source":{"type":"base64","media_type":"application/pdf","data":"<base64>"}
#   "source":{"type":"url","url":"https://example.com/report.pdf"}

模型看到的内容:文本还是文件本身

默认情况下,提取文本。我们会提取 PDF 的文本层,并将其传递给模型,而不是传递文件。此操作免费,且适用于任何模型,即使该模型不支持 PDF。模型可以看到文字和数字,包括表格(没有边框,但数值正确)。它看不到的内容包括:图片、图表、印章、签名、颜色和版式。每个请求最多传递 60,000 个字符的文本(约 28 页密集内容);超出部分会被截断,并告知模型文档已被截断。x-pv-document-shim响应头会说明处理结果:applied:text_extracted表示模型收到的是文本,not-needed:lane_reads_pdf表示模型收到的是文件本身。

文件本身。若要让模型查看完整页面(包括图片和版式),请在请求正文中添加 "plugins":[{"id":"documents","enabled":false}](此时响应头会显示 not-needed:disabled_by_client)。仅对表格中标记为“yes”的模型使用此方式:其他模型会回答 400 或表示看不到文件,但文件的输入 token 仍会计费。

# curl: add the field to the request body
"plugins": [{"id": "documents", "enabled": false}]

# Python (openai SDK)
r = client.chat.completions.create(
    model="gpt-6.1-sol",
    messages=[...],
    extra_body={"plugins": [{"id": "documents", "enabled": False}]},
)
模型默认情况下可看到文件本身(关闭提取)
gpt-6.1-sol文件本身是 — 在 /chat/completions 和 /responses 上
gpt-6-lunatext是 — 在 /chat/completions 和 /responses 上
gpt-5.6-soltext尚未确认 — 保持默认设置
claude-sonnet-5.5, claude-opus-5.5text否 — 模型无法看到文件,因此即使插件已关闭,我们仍会提取文本(响应头 x-getvibe-warnings: plugin_overridden:documents);如需文件本身,请使用 gpt-6.1-sol
claude-haiku-5.5text否 — 模型看不到文件
gemini-4-argon, gemini-3.8-flashtext否 — 模型看不到文件,或返回 400
qwen3.8-flashtext是 — 在 /chat/completions 上;在 /responses 上返回 400
deepseek-v4.1-flash, glm-5.3, kimi-k3text否 — 400

测试方法:要求模型提供第 1 页中的一个词、表格单元格中的一个数字,并描述一张图片(形状、颜色和以图像绘制的数字)。“Text”表示模型正确说出了该词和数字,并表示看不到图片。“Yes”表示模型也正确描述了图片。通过 /v1/chat/completions 或 /v1/responses 将 PDF 发送给 GPT、Gemini 和 Qwen 模型:在 /v1/messages 上,它们看不到文件本身。

扫描件。扫描件没有文本层,因此无法提取文本,模型会收到原始文件(响应头为 not-needed:no_text_layer_unmeasured_lane)。这取决于模型:gpt-6.1-sol和qwen3.8-flash可以读取我们的扫描件,DeepSeek 模型则会回答 400。如果你的模型无法读取扫描件,请在本地运行 OCR 并发送文本,或通过 image_url 将页面作为 PNG/JPEG 图片发送给支持图片的模型。

限制、token 和耗时

什么限制
模型请求中的 PDF(base64、链接或 file_id)每个文件最多 20 MiB;文件必须以 %PDF- 开头
上传到 POST /v1/files最多 50 MiB(52,428,800 字节),但只有不超过 20 MiB 的 PDF 才能放入模型请求
file_id lifetime7 天(expires_at 字段),之后文件将被删除
页面没有单独的限制;使用文本提取时,每个请求最多 60,000 个字符;使用文件本身时,最多不超过模型的上下文窗口
通过链接下载最多 10 秒,最多 3 次重定向

Token 的计算方式。PDF 按所选模型的普通输入 token 计费,价格相同;文件本身或文本提取不另收费。以下是实际用量(包含一个简短问题):

  • 提取的文本:每页密集文本约 700 个 token(10 页 — 7,300 个 token;40 页截断至 60,000 个字符 — 20,300 个 token)。包含简短表格的页面 — 100–200 个 token。
  • 在 GPT 模型上,文件本身每页约占 600–700 个 token(10 页 — 5,900;40 页 — 23,300);在 gemini-4-argon 上,每页约占 1,200 个 token;在 Claude 上,每页约占 1,600 个 token。在 gpt-6.1-sol 上,扫描页约占 5,800 个 token。
  • 只要请求开头不变,重复使用同一份文档就能命中缓存:第二个请求中,相同的 file_id 有 7,168 个 token(共 7,309 个)来自缓存。

耗时。文本提取只需不到一秒;一份 40 页文档的回答在 4–12 秒内返回。对于大型文档和较长的回答,请使用 stream: true,并将客户端超时设为至少 300 秒。

错误及解决方法

响应原因处理方法
400 invalid_pdfThe PDF must start with the %PDF- signature.这不是 PDF,或者 base64 已损坏。请确保编码的是文件本身,而不是文件路径,并确认类型为 application/pdf。
400 invalid_pdfThe PDF size must not exceed 20 MiB.拆分文档或压缩其中的图片。
413 invalid_request_error在 POST /v1/files 上:文件大于 52,428,800 字节文件超过 50 MiB:请拆分文件。
400 invalid_request_errorfile_id 不可用文件已删除、已过期(7 天)、由其他账户上传,或者该 id 来自其他服务。请使用同一个 key 重新上传文件。
400 invalid_pdfThe PDF URL must be a public HTTPS URL without credentials.链接使用 http://、包含登录名和密码、使用非标准端口,或域名不存在。请提供公开的 HTTPS 链接或发送 base64。
400 invalid_pdfCould not safely fetch the PDF from the URL.链接返回 404、登录页面、而不是 PDF 的 HTML,或者服务器在 10 秒内没有响应。请在浏览器的无痕窗口中打开链接;如果文件没有立即开始下载,请发送 base64。
400 unsupported_input模型无法读取 PDF,且文件没有文本(扫描件)。使用可以读取扫描件的模型(见上文),或在你这边运行 OCR。
400 invalid_request_error关闭文本提取或使用扫描件时的 Invalid request…。模型不接受 PDF 文件。请移除 plugins documents enabled:false,让模型获取文本;或者选择表格中标记为 "yes" 的模型。
200,但“我看不到文件”文本提取已关闭,且模型或通道无法读取文件。恢复默认的文本提取,或选择表格中标记为“yes”的模型。

最佳实践

  • 需要在多个请求中使用同一份文档?上传一次并传递 file_id:请求会更小,重复的前缀会被缓存,费用也更低。
  • 将 PDF 和固定指令放在消息开头,将变化的问题放在末尾:这样更容易命中缓存。
  • 将超过约 28 页密集内容的文档按章节拆分:使用文本提取时,超过 60,000 个字符的内容不会传递给模型。
  • 对于带有文本层的合同、报告和导出文件,提取文本就足够了——这是任何模型上最便宜的选项,包括 deepseek-v4.1-flash。
  • 需要查看图表、印章或扫描件?请关闭文本提取,并使用表格中标记为“yes”的模型,例如 gpt-6.1-sol。
  • PDF 中的非拉丁文字(俄语、中文等)无需任何设置即可读取。发送 PDF 前,请移除其密码。
  • 不再需要已上传的文件时,请使用 DELETE /v1/files/{file_id} 将其删除。
Files API 不保证所选模型路由接受文件。如果某个路由不支持文件,请修正请求结构或选择兼容的模型;不要将返回的 file_id 替换为第三方标识符。
GetVibe API Files API 和 PDF — 上传文件并将 PDF 发送给模型 | GetVibe API