CPFHub.io

批量查询

发送 最多 10,000 个 CPF 的列表(CPF 即巴西个人税号),系统在后台处理,返回每个 CPF 的 姓名、性别 和 出生日期。每查到一个 CPF 消耗 1 个积分。

正在使用 Cursor、Lovable、v0 或其他 AI 工具? 复制批量查询的提示词,粘贴到您的 AI 助手中。

在 Cursor 中打开

不确定该用哪种查询?请对比各查询方式。如果不想写代码,可以在控制台上传 CSV/TXT 文件或粘贴 CPF,并将结果导出为 CSV。

两步流程:

  1. POST /cpf/bulk 提交列表,并立即返回 jobId。
  2. GET /cpf/bulk/{jobId} 返回进度和结果。重复调用,直到 status 为 "done" 或 "failed"。

端点

POSThttps://api.cpfhub.io/cpf/bulk

参数

位置名称必填说明
请求头x-api-key是您的 API 密钥。见身份认证。
请求头Content-Type是application/json
请求体cpfs是CPF 的 string[],带或不带格式均可。不能为空,最多 10,000 个。非字符串项计为无效。
请求体fileName否自定义标签。在状态查询中以 file_name 返回。
请求体format否来源格式的自定义标签(例如 "csv")。以 format 返回。

提交时的处理

步骤效果
规范化去除格式。不是 11 位数字或校验位错误的 CPF 计入 invalid,不计费。
去重重复项会被移除。每个 CPF 只查询和计费一次。重复项不计入 totalRecords 或 invalid。
每分钟限制每次提交按 一次 请求计入标准查询的限制(默认每分钟 30 次)。
余额未开通超额用量时,余额必须覆盖 所有 有效 CPF(totalRecords × 标准查询费用,默认 1 个积分)。不足时返回 403,不扣任何积分。

超过 10,000 个 CPF 时,请拆分为多批,每批发送一个 POST。

示例

读取 data 前请先检查状态码:出错时响应中没有 jobId。

curl -X POST "https://api.cpfhub.io/cpf/bulk" \
  -H "x-api-key: $CPFHUB_API_KEY" \
  -H "content-type: application/json" \
  -d '{
    "cpfs": ["12345678909", "11144477735", "52998224725"]
  }'

响应

HTTP 202 Accepted

JSON
{
  "success": true,
  "data": {
    "jobId": "4a1ef25e-052c-4464-9657-4148f53bb0fc",
    "status": "processing",
    "totalRecords": 3,
    "invalid": 0
  }
}
字段类型说明
data.jobIdstring批次 ID。请保存,用于查询状态。
data.statusstring始终为 "processing"
data.totalRecordsnumber将被查询的有效且不重复的 CPF 数量
data.invalidnumber被丢弃的项数(格式错误、校验位错误或非字符串)

提交接口的响应使用 camelCase,状态接口的响应使用 snake_case。

状态与结果

GEThttps://api.cpfhub.io/cpf/bulk/{jobId}

请使用提交时的同一个 API 密钥。该接口不消耗积分,不计入每分钟限制,余额为零时也可使用。

轮询:

  • 初始间隔 5 秒,大批次可逐步增加到 30 秒。每次调用都会返回完整的 cpfs 数组(10,000 个 CPF 约 2 MB)。
  • 在客户端设置最长等待时间(例如 30 分钟)。批次耗时取决于提交的 CPF 数量。
  • 遇到 5xx 或网络错误时,在下一轮重试即可。GET 可以安全地重复调用。
curl "https://api.cpfhub.io/cpf/bulk/4a1ef25e-052c-4464-9657-4148f53bb0fc" \
  -H "x-api-key: $CPFHUB_API_KEY"

HTTP 200 OK

JSON
{
  "success": true,
  "data": {
    "id": "4a1ef25e-052c-4464-9657-4148f53bb0fc",
    "status": "done",
    "file_name": null,
    "format": null,
    "total_records": 2,
    "processed": 2,
    "found": 1,
    "not_found": 1,
    "skipped": 0,
    "error": null,
    "created_at": "2026-10-02T14:15:16.000Z",
    "updated_at": "2026-10-02T14:15:18.000Z",
    "cpfs": [
      {
        "cpf": "12345678909",
        "found": true,
        "name": "Fulano de Tal",
        "nameUpper": "FULANO DE TAL",
        "gender": "M",
        "birthDate": "15/06/1990",
        "day": 15,
        "month": 6,
        "year": 1990
      },
      {
        "cpf": "52998224725",
        "found": false,
        "name": null,
        "nameUpper": null,
        "gender": null,
        "birthDate": null,
        "day": null,
        "month": null,
        "year": null
      }
    ]
  }
}
字段说明
data.id批次 ID(即提交时返回的 jobId)
data.status"processing"、"done" 或 "failed"
data.total_records批次中有效且不重复的 CPF 数量
data.processed已处理的 CPF 数量(包括 skipped)
data.found查到的数量。默认每个消耗 1 个积分(您套餐的费用见控制台)
data.not_found未查到的数量。不消耗积分。
data.skipped因批次处理中余额用完(未开通超额用量)而未查询的数量。不消耗积分。
data.errorstatus 为 "failed" 时的失败原因
data.file_name, data.formatPOST 中发送的标签
data.created_at, data.updated_atISO 8601 格式日期
data.cpfs[]每个已处理 CPF 的结果:cpf(11 位数字)、found、name、nameUpper、gender、birthDate、day、month、year(found 为 false 时为 null)

状态为 "processing" 时,计数器每处理 50 个 CPF 更新一次,可能落后于 cpfs。

错误

API 只返回葡萄牙语信息。错误信息按原样列出,首次出现时在括号内附中文释义。

状态码触发场景处理方式
400cpfs 缺失、为空、不是数组或超过 10,000 项修正请求体。
401API 密钥缺失、无效或已停用(error 为字符串)检查 x-api-key 请求头。
403未开通超额用量:余额为零(error 为字符串 "Limite de créditos excedido",积分额度已超出),或余额少于批次所需(error.message:"Créditos insuficientes para o lote: N necessários.",批次积分不足:需要 N 个)。账户停用/封禁时也会返回。仅限 POST。补充积分或缩小批次。
404jobId 不存在,或由其他 API 密钥创建检查 jobId 和密钥。
422列表中没有有效 CPF修正列表。
429超出每分钟限制(仅限 POST)等待 Retry-After 请求头给出的秒数。
500, 503临时故障。未创建批次。重试。如持续出现,请反馈给我们。

错误格式、重试策略以及如何在不消耗积分的情况下测试,见错误码。每分钟限制和积分规则见使用限制。

补充说明

批次状态

状态判断方式处理方式
处理中status: "processing"继续轮询。cpfs 中已有部分结果。
已完成"done" 且 skipped: 0使用 cpfs。
已完成但有跳过项"done" 且 skipped > 0批次处理中余额用完。补充积分后,只重新提交缺失的 CPF。
失败"failed"读取 error。cpfs 中已查到的项 已经计费。只重新提交缺失的 CPF。

批次失败时 error 的取值:

error含义
"Banco de dados indisponível"(数据库不可用)没有任何处理,也没有计费。
"Falha ao registrar validação"(记录查询失败)保存结果失败。处理已停止。
"Worker interrompido (job órfão)"(处理进程中断,孤立任务)处理被中断。约 10 分钟无更新后会标记为此状态。

开通超额用量时不会跳过任何 CPF:所有 CPF 都会被查询,超出部分按超额用量计费。

将结果与您的列表对应

cpfs 按处理顺序返回,不包含 skipped 项和未处理项。请将您的列表规范化为 11 位数字,并按 cpf 字段匹配。缺失的就是需要重新提交的(其中也包括无效项,无效项不计费)。

const normalize = (cpf: string) => cpf.replace(/\D/g, '')

const results = new Map(job.cpfs.map((item) => [item.cpf, item]))

for (const original of myCpfs) {
  const result = results.get(normalize(original))
  console.log(original, result ? (result.found ? result.name : 'not found') : 'no result')
}

// CPFs to resend in a new batch (if the batch failed or had skipped items)
const missing = [...new Set(myCpfs.map(normalize))].filter((cpf) => !results.has(cpf))

其他说明

  • 提交不是幂等的: 每个被受理的 POST 都会创建新批次,并对查到的 CPF 计费。如果连接中断且未拿到 jobId,重新提交前请先查看控制台或 GET /quota。如果收到的是错误响应,则没有创建批次。
  • 积分: 只有 found: true 计费。无效、重复、未查到和 skipped 项都不计费。
  • CSV 导出: 仅在控制台提供,列为 CPF、Nome(姓名)、Nascimento(出生日期)和 Encontrado(是否查到),不含性别。

更新于 2026 年 10 月 4 日