UniGateway SystemOne API
SystemOne API 用于调用快速决策模型。它接收文本、结构化状态或通过 assets 引用的图像,并返回类型明确的判断结果,不用于生成对话回复、代码或推理过程说明。
SystemOne API 提供以下问题类型;图像输入与 box 为实验能力,适用模型和启用方式见下文:
| 类型 | 用途 | 主要返回值 |
|---|---|---|
noul | 判断一个是非问题 | 表示“是”的概率 |
choice | 从预先定义的选项中选择一项 | 选中项、各选项概率和置信度 |
score | 按有序等级评价输入 | 加权分数、各等级概率和置信度 |
box | 定位图像中的一个目标(实验能力) | 归一化边界框坐标和置信度 |
准备工作
请前往 UniGateway API Keys 创建或获取 API Key。
将 API Key 设置为环境变量,不要将真实密钥写入源代码、前端代码、日志或公开仓库。
export UNIGATEWAY_API_KEY="<YOUR_UNIGATEWAY_API_KEY>"
Windows PowerShell:
$env:UNIGATEWAY_API_KEY = "<YOUR_UNIGATEWAY_API_KEY>"
| 项目 | 值 |
|---|---|
| Base URL | https://api.unigateway.ai |
| 鉴权 | Authorization: Bearer $UNIGATEWAY_API_KEY |
| Content-Type | JSON 请求使用 application/json;文件上传使用 multipart/form-data,由客户端生成 boundary。 |
接口概览
| 方法 | 路径 | 用途 |
|---|---|---|
GET | /decision/v1/models | 查询当前账户可用的决策模型 |
POST | /decision/v1/systemone | 使用决策模型对状态执行结构化判断 |
可选模型
| 模型 | model | 类型 | 说明 |
|---|---|---|---|
| Jev 1.13 | jev-1.13.0 | 固定版本 | 支持文本;启用实验能力后可输入图像,不支持 box。 |
| Jev Latest | jev-latest | 稳定版别名 | 指向当前最新稳定版本(目前为 Jev 1.14,支持文本;启用实验能力后可输入图像并使用 box),后续可能随版本发布而更新。 |
| Jev Preview | jev-preview | 预览版别名 | 指向当前预览版本;没有单独预览版本时,可能与稳定版指向相同版本。 |
以上 model 值均属于 Jev 模型系列。后续可用模型可能增加,请调用模型列表接口获取当前账户可用于 model 字段的精确模型 ID:
curl "https://api.unigateway.ai/decision/v1/models" \
-H "Authorization: Bearer $UNIGATEWAY_API_KEY"
模型列表响应包含 models 数组。每个模型对象包含以下字段:
| 字段 | 类型 | 说明 |
|---|---|---|
name | string | 可传入 model 的模型 ID 或别名。 |
description | string | 模型用途说明。 |
release_date | string | 模型或别名的发布日期;未提供时为空字符串。 |
本文示例使用 jev-latest。模型 ID、能力、价格和可用性可能调整,应以 /decision/v1/models 对当前账户的实时返回结果为准。若需要固定模型行为,可使用账户可用的版本化模型 ID;响应中的 model 会显示实际执行请求的版本。
创建判断
POST /decision/v1/systemone
请求使用一个 state 和一个或多个命名问题。所有问题读取同一个 state,并分别返回到 answers 中对应的问题 ID 下。
请求参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
state | string / object / array | 是 | 所有问题共用的待判断状态,可包含文本、嵌套结构和图像引用。 |
model | string | 是 | /decision/v1/models 返回的模型 ID。 |
questions | object | 是 | 至少包含一个问题;键为调用方自定义的问题 ID,值为问题对象。 |
assets | object | 输入图像时必填 | 图像引用与资源对象的映射;每个资源使用 part 或 data_base64 提供图像,详见“图像输入”。 |
问题 ID 仅用于关联请求和响应,不参与模型判断。一次请求可以包含多个 noul、choice、score 或 box 问题;box 需要支持该类型的模型及图像输入。
通用问题字段
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
type | string | 是 | noul、choice、score 或 box。 |
instructions | string / object / array | 否 | 需要模型执行的判断或定位任务;建议显式提供清晰、单一且可验证的说明。可包含图像引用。 |
criteria | object / array | 视类型而定 | 描述选项、等级或是非边界,可包含图像引用;box 不接受该字段。 |
state 可以是简单字符串,也可以是包含工单、记录、规则、对话或图像引用的 JSON 对象或数组。图像必须通过顶层 assets 提供,不能把文件路径或图像 URL 当作已上传的图像。音频和视频不作为原始输入:应先转换为文本、结构化字段,或提取符合要求的静态图像。
图像输入
图像与 Box 当前为实验能力,尚不适合未经评估直接用于生产决策;请求格式、响应和限制可能随版本变化。
Jev 1.13 和 Jev 1.14 可接收图像,Box 需要 Jev 1.14。以下示例使用 jev-latest,该别名目前指向 Jev 1.14;别名指向可能随版本发布而变化,可通过响应中的 model 确认实际执行的版本。
资源字段与引用规则
每张图像在顶层 assets 中定义一次,以引用字符串为键。在 state、问题的 instructions 或 criteria 的字符串值中写入该引用,接口会将其替换为图像。引用可单独作为整个值,也可嵌入句子或嵌套结构。对象的键不会被替换。
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
assets | object | 输入图像时必填 | 引用字符串到图像资源对象的映射。 |
assets.<引用>.type | string | 否 | 如提供,固定为 image。 |
assets.<引用>.part | string | form-data 上传时必填 | 保存图像文件的 multipart 分段名称。 |
assets.<引用>.data_base64 | string | 未设置 part 时必填 | 标准 Base64 编码,保留 = 填充,不含换行、空白或 data: 前缀。 |
assets.<引用>.format | string | 使用 data_base64 时必填 | 小写 png、jpg 或 jpeg;使用 part 时可省略。 |
每个资源选择 part 或 data_base64 一种方式;同时提供时接口优先使用 part。每个资源都必须在 state、instructions 或 criteria 中被引用,否则返回 400。
方式一:multipart/form-data 上传(推荐)
curl --request POST "https://api.unigateway.ai/decision/v1/systemone" \
-H "Authorization: Bearer $UNIGATEWAY_API_KEY" \
-F 'request={"model":"jev-latest","state":{"door":"a3f1c2e8-door"},"assets":{"a3f1c2e8-door":{"type":"image","part":"door-photo"}},"questions":{"person_present":{"type":"noul","instructions":"Is there a person in `door`?"}}};type=application/json' \
-F 'door-photo=@door-camera.jpg;type=image/jpeg'
multipart 请求须遵守以下规则:第一个分段必须命名为 request,内容为 JSON 请求体;后续每张图像使用独立文件分段,assets.<引用>.part 必须与分段名完全一致;不要手动设置整个请求的 Content-Type。
方式二:application/json 携带 Base64
无法使用 multipart 时,将图像编码到 data_base64,同时提供 format。Base64 应为实际 PNG 或 JPEG 文件的标准编码,不要填入 Data URL 或文件路径。
图像限制与预处理
| 项目 | 限制 |
|---|---|
| 格式 | PNG 或 JPEG 静态图像;不接受动画 PNG。 |
| 单张文件 | 最多 16 MiB;Base64 方式按解码后文件大小计算。 |
| 宽和高 | 每边均须为 280 至 1568 像素,含边界值。 |
| 总像素 | 宽 × 高为 78,400 至 2,458,624,含边界值。 |
| HTTP 请求体 | 最多 32 MiB,包含 JSON、Base64 文本和 multipart 封装,不含 HTTP 请求头。 |
| 全部不同图像 | 经接口处理后的图像合计最多 32 MiB。 |
| 展开后的请求 | 文本、问题、结构及所有引用替换后的图像合计最多 32 MiB;每次重复引用均计入。 |
超出限制的图像会被拒绝,不会自动缩放。应用侧应缩放或补边,将 GIF、WebP、HEIC 等转换为 PNG 或 JPEG;接口不会按 EXIF 自动旋转图像。视频须先提取静态帧。
Noul:是非判断
noul 用于回答是非问题,返回值是答案为“是”的概率。0 表示“否”,1 表示“是”;应用应根据业务风险设置阈值,而不是将所有非零值直接视为“是”。
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
type | string | 是 | 固定为 noul。 |
instructions | string / object / array | 否 | 需要判断的是非问题。 |
criteria | object | 否 | 可通过 true 和 false 分别说明“是”与“否”的判定边界。 |
以下示例判断客户是否明确提出退款要求:
curl --request POST "https://api.unigateway.ai/decision/v1/systemone" \
-H "Authorization: Bearer $UNIGATEWAY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "jev-latest",
"state": "I was charged twice for order A-104. Please refund the duplicate charge.",
"questions": {
"refund_requested": {
"type": "noul",
"instructions": "Does the customer explicitly request a refund?",
"criteria": {
"true": "The customer asks to return money or reverse a charge.",
"false": "The customer only asks a question or reports an issue without requesting a refund."
}
}
}
}'
响应示例中的概率仅用于说明字段格式,实际值以接口返回为准:
{
"model": "jev-1.14.0",
"answers": {
"refund_requested": {
"type": "noul",
"noul": 0.99
}
},
"usage": {
"input_tokens": 334,
"output_tokens": 21
}
}
Choice:枚举选择
choice 用于从调用方提供的有限选项中选择一项。接口同时返回最高概率选项、所有选项的概率分布和置信度。
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
type | string | 是 | 固定为 choice。 |
instructions | string / object / array | 否 | 需要执行的分类或选择任务。 |
criteria | object | 是 | 选项与说明的映射,最多包含 255 个选项;无需补充说明的选项值可设为 null。 |
以下示例将客户工单分配到一个处理团队:
curl --request POST "https://api.unigateway.ai/decision/v1/systemone" \
-H "Authorization: Bearer $UNIGATEWAY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "jev-latest",
"state": "Our SSO callback returns HTTP 500 after we rotated the signing certificate.",
"questions": {
"department": {
"type": "choice",
"instructions": "Which team should handle this support ticket?",
"criteria": {
"billing": "Payments, invoices, refunds, and account charges.",
"technical": "API errors, outages, authentication, and integrations.",
"sales": "Pricing, plans, upgrades, and procurement."
}
}
}
}'
{
"model": "jev-1.14.0",
"answers": {
"department": {
"type": "choice",
"choice": "technical",
"probabilities": {
"billing": 0.0,
"technical": 1.0,
"sales": 0.0
},
"confidence": 1.0
}
},
"usage": {
"input_tokens": 367,
"output_tokens": 38
}
}
Score:分级评分
score 用于按有序等级评价状态。criteria 按从低到高的顺序定义 2 至 10 个等级,响应中的 score 是根据各等级概率计算的加权值,因此可能位于两个整数等级之间。
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
type | string | 是 | 固定为 score。 |
instructions | string / object / array | 否 | 需要评分的维度。 |
criteria | array | 是 | 由低到高排列的等级说明,至少 2 项,最多 10 项。 |
以下示例评价客户消息的紧迫程度:
curl --request POST "https://api.unigateway.ai/decision/v1/systemone" \
-H "Authorization: Bearer $UNIGATEWAY_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"model": "jev-latest",
"state": "Production checkout has been unavailable for 20 minutes and all customer payments are failing.",
"questions": {
"urgency": {
"type": "score",
"instructions": "How urgent is this incident?",
"criteria": [
"Low: no current user or business impact.",
"Medium: limited impact with a workaround available.",
"High: broad production impact or a critical workflow is unavailable."
]
}
}
}'
{
"model": "jev-1.14.0",
"answers": {
"urgency": {
"type": "score",
"score": 2.0,
"legend": {
"0": "Low: no current user or business impact.",
"1": "Medium: limited impact with a workaround available.",
"2": "High: broad production impact or a critical workflow is unavailable."
},
"probabilities": {
"0": 0.0,
"1": 0.0,
"2": 1.0
},
"confidence": 1.0
}
},
"usage": {
"input_tokens": 340,
"output_tokens": 18
}
}
Box:图像目标定位
box 用于在图像中定位一个目标,返回归一化边界框。该能力需要 Jev 1.14 和图像输入,当前仅建议用于原型和评估。
| 字段 | 类型 | 必填 | 说明 |
|---|---|---|---|
type | string | 是 | 固定为 box。 |
instructions | string / object / array | 否 | 描述目标及其所在图像。 |
criteria | 不适用 | 不接受 | Box 不使用选项或评分标准。 |
以下请求同时检查目标是否存在并定位目标:
curl --request POST "https://api.unigateway.ai/decision/v1/systemone" \
-H "Authorization: Bearer $UNIGATEWAY_API_KEY" \
-F 'request={"model":"jev-latest","state":{"photo":"6e1d0b7c-kitchen"},"assets":{"6e1d0b7c-kitchen":{"type":"image","part":"kitchen-photo"}},"questions":{"mug_visible":{"type":"noul","instructions":"Is there a coffee mug in `photo`?"},"mug":{"type":"box","instructions":"the coffee mug in `photo`"}}};type=application/json' \
-F 'kitchen-photo=@kitchen.jpg;type=image/jpeg'
Box 坐标为图像尺寸的归一化比例,原点在左上角;left、right 是宽度比例,top、bottom 是高度比例,均在 0 至 1 之间。Box 不返回“未找到”,应用应先用经过业务验证的 noul 结果判断目标是否存在。每个 Box 问题只返回一个框;多个目标应分别提问或先分区处理。confidence 为 0 至 1,模型未提供时可能为 null。
在一次请求中组合问题
当多个判断使用同一份 state 时,可以在一个请求中混合问题类型。含图像的请求也可加入 box,但须满足其模型和图像输入要求。每个问题独立判断,响应通过相同的问题 ID 返回结果:
{
"model": "jev-latest",
"state": {
"subject": "Duplicate charge blocking month-end close",
"message": "We were charged twice for invoice INV-204. Please refund the duplicate today because finance closes the books tonight."
},
"questions": {
"refund_requested": {
"type": "noul",
"instructions": "Does the customer explicitly request a refund?"
},
"department": {
"type": "choice",
"instructions": "Which team should handle this ticket?",
"criteria": {
"billing": "Charges, invoices, and refunds.",
"technical": "Product errors and integrations.",
"sales": "Plans, pricing, and procurement."
}
},
"urgency": {
"type": "score",
"instructions": "How urgent is the requested response?",
"criteria": [
"Low: no deadline or current impact.",
"Medium: time-sensitive but not blocking a critical workflow.",
"High: an explicit near-term deadline or critical workflow is blocked."
]
}
}
}
响应格式
| 字段 | 类型 | 说明 |
|---|---|---|
model | string | 实际执行请求的版本化模型 ID。 |
answers | object | 以请求中的问题 ID 为键的答案映射。 |
usage.input_tokens | integer | 请求使用的输入 token 数。 |
usage.output_tokens | integer | 响应使用的输出 token 数。 |
不同问题类型的答案字段如下:
| 类型 | 字段 | 说明 |
|---|---|---|
noul | noul | 取值为 0 至 1,表示答案为“是”的概率。 |
choice | choice | 概率最高的选项。 |
choice | probabilities | 各选项对应的概率;所有值之和为 1。 |
choice | confidence | 从概率分布计算出的置信度,取值为 0 至 1。 |
score | score | 基于等级概率计算的加权分数,可能为小数。 |
score | legend | 等级索引与请求中等级说明的映射。 |
score | probabilities | 各等级索引对应的概率;所有值之和为 1。 |
score | confidence | 从概率分布计算出的置信度,取值为 0 至 1。 |
box | box | 包含 top、bottom、left、right 的归一化边界框坐标。 |
box | confidence | 0 至 1;模型未提供时为 null。 |
概率和置信度表示模型的不确定性,不保证单次判断一定正确。上线前应使用具有代表性的业务数据验证效果,并根据误判成本设置自动执行、人工复核或拒绝处理的阈值。
Jev 官方 SDK
Jev 提供 Python 和 JavaScript SDK。通过 SDK 调用 UniGateway 时,必须同时配置 UniGateway API Key 和以下 API 根地址:
https://api.unigateway.ai/decision
SDK 会在该地址后追加 /v1/systemone 或 /v1/models。因此,base_url 或 baseURL 中不要包含这两个接口路径。
Python SDK
安装 typesafe-sdk:
pip install typesafe-sdk
以下代码依次发起三次独立请求,分别演示 Noul、Choice 和 Score:
import os
from typesafe_sdk import Choice, Noul, Score, TypeSafeClient
with TypeSafeClient(
api_key=os.environ["UNIGATEWAY_API_KEY"],
base_url="https://api.unigateway.ai/decision",
) as client:
noul_response = client.system_one(
model="jev-latest",
state="Please cancel my subscription before the next renewal.",
questions={
"cancel_requested": Noul(
instructions="Does the customer explicitly request cancellation?",
)
},
)
choice_response = client.system_one(
model="jev-latest",
state="Our SSO callback returns HTTP 500 after certificate rotation.",
questions={
"department": Choice(
instructions="Which team should handle this ticket?",
criteria={
"billing": "Charges, invoices, and refunds.",
"technical": "Product errors and integrations.",
"sales": "Plans, pricing, and procurement.",
},
)
},
)
score_response = client.system_one(
model="jev-latest",
state="Production checkout is unavailable and all payments are failing.",
questions={
"urgency": Score(
instructions="How urgent is this incident?",
criteria=[
"Low: no deadline or current impact.",
"Medium: time-sensitive but not blocking a critical workflow.",
"High: an explicit near-term deadline or critical workflow is blocked.",
],
)
},
)
print(noul_response.nouls["cancel_requested"].noul)
print(choice_response.choices["department"].choice)
print(score_response.scores["urgency"].score)
JavaScript SDK
JavaScript SDK 要求 Node.js 22 或更高版本。安装 @typesafe-ai/sdk:
npm install @typesafe-ai/sdk
import { choice, noul, score, TypeSafeClient } from "@typesafe-ai/sdk";
const apiKey = process.env.UNIGATEWAY_API_KEY;
if (!apiKey) {
throw new Error("UNIGATEWAY_API_KEY is not set");
}
const client = new TypeSafeClient({
apiKey,
baseURL: "https://api.unigateway.ai/decision",
defaultModel: "jev-latest",
});
const noulResponse = await client.systemOne({
state: "Please cancel my subscription before the next renewal.",
questions: {
cancelRequested: noul(
"Does the customer explicitly request cancellation?",
),
},
});
const choiceResponse = await client.systemOne({
state: "Our SSO callback returns HTTP 500 after certificate rotation.",
questions: {
department: choice("Which team should handle this ticket?", {
billing: "Charges, invoices, and refunds.",
technical: "Product errors and integrations.",
sales: "Plans, pricing, and procurement.",
}),
},
});
const scoreResponse = await client.systemOne({
state: "Production checkout is unavailable and all payments are failing.",
questions: {
urgency: score("How urgent is the requested response?", [
"Low: no deadline or current impact.",
"Medium: time-sensitive but not blocking a critical workflow.",
"High: an explicit near-term deadline or critical workflow is blocked.",
]),
},
});
console.log(noulResponse.answers.cancelRequested.noul);
console.log(choiceResponse.answers.department.choice);
console.log(scoreResponse.answers.urgency.score);
Python SDK:图像与 Box
typesafe-sdk 支持使用 Image 发送图像,并使用 Box 定位图像中的目标。SDK 会自动以 multipart/form-data 上传图像:
import os
from pathlib import Path
from typesafe_sdk import Box, Image, Noul, TypeSafeClient
with TypeSafeClient(
api_key=os.environ["UNIGATEWAY_API_KEY"],
base_url="https://api.unigateway.ai/decision",
) as client:
result = client.system_one(
model="jev-preview",
state={"photo": Image(Path("kitchen.jpg"))},
questions={
"mug_visible": Noul(instructions="Is there a coffee mug in `photo`?"),
"mug": Box(instructions="The coffee mug in `photo`"),
},
)
print(result.nouls["mug_visible"].noul)
print(result.boxes["mug"].box)
print(result.boxes["mug"].confidence)
Image 可以接收图像文件路径、文件字节或 Base64 数据。Box 只返回一个边界框,不返回“未找到”;应用应结合 mug_visible 的结果和经过业务验证的阈值决定是否使用坐标。图像仍须符合本文的格式、尺寸和大小限制。
JavaScript SDK:图像与 Box
JavaScript SDK 要求 Node.js 22 或更高版本。使用 image() 创建图像资源,使用 box() 创建定位问题;SDK 会自动以 multipart/form-data 上传图像:
import { openAsBlob } from "node:fs";
import { box, image, noul, TypeSafeClient } from "@typesafe-ai/sdk";
const client = new TypeSafeClient({
apiKey: process.env.UNIGATEWAY_API_KEY,
baseURL: "https://api.unigateway.ai/decision",
defaultModel: "jev-preview",
});
const { answers } = await client.systemOne({
state: { photo: image(await openAsBlob("kitchen.jpg")) },
questions: {
mugVisible: noul("Is there a coffee mug in the photo?"),
mug: box("The coffee mug in the photo"),
},
});
console.log(answers.mugVisible.noul);
console.log(answers.mug.box);
console.log(answers.mug.confidence);
image() 接受 PNG 或 JPEG 的文件字节或 Blob;Box 的 top、bottom、left 和 right 是相对于图像高度和宽度的比例。图像和 Box 仍属于实验能力,发布前应使用实际业务图像进行验证。
Jev SDK 属于可选客户端。无需安装 SDK 时,可以使用支持 HTTPS、JSON 或 multipart 的 HTTP 客户端直接调用 UniGateway。
使用限制与建议
- SystemOne API 返回结构化判断,不生成自由文本回复,也不提供推理过程说明。
state、instructions和criteria应只包含任务所需的信息。不要传入与判断无关的个人信息、密钥或其他敏感数据。- 图像通过
assets提交,支持 form-data 文件上传或 JSON Base64;须遵守本文的格式、尺寸和引用要求。音频和视频应先转换为文本或符合要求的静态帧。 - 图像与 Box 属于实验能力,格式、限制和准确率可能变化;上线前应单独验证,不能以 Box 返回了坐标作为目标存在的证据。
- 本文示例使用的 Jev 模型主要以英语训练。其他语言也可以作为输入,但准确率可能不同;非英语场景必须使用实际业务数据进行评估。其他模型的语言能力以实时说明和实际测试结果为准。
jev-latest等模型别名可能随新版本发布而指向不同版本。对结果稳定性有严格要求时,应使用/decision/v1/models返回的可用版本化模型 ID,并记录响应中的model。- 模型可用性、上下文长度、限流和计费规则以 UniGateway 控制台及接口实时返回为准。
- 对退款、封禁、权限变更等高影响操作,不应只依据单次模型结果直接执行;应结合确定性业务规则、置信度阈值和人工复核。
错误处理
| HTTP 状态码 | 常见原因 | 处理建议 |
|---|---|---|
400 Bad Request | JSON 或资源无效、图像格式或 multipart 结构错误。 | 检查图像编码、资源引用和 part 对应关系。 |
413 Payload Too Large | 图像文件、请求体或展开后的请求超过限制。 | 缩放或重新编码图像,减少重复引用或拆分请求。 |
401 Unauthorized | 未提供 API Key,或 API Key 无效。 | 检查 Authorization: Bearer $UNIGATEWAY_API_KEY,更换密钥后重试。 |
403 Forbidden | API Key 无权访问目标模型或接口。 | 检查 API Key 权限,并通过模型列表确认当前账户可用模型。 |
422 Unprocessable Entity | 缺少必填字段,或问题结构不符合类型要求。 | 根据错误响应定位字段,核对 state、model、questions 和 criteria。 |
429 Too Many Requests | 请求速率或 token 用量超过限制。 | 优先读取 Retry-After,采用指数退避并加入随机抖动后重试。 |
5xx | 服务暂时不可用或处理失败。 | 仅对可安全重放的请求进行有限次数重试;持续失败时记录请求 ID 并联系 UniGateway 支持。 |
应用应为请求设置超时,并记录 HTTP 状态码、错误响应、实际 model 和网关返回的请求 ID。日志中不得记录完整 API Key;包含业务敏感信息的 state 也应按数据安全要求脱敏。
常见问题
Q: 请求返回 401 Unauthorized,如何处理?
检查 Authorization 是否使用 Bearer $UNIGATEWAY_API_KEY,并确认当前进程已设置 UNIGATEWAY_API_KEY。在 Windows PowerShell 中重新设置环境变量后,重启当前终端或应用再发送请求;如果密钥已失效或被停用,请在 UniGateway 控制台创建或获取新的 API Key。
Q: 请求返回 403 Forbidden,如何处理?
通过 GET https://api.unigateway.ai/decision/v1/models 检查当前 API Key 可用的模型,并核对请求中的 model 是否与返回的模型 ID 或别名完全一致。若模型可用但仍返回 403,检查 API Key 的模型访问控制和 IP 访问策略,修改后重新发送请求。
Q: 请求返回 400 或 422,如何定位参数问题?
先读取错误响应中的 detail 和字段路径,再逐项检查 state、model、questions、criteria 和 assets。400 常见于 JSON、图像资源或 multipart 结构错误;422 常见于缺少必填字段或问题类型与字段结构不匹配。修正后使用同一请求重新验证,不要仅重复发送原请求。
Q: 请求返回 429 Too Many Requests,如何处理?
优先读取响应中的 Retry-After,在指定时间后重试;没有该字段时采用带随机抖动的指数退避,并降低并发请求或 token 用量。确认限流恢复后再逐步提高并发,不要立即连续重试。
Q: 请求返回 5xx、超时或连接失败,如何处理?
先检查 https://api.unigateway.ai 是否可访问、请求超时设置和响应中的请求 ID。仅对可安全重放的请求进行有限次数重试,并记录状态码、错误响应和实际 model;持续失败时请提供请求 ID 联系 UniGateway 支持。
Q: SDK 导入 Image 或 Box 失败怎么办?
确认已安装支持图像和 Box 的最新版 SDK,并在当前 Python 环境中升级:
python -m pip install --upgrade typesafe-sdk
然后重新运行示例。若仍无法导入,检查 python -m pip show typesafe-sdk 的安装路径是否与执行代码的 Python 环境一致;旧版 SDK 不包含 Image 或 Box 类型时,应升级后再重试。
Q: SDK 请求返回 400,但文本请求正常怎么办?
确认图像是 PNG 或 JPEG 静态图像,并检查每张图像的宽、高、文件大小和总像素是否符合本文限制。Python 使用 Image,JavaScript 使用 image();不要将文件路径、Data URL 或 Base64 字符串直接放入 state,除非使用 SDK 提供的对应图像对象或 Image.from_base64()。重新导出图像后重试,并保留状态码和请求 ID。
Q: SDK 调用 UniGateway 时请求地址不正确怎么办?
检查 Python 的 base_url 或 JavaScript 的 baseURL 是否为 https://api.unigateway.ai/decision。不要在 SDK Base URL 后追加 /v1/systemone 或 /v1/models;SDK 会自动追加接口路径。同时确认 UNIGATEWAY_API_KEY 已设置,且没有误用 TYPESAFE_API_KEY。
Q: Box 请求提示模型不支持或返回结构不符合预期怎么办?
确认请求使用当前账户可用且支持 Box 的模型;示例使用 jev-preview。通过 /decision/v1/models 查询当前账户可用模型后,将 SDK 的 model 或 defaultModel 改为实际返回的模型 ID,再重启程序并重新验证。Box 只返回一个框,且不提供“未找到”状态;应用应同时使用 noul 检查目标是否存在。
Q: Box 坐标应该如何转换为像素?
读取 answers.<问题 ID>.box 或 Python 的 result.boxes["<问题 ID>"].box,将 left、right 乘以图像宽度,将 top、bottom 乘以图像高度,再取整并限制在图像边界内。确认处理时使用的是提交给接口的同一张图像;如果提交前做过旋转、裁剪或补边,应先按相同变换换算回原图。
Q: form-data 请求提示分段错误怎么办?
确认 JSON 请求体是第一个名为 request 的分段,Content-Type 为 application/json;每张图像使用独立文件分段,且 assets.<引用>.part 与文件分段名完全一致。使用 curl 时保留 -F,不要同时使用 -d,也不要手动设置整个 multipart/form-data 的 Content-Type。检查资源是否都在 state、instructions 或 criteria 中被引用后再重试。