System OnePOST
结构化判断与抽取:TypeSafe Jev 与 Cloudflare Clef 返回概率、分类、评分与区域定位,Cloudflare Clairic 从文字或图片中抽取字段。
本页内容
POST https://api.tokentosea.com/v1/systemone
System One 型号不生成自由文本。你提供应用状态(state)和一组问题或字段,型号为每一项返回程序可直接使用的结构化答案。只按厂商返回的 usage.input_tokens 计费,输出免费;图片、音频、视频计入输入 token。
不要把这些型号用于 Chat Completions、Messages 或 Responses。
前提:全能密钥或模型密钥,账户可用余额足以覆盖单次预留。Python 示例需要 pip install requests,Node.js 示例需要 Node.js 18+。
支持的型号#
| 型号 | 厂商 | 类型 | 能力 | 上下文 |
|---|---|---|---|---|
jev-1.14.0 | TypeSafe | 判断 | Noul、Choice、Score;图片输入与 Box(实验能力) | 约 64K |
jev-1.13.0 | TypeSafe | 判断 | Noul、Choice、Score;图片输入(实验能力) | 约 64K |
clef | Cloudflare | 判断 | Noul、Choice、Score;图片 | 65,536 |
clef-flash | Cloudflare | 判断 | Noul、Choice、Score;图片 | 24,576 |
clef-omni | Cloudflare | 判断 | Noul、Choice、Score;图片、音频、视频 | 65,536 |
clairic | Cloudflare | 抽取(研究预览) | 数值、日期、文本、列表、估计、预测 | 65,536 |
均在海外区域执行,只支持非流式 JSON 响应。每次调用按单次上限保守预留,收到可核验的用量后结算并释放余款;用量缺失或答案结构不符合协议时进入待核对,不按估算扣费。
请求格式#
| 项目 | 规则 |
|---|---|
Content-Type | application/json;Jev 另支持 multipart/form-data(见图片) |
Content-Encoding | 可选 gzip、zstd。原始请求与解压后都不能超过 32 MiB |
| 结构 | 嵌套深度不超过 64 层,节点总数不超过 100,000,不能包含非有限数值 |
TypeSafe-Danger-Zone-Images | Jev 图片判断的官方请求头。平台已在上游固定发送,客户端可以携带 |
TypeSafe-Danger-Zone-Long-Context | 不支持,发送即返回 422 system_one_long_context_not_enabled |
请求体只能包含下文列出的字段,出现其他字段(包括 stream)返回 422。
判断型号:Jev 与 Clef#
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
model | string | 必填 | 型号 ID |
state | string | object | 必填 | 应用状态,作为数据处理,不会被当作指令、文件或链接执行 |
questions | object | 必填 | 问题表,键为问题 ID,至少 1 个。Clef 最多 64 个,ID 需匹配 ^[A-Za-z0-9_.-]{1,100}$ |
assets | object | 可选 | 仅 Jev:图片资产表,见图片 |
images | array | 可选 | 仅 Clef:最多 4 张图片,见 Clef 媒体 |
audio / videos | array | 可选 | 仅 clef-omni,见 Clef 媒体 |
问题#
每个问题是 { "type": "…", "instructions": "…", "criteria": … },只能包含这三个字段;instructions 为字符串或对象。
type | criteria | 答案 |
|---|---|---|
noul | 可选,只能包含 true、false 两个键,例如 { "true": "已付款", "false": "未付款" } | { "type": "noul", "noul": 0.97 }:条件成立的概率 |
choice | 必填,选项表(Jev 1–255 项,Clef 2–255 项),值为说明或 null | { "type": "choice", "choice": "billing", "probabilities": { "billing": 0.91, … }, "confidence": 0.88 } |
score | 必填,2–10 个有序等级说明组成的数组 | { "type": "score", "score": 2.4, "probabilities": { "0": 0.02, … }, "confidence": 0.8 }:score 为 0 到等级数减 1 之间的加权分 |
box | 不能提供 | 仅 jev-1.14.0 且请求包含图片:{ "type": "box", "box": { "top": 0.1, "bottom": 0.6, "left": 0.2, "right": 0.7 }, "confidence": 0.75 },坐标归一化到 0–1 |
probabilities 的各项之和为 1。置信度适合用来决定是否转人工复核,不等于业务正确率。
Box 即使目标不存在也会返回框
同时问一个 Noul「目标是否存在」,只有存在概率与定位置信度都达到你用样本校准过的阈值时才使用坐标。同一次调用中的问题并行处理,不能让 Box 依赖另一个问题的答案。
Jev 图片#
在 assets 中登记图片,并在 state 或问题文本中引用资产 ID 字符串(未被引用的资产返回 422 system_one_asset_reference)。
| 规则 | 值 |
|---|---|
| 资产写法 | { "type": "image", "format": "png" 或 "jpg", "data_base64": "…" } |
| 数量 | 最多 128 个;资产 ID 每个最多 1024 字节,合计最多 64 KiB |
| 格式 | PNG(不能是动画)或 JPEG |
| 尺寸 | 宽、高各 280–1568 像素,面积不超过 2,458,624 像素 |
| 大小 | 每张最多 16 MiB;整个请求(含 base64)最多 32 MiB |
multipart 请求:第一个部分必须命名为 request,内容是上面的 JSON;资产写成 { "type": "image", "part": "<部分名>" }(可省略 format,平台按文件头识别),图片作为同名部分上传(image/png、image/jpeg 或 application/octet-stream)。最多 129 个部分,部分名不能重复,每个文件部分都必须被引用。
Clef 媒体#
媒体只能内嵌,不能是远程 URL:写成 data:<MIME>;base64,<数据> 字符串,或 { "content_type": "<MIME>", "base64": "<数据>" }。
| 字段 | 型号 | 格式 | 数量与大小 |
|---|---|---|---|
images | 全部 Clef | image/png、image/jpeg、image/webp | 最多 4 张,每张 4 MiB,合计 8 MiB |
audio | clef-omni | audio/wav、audio/x-wav、audio/mpeg、audio/mp3 | 最多 4 段,每段 8 MiB |
videos | clef-omni | video/mp4、video/webm | 最多 2 段,每段 16 MiB;音频与视频合计 16 MiB |
请求体 JSON 上限:clef、clef-flash 13 MiB,clef-omni 32 MiB;超出返回 413 cloudflare_request_size。
抽取型号:Clairic#
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
model | string | 必填 | clairic |
state | string | 必填(提供了 images 时可省略) | 原文,最多 65,536 字节 |
fields | object | 必填 | 字段表,1–16 个,ID 需匹配 ^[A-Za-z_][A-Za-z0-9_.-]{0,63}$,整个字段表 JSON 最多 32,768 字节 |
images | array | 可选 | 同 Clef 媒体 的图片规则 |
reference_date | string | 可选 | YYYY-MM-DD,用于解析相对日期 |
options | object | 可选 | include_quantiles、return_state_text,均为布尔值 |
请求体 JSON 上限 16 MiB。
字段定义:
| 键 | 说明 |
|---|---|
type | 必填:text、number、date、time、datetime、duration、list、estimate、forecast |
instructions | 可选,字段说明 |
unit | 可选,单位,例如 USD |
integer | 可选,布尔值 |
decimals | 可选,0–6 |
items | list 必填:text、number 或 date |
min / max | estimate、forecast 必填:数值或 YYYY-MM-DD 日期,且 min 小于 max |
step | 可选:正数,或 month、year |
scale | 可选:linear 或 log |
null_threshold | 可选:大于 0 且不超过 1 |
horizon / interval | forecast 必填:horizon 为 1–64,interval 为 step、minute、hour、day、week、month、quarter、year |
答案:{ "type": "…", "value": …, "p_null": 0.01, "confidence": 0.9 }。value 可能为 null(原文中没有);number、duration 为数值,text、日期时间类为字符串,list 为数组,forecast 另有 steps 数组。响应顶层的 truncated 表示原文是否被截断。
响应#
{
"model": "jev-1.14.0",
"answers": {
"payment_issue": { "type": "noul", "noul": 0.98 },
"queue": {
"type": "choice",
"choice": "billing",
"probabilities": { "billing": 0.93, "technical": 0.05, "other": 0.02 },
"confidence": 0.9
}
},
"usage": { "input_tokens": 212 }
}Cloudflare 型号的 usage 另含 output_tokens: 0。answers 的键与请求中的问题 / 字段 ID 一一对应。
示例#
文字判断(Jev)#
curl https://api.tokentosea.com/v1/systemone \
-H "Authorization: Bearer $TOKENTOSEA_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"model": "jev-1.14.0",
"state": {"ticket": "我充值成功了,但主站余额还没更新。"},
"questions": {
"payment_issue": {"type": "noul", "instructions": "Does `ticket` report a payment or balance problem?"},
"queue": {
"type": "choice",
"instructions": "Which support queue should handle `ticket`?",
"criteria": {"billing": "Payments, balance or charges.", "technical": "API usage and technical errors.", "other": "Any other issue."}
}
}
}'import os
import uuid
import requests
payload = {
"model": "jev-1.14.0",
"state": {"ticket": "我充值成功了,但主站余额还没更新。"},
"questions": {
"payment_issue": {"type": "noul", "instructions": "Does `ticket` report a payment or balance problem?"},
"queue": {
"type": "choice",
"instructions": "Which support queue should handle `ticket`?",
"criteria": {
"billing": "Payments, balance or charges.",
"technical": "API usage and technical errors.",
"other": "Any other issue.",
},
},
},
}
response = requests.post(
"https://api.tokentosea.com/v1/systemone",
headers={
"Authorization": "Bearer " + os.environ["TOKENTOSEA_API_KEY"],
"Idempotency-Key": str(uuid.uuid4()),
},
json=payload,
timeout=150,
)
response.raise_for_status()
answers = response.json()["answers"]
if answers["payment_issue"]["noul"] > 0.9:
print("route to:", answers["queue"]["choice"], answers["queue"]["confidence"])import { randomUUID } from 'node:crypto';
const payload = {
model: 'jev-1.14.0',
state: { ticket: '我充值成功了,但主站余额还没更新。' },
questions: {
payment_issue: { type: 'noul', instructions: 'Does `ticket` report a payment or balance problem?' },
queue: {
type: 'choice',
instructions: 'Which support queue should handle `ticket`?',
criteria: {
billing: 'Payments, balance or charges.',
technical: 'API usage and technical errors.',
other: 'Any other issue.',
},
},
},
};
const response = await fetch('https://api.tokentosea.com/v1/systemone', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.TOKENTOSEA_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': randomUUID(),
},
body: JSON.stringify(payload),
});
if (!response.ok) throw new Error(`HTTP ${response.status}: ${await response.text()}`);
const { answers, usage } = await response.json();
console.log(answers, usage);图片判断与区域定位(Jev 1.14)#
# multipart:第一个部分 request 为 JSON,图片部分按 part 名引用
cat > request.json <<'JSON'
{
"model": "jev-1.14.0",
"state": {"picture": "picture-1"},
"assets": {"picture-1": {"type": "image", "part": "picture"}},
"questions": {
"present": {"type": "noul", "instructions": "Does `picture` contain a chart?"},
"region": {"type": "box", "instructions": "The main chart in `picture`."}
}
}
JSON
curl https://api.tokentosea.com/v1/systemone \
-H "Authorization: Bearer $TOKENTOSEA_API_KEY" \
-H "Idempotency-Key: $(uuidgen)" \
-H "TypeSafe-Danger-Zone-Images: true" \
-F "request=@request.json;type=application/json" \
-F "picture=@selected-image.png;type=image/png"import base64
import os
import uuid
from pathlib import Path
import requests
image = Path("selected-image.png").read_bytes() # 宽高 280–1568 像素
payload = {
"model": "jev-1.14.0",
"state": {"picture": "picture-1"}, # 引用资产 ID
"assets": {"picture-1": {"type": "image", "format": "png", "data_base64": base64.b64encode(image).decode()}},
"questions": {
"present": {"type": "noul", "instructions": "Does `picture` contain a chart?"},
"region": {"type": "box", "instructions": "The main chart in `picture`."},
},
}
response = requests.post(
"https://api.tokentosea.com/v1/systemone",
headers={
"Authorization": "Bearer " + os.environ["TOKENTOSEA_API_KEY"],
"Idempotency-Key": str(uuid.uuid4()),
"TypeSafe-Danger-Zone-Images": "true",
},
json=payload,
timeout=150,
)
response.raise_for_status()
answers = response.json()["answers"]
# 阈值需用你自己的正例、反例和无目标图片校准
if answers["present"]["noul"] > 0.9 and answers["region"]["confidence"] > 0.7:
print("chart at", answers["region"]["box"])import { randomUUID } from 'node:crypto';
import { readFile } from 'node:fs/promises';
const image = await readFile('selected-image.png'); // 宽高 280–1568 像素
const payload = {
model: 'jev-1.14.0',
state: { picture: 'picture-1' }, // 引用资产 ID
assets: { 'picture-1': { type: 'image', format: 'png', data_base64: image.toString('base64') } },
questions: {
present: { type: 'noul', instructions: 'Does `picture` contain a chart?' },
region: { type: 'box', instructions: 'The main chart in `picture`.' },
},
};
const response = await fetch('https://api.tokentosea.com/v1/systemone', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.TOKENTOSEA_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': randomUUID(),
'TypeSafe-Danger-Zone-Images': 'true',
},
body: JSON.stringify(payload),
});
if (!response.ok) throw new Error(`HTTP ${response.status}: ${await response.text()}`);
const { answers } = await response.json();
// 阈值需用你自己的正例、反例和无目标图片校准
if (answers.present.noul > 0.9 && answers.region.confidence > 0.7) console.log('chart at', answers.region.box);判断(Clef Flash)#
{
"model": "clef-flash",
"state": "Checkout has been failing for every customer for the last hour.",
"questions": {
"urgent": { "type": "noul", "instructions": "Is this an urgent service outage?" },
"severity": {
"type": "score",
"instructions": "How severe is the impact on customers?",
"criteria": ["No impact", "Minor", "Major", "Critical"]
}
}
}字段抽取(Clairic)#
curl https://api.tokentosea.com/v1/systemone \
-H "Authorization: Bearer $TOKENTOSEA_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{
"model": "clairic",
"state": "Invoice INV-2291. The total is 1080 USD.",
"fields": {
"total": {"type": "number", "unit": "USD"},
"reference": {"type": "text", "instructions": "Invoice reference"}
}
}'import os
import uuid
import requests
response = requests.post(
"https://api.tokentosea.com/v1/systemone",
headers={
"Authorization": "Bearer " + os.environ["TOKENTOSEA_API_KEY"],
"Idempotency-Key": str(uuid.uuid4()),
},
json={
"model": "clairic",
"state": "Invoice INV-2291. The total is 1080 USD.",
"fields": {
"total": {"type": "number", "unit": "USD"},
"reference": {"type": "text", "instructions": "Invoice reference"},
},
},
timeout=150,
)
response.raise_for_status()
body = response.json()
print(body["answers"]["total"]["value"], body["answers"]["reference"]["value"], body["truncated"])import { randomUUID } from 'node:crypto';
const response = await fetch('https://api.tokentosea.com/v1/systemone', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.TOKENTOSEA_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': randomUUID(),
},
body: JSON.stringify({
model: 'clairic',
state: 'Invoice INV-2291. The total is 1080 USD.',
fields: {
total: { type: 'number', unit: 'USD' },
reference: { type: 'text', instructions: 'Invoice reference' },
},
}),
});
if (!response.ok) throw new Error(`HTTP ${response.status}: ${await response.text()}`);
const body = await response.json();
console.log(body.answers.total.value, body.answers.reference.value, body.truncated);错误#
| 状态码 | code | 原因 |
|---|---|---|
400 | system_one_invalid_json | 请求体不是有效的 UTF-8 JSON 对象(含 BOM 也会被拒绝) |
400 | system_one_multipart_boundary、system_one_multipart_headers、system_one_invalid_multipart | multipart 格式错误 |
413 | system_one_request_size、system_one_compressed_body_invalid_or_too_large | Jev 请求超过 32 MiB,或压缩数据无效 |
413 | cloudflare_request_size | Cloudflare 型号请求超过上限 |
415 | system_one_content_type、system_one_encoding_not_supported | Content-Type 或 Content-Encoding 不支持 |
422 | system_one_request_fields、system_one_question_invalid、system_one_question_type | 出现未定义的字段,或问题结构错误 |
422 | system_one_noul_criteria、system_one_choice_criteria、system_one_score_criteria | criteria 不符合该类型的规则 |
422 | system_one_box_requires_v14_image | Box 只能用于 jev-1.14.0 且请求包含图片 |
422 | system_one_asset_reference、system_one_asset_fields、system_one_base64 | 资产未被引用、字段错误或 base64 不规范 |
422 | system_one_image_format、system_one_image_dimensions、system_one_image_size、system_one_image_invalid、system_one_image_invalid_or_animated | 图片格式、尺寸或大小不符合要求 |
422 | system_one_multipart_parts、system_one_multipart_asset、system_one_multipart_unreferenced | multipart 部分命名或引用错误 |
422 | system_one_structure_limit、system_one_nonfinite_number | 结构过深、过大,或包含非有限数值 |
422 | system_one_long_context_not_enabled | 发送了长上下文请求头 |
422 | cloudflare_unsupported_field、cloudflare_questions_limit、cloudflare_fields_limit、cloudflare_state_required | Cloudflare 请求字段、问题或字段数量不符合规则 |
422 | cloudflare_embedded_media_required、cloudflare_media_format、cloudflare_media_count、cloudflare_media_size_or_base64、cloudflare_combined_media_size | 媒体不是内嵌 base64,或格式、数量、大小超限 |
422 | cloudflare_field_type、cloudflare_estimate_range、cloudflare_forecast_range、cloudflare_extraction_text_limit、cloudflare_extraction_options | Clairic 字段定义错误 |
422 | cloudflare_input_not_verified、system_one_input_not_verified | 该型号未开放所用的媒体类型 |
厂商答案不符合协议(例如概率之和不为 1)时,调用进入待核对,接口返回 202;不会扣除无法核验的费用。
下一步#
- System One 指南:问题设计与置信度路由
- 模型目录:Jev 与 Cloudflare 型号的价格