GET /v1/live/pull 支持增量交付和从头读取当前可读范围。首次接入请先按小范围读取指南保存和检查一页。
环境与认证
| 环境 | API 地址 |
|---|---|
| 正式环境 | https://api.humanbased.ai |
| 测试环境 | https://api.staging.humanbased.ai |
在请求头传入该环境签发的完整组织密钥:Authorization: Bearer <API_KEY>。Key 必须有效、未过期、有数据交付权限,且覆盖目标订阅。订阅应属于该 Key 的组织并处于有效状态。网页登录会话、掩码 Key 和 Campaign ID 都不能代替它;不要把 Key 放入 URL 查询参数。
认证通过也不会扩展数据使用条款。下载、分享、保留或训练用途应另外符合适用授权。
两种读取模式
| 从头读取 | 增量交付 | |
|---|---|---|
| 请求 | 带 from=beginning。 | 不带 from。 |
| 用途 | 读取或恢复订阅当前可读范围。 | 取得共享读取位置之后的记录。 |
| 分页 | 用最新 next_cursor 作为下一页的 cursor,保持筛选条件。 | has_more=true 时继续请求;服务端保存进度。 |
| 共享进度 | 不推进。 | 按订阅推进,其他 Key 和程序也受影响。 |
| 计量 | 不产生新的计量拉取费用;receipt 为空。 | 新交付记录可能按订阅价格计费。 |
| 筛选 | 可用任务或 Campaign ID 缩小范围。 | 不接受这两类筛选。 |
零价订阅可从头读取符合条件的已交付记录,包括增量尚未取过的记录。收费订阅只能重读此前已取得的范围;从头读取不能绕过计费。该接口不保证冻结的数据快照,新交付或更正可能改变之后可读的内容。
增量请求虽然使用 GET,仍会改变订阅共享的读取位置。每次完整保存响应后再继续。如果响应丢失,位置可能已经前进;用从头读取恢复已取得的范围,并以 submission_id 对照本地记录。
查询参数
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
subscription_id | 字符串 | 是 | 有效订阅 ID,不是 Campaign ID。 |
limit | 整数 | 否 | 每页 1–200 条,默认 50。 |
from | 字符串 | 否 | 从头读取时用 beginning;省略则为增量。 |
cursor | 字符串 | 否 | 从头读取后续页使用上页返回的 next_cursor。 |
task_ids | 字符串 | 否 | 逗号分隔的任务 ID,仅从头读取;缩小订阅范围。 |
campaign_ids | 字符串 | 否 | 逗号分隔的 Campaign ID,仅从头读取;缩小订阅范围。 |
同时给出两类筛选时,两者一起生效。每类最多接收 200 个 ID;当前实现会截断超出的条目,应自行拆分请求。空条目会被忽略,完全为空的筛选表示“不筛选”,不是“返回零条”。范围外的筛选通常返回空页,不会扩大授权。分页时保持原筛选,并原样传回游标。
示例:从头读取一页
先安全地设置 HB_API_KEY 和本组织正式环境的 HB_SUBSCRIPTION_ID:
curl --silent --show-error --get 'https://api.humanbased.ai/v1/live/pull' \
--header "Authorization: Bearer $HB_API_KEY" \
--data-urlencode "subscription_id=$HB_SUBSCRIPTION_ID" \
--data-urlencode 'from=beginning' \
--data-urlencode 'limit=5'下例仅展示结构。ID、内容和金额是示例值,不是可下载的样本;实际 data.items[].data 取决于交付的输出结构。
{
"data": {
"items": [{
"submission_id": "784210006031",
"task_id": "784210005001",
"campaign_id": "784210001001",
"template_id": "784210002001",
"data": {"case_id": "returns-014", "decision": "escalate"},
"quality_score": 0.85,
"quality_grade": "A",
"unit_price_usd": 0.02,
"source": "web",
"created_at": "2026-10-01T09:30:00+00:00"
}],
"next_cursor": null,
"has_more": false,
"count": 1,
"receipt": null
},
"success": true,
"errorCode": 0,
"errorMessage": "SUCCESS"
}记录的单价可大于零,而此次重读的回执为空。单价不是本次扣费的证明。
成功响应
只有 success: true 才能把 data 当作成功页。
| 字段 | 类型 | 含义 |
|---|---|---|
success | 布尔值 | 请求是否成功。 |
errorCode | 整数 | 成功时为 0。 |
errorMessage | 字符串 | 成功时为 SUCCESS;失败时为诊断信息。 |
data.items | 数组 | 本页记录;空数组也是有效结果。 |
data.count | 整数 | 本页记录数。 |
data.has_more | 布尔值 | 读取本页时是否还有下一页。 |
data.next_cursor | 字符串或空值 | 从头读取时的下一页游标。 |
data.receipt | 对象或空值 | 收费增量读取的计量回执;重读时为空。 |
回执存在时,包含 usage_event_id、amount_usd、quantity 和 balance_available_usd。把回执与响应一起保存,对账方法见用量对账。
记录字段
| 字段 | 类型 | 含义 |
|---|---|---|
submission_id | 字符串 | 来源提交 ID;无法取得时可能为空。 |
task_id | 字符串 | 来源任务 ID;可能为空。 |
campaign_id | 字符串 | 来源 Campaign ID;可能为空。 |
template_id | 字符串 | 模板 ID;空值表示未知。 |
data | JSON 值 | 按配置的输出映射交付的内容,不需再次解析为 JSON 字符串。 |
quality_score | 数字 | 从等级映射的分数;没有已识别等级时为 0。 |
quality_grade | 字符串 | S、A、B、C 或 D;无法识别时为空。 |
unit_price_usd | 数字 | 此订阅的单条价格,不是付款回执。 |
source | 字符串 | 来源标签;可能为空。 |
created_at | 字符串 | 原提交时间;可能为空。 |
等级映射为 S → 0.97、A → 0.85、B → 0.70、C → 0.50、D → 0.30。这些数值不是经过校准的概率,也不度量模型效果。分页按交付记录内部顺序;较晚页出现较早的 created_at 不足以证明重复。保留 ID 的字符串形式,解析 data 中任意精度数字时也应避免精度损失。
获取 data 的字段结构
每条记录 data 里有哪些字段,取决于它的 template_id。下面两个读取接口返回这份字段约定,不必再靠猜测解析记录:
GET /v1/live/task/templates?subscription_id=<SUBSCRIPTION_ID>
GET /v1/live/task/template?template_id=<TEMPLATE_ID>
Authorization: Bearer <API_KEY>复数形式列出该订阅所属活动Developer 组织的一组数据工作及其相关设置配置要交付的全部模板,可以在记录到达前先缓存。它返回 subscription_id、count 和 templates;没有配置模板时 templates 为空。单数形式按记录中遇到的 template_id 查询一个模板,不限于某个订阅。两种形式都需要有数据访问权限的 Key:只用于活动配置的 Key 会得到 403。复数形式中,订阅不在 Key 所选范围内时同样返回 403;你的组织没有该订阅时返回 404。
| 字段 | 类型 | 含义 |
|---|---|---|
template_id | string | 与拉取记录中的 template_id 对应 |
name | string | 模板名称 |
description | string | 模板收集的内容 |
kind | string | 模板类型;表单类工作为 form |
fields | array | data 中每个字段一项:name、type、required、description;取值来自固定选项时另有 enum |
缺少 template_id 或 subscription_id 时,请求校验直接返回 422,消息写明缺少的参数,没有 errorCodeName。带了 template_id 但值为空时返回 400 和 TEMPLATE_ID_REQUIRED;模板不存在时返回 404 和 TEMPLATE_NOT_FOUND。
用量对账
GET /v1/live/usage
Authorization: Bearer <API_KEY>这个接口列出组织已被计费的用量事件,最新的在前。每次返回了记录的收费增量读取产生一条事件,事件的 usage_event_id 就是那次读取回执里的值。读取这份列表既不计费,也不移动任何读取位置。
地址和 Key 与 GET /v1/live/pull 相同,Key 需要有数据读取权限。列表覆盖该环境中整个组织的用量,Key 自身范围之外的订阅也在其中。接口没有 subscription_id 参数。
| 参数 | 类型 | 必填 | 说明 |
|---|---|---|---|
limit | 整数 | 否 | 返回的事件数。默认 50,最多 200;超过时返回 422。 |
接口没有游标,只返回最新的若干条事件。
| 字段 | 类型 | 含义 |
|---|---|---|
data.items | 数组 | 用量事件,最新的在前。 |
data.count | 整数 | items 中的事件数。 |
usage_event_id | 字符串 | 事件标识,与被计费那次读取的 receipt.usage_event_id 相同。 |
subscription_id | 字符串 | 那次读取使用的订阅。 |
dataset_id | 字符串或空值 | 费用归属的数据集;价格并非来自数据集时为空。 |
vertical_id | 字符串或空值 | 订阅所属的 vertical;没有时为空。 |
quantity | 整数 | 那次读取交付的记录数。 |
unit_price_usd | 数字 | 读取时每条记录的价格。 |
amount_usd | 数字 | 计费金额:unit_price_usd 乘以 quantity,保留六位小数。 |
currency | 字符串 | USD。 |
occurred_at | 字符串 | 计费记录的时间。 |
下面的数值只是示意。随读取响应保存的这份回执:
{
"usage_event_id": "784210009001",
"amount_usd": 0.1,
"quantity": 5,
"balance_available_usd": 49.9
}对应用量列表里的这条事件:
{
"data": {
"items": [
{
"usage_event_id": "784210009001",
"subscription_id": "784210003001",
"dataset_id": null,
"vertical_id": "784210004001",
"quantity": 5,
"unit_price_usd": 0.02,
"amount_usd": 0.1,
"currency": "USD",
"occurred_at": "2026-10-01T09:31:00+00:00"
}
],
"count": 1
},
"success": true,
"errorCode": 0,
"errorMessage": "SUCCESS"
}对账时,用每份回执的 usage_event_id 在 data.items 中查找,再比较 quantity 和 amount_usd。
| 你找到 | 说明什么 | 你现在做什么 |
|---|---|---|
usage_event_id 与回执相同的事件 | 这笔费用记录了一次。 | 核对 quantity 和 amount_usd 与回执一致。 |
没有这条事件,且 count 等于你传的 limit | 事件可能比这次取回的更早。 | 用更大的 limit 再请求,最多 200。 |
| 最新 200 条里也没有 | 事件比这个接口能返回的更早。 | 以保存的回执为凭,并在组织的 Billing 页面核对该时段的费用。 |
| 有事件却没有对应的回执 | 某次读取已计费,但响应没有保存下来,例如在传输中丢失。 | 按两种读取模式从头读取,找回那批记录。 |
保存的响应里 receipt: null | 这次是从头读取,或者没有产生费用。 | 无需对账。 |
调用频率限制
每个接口对每把 API Key 单独计数,默认每分钟 100 次请求。每个响应都会说明当前额度:
| 响应头 | 含义 |
|---|---|
X-RateLimit-Limit | 当前时间窗口允许的请求数 |
X-RateLimit-Remaining | 当前时间窗口剩余的请求数 |
Retry-After | 收到 429 时,需要等待的秒数 |
超过限制时,网关返回 429,errorMessage 为 Too many requests,没有 errorCodeName。等待 Retry-After 给出的秒数后,降低频率继续。分页循环在 X-RateLimit-Remaining 降到 0 时应先暂停。
错误与恢复
同时检查 HTTP 状态和返回外层。errorCode 是数字;部分错误有 errorCodeName,部分详细错误将结构写入 errorMessage,客户端不能假定所有失败具有同一命名字段。
数据接口带详细信息的拒绝,会把详情写成 JSON 字符串放进 errorMessage,此时没有 errorCodeName。例如余额不足以支付一次计费读取:
{
"data": null,
"success": false,
"errorCode": 402,
"errorMessage": "{\"error\": \"insufficient_balance\", \"available_usd\": 0.0, \"required_usd\": 0.02}"
}errorMessage 以 { 开头时,先解析它,再按其中的 error 字段分支:invalid_cursor 和 filters_need_reread(400)、insufficient_balance 和 entitlement_required(402,后者附 dataset_id),或 pull_contended 和 billing_unavailable(503)。
| HTTP 状态 | 原因示例 | 下一步 |
|---|---|---|
400 | 不支持的 from、无效订阅或游标,或增量请求带筛选。 | 修正参数,使用接口返回的游标。 |
401 | Key 缺失、格式错误、撤销或过期。 | 核对完整 Bearer 凭证或请管理员替换。 |
402 | 收费增量读取资金不足。 | 由负责人员核对可用资金。 |
402 | 数据按申请定价(entitlement_required)。 | 目前没有自助购买方式,充值无效;带上响应中的 dataset_id 联系支持。 |
403 | 无数据交付权限或订阅不在 Key 范围。 | 核对组织、订阅和获准的 Key。 |
404 | 调用方找不到订阅。 | 核对环境、组织和 ID。 |
422 | 必填参数缺失或 limit 无效。 | 按上表修正请求。 |
429 | 用同一把 Key 调用该接口过于频繁。 | 等待 Retry-After 给出的秒数,见调用频率限制。 |
503 | 计价、余额、计费暂不可用或并发拉取冲突。 | 稍后重试,并按所选读取模式恢复。 |
500 或未知响应 | 服务错误或契约不一致。 | 保存脱敏诊断并联系支持。 |
服务端如返回 Retry-After,按其建议重试;重试次数应有限,避免密集轮询。
活动来源的提交必须进入符合条件的交付集合。仅显示审核接受还不够:交付路径还等待奖励授予和交付记录生成,再受订阅和质量筛选限制。此请求是同步响应,不会返回需要轮询的导出任务 ID。到达 has_more=false 仅表示完成当前可读范围的遍历,不赋予数据许可或保证永久可用。
支持时请向 hello@humanbased.ai 提供环境、请求时间、HTTP 状态和脱敏错误,排除 Key 与私有内容。