主题
税务分页交付
数据量较大时,在 /api/channel/data/tax/all 传 pagination: true。 分页基于固定交付快照,先准备、再读取、最后确认;原有不传分页参数的调用继续返回非分页结构。
API 1.5.144 起新生成交付重组后为 tax-all-business.v3 完整业务对象,读取方式见完整业务对象。分页协议仍为 tax-all-pages.v1。旧压缩交付返回 DELIVERY_SCHEMA_CHANGED,移除 deliveryId 和 cursor 后重新请求;已保留的历史分片不修改。
1. 选择表并发起交付
json
{
"channelCode": "BANK",
"channelOrderNo": "BANK-20260915-0001",
"orderNo": "订单查询返回的任务或授权标识",
"additionalTables": [],
"pagination": true,
"pageSize": 500
}additionalTables: []使用默认主表范围;省略时使用创建授权保存的默认附表。- 用
/api/channel/data/tax/tableCatalog查询可选表;只选择当前支持的编码。 - 取数选择不能扩大本批次采集计划;需要未采附表时须在新一轮采集前选择,不能只改分页参数补采。
pageSize为 1–1000,默认 500,指协议记录数量,不等于税表或企业数量。/tax/results分页仅支持明确传taxDataTypes: ["ALL"],其余输出单独查询。
准备中返回 HTTP 200、code=60003、delivery.state 为 QUEUED/RUNNING/RETRY_WAIT。 保存 delivery.deliveryId,在同一接口携带该标识轮询;不要因此重建授权。
2. 读取固定快照
json
{
"channelCode": "BANK",
"channelOrderNo": "BANK-20260915-0001",
"orderNo": "订单查询返回的任务或授权标识",
"pagination": true,
"deliveryId": "准备响应中的 deliveryId"
}就绪时 code=200,data 为 tax-all-pages.v1 页,包含:
| 字段 | 用法 |
|---|---|
deliveryId、snapshotId | 保存交付及快照身份 |
pageIndex | 页序号,以交付标识和页序号幂等保存 |
records | 有序路径操作记录,见下文 |
pageSha256 | 对 records 按 TAX-C14N1 求出的校验值 |
hasMore、nextCursor | true 时带游标续拉;false 时结束当前交付 |
续页仍 POST 原接口,保留渠道和订单三个字段、pagination: true,传上页 nextCursor 作为 cursor。 游标绑定原交付选择,不要中途改表范围。SM4 订单先解密整个响应,再保存与校验。
3. 重组数据并校验
第一类记录 recordType=DELIVERY_MANIFEST 的 payload 是清单,说明数组数量、内容页数、校验算法等。 其他记录的 path 是字符串键/整数下标组成的路径数组:
operation=CONTAINER:按containerType创建空对象或数组。- 其他值操作:按路径写入
payload;有largeRecord时先取回完整原值。 - 按页序和记录序处理,保留空对象、空数组、null、数值和字符串;不能把 records 当成税表业务行直接相加。
重组完成后得到 tax-all-business.v3 完整业务数据,与非分页 ALL 的 data 使用同一结构。直接读取 数据表[记录下标].字段名;嵌套对象和明细保留在当前记录内,无需展开公共属性、列值或跨记录引用。
下载 Python 校验和重组参考实现。它使用标准库,适用于读取后验证;大量数据应将路径操作幂等写入持久存储。
校验值不是随意格式化 JSON 的 SHA-256
TAX-C14N1 按类型编码 null、布尔、整数、双精度浮点、UTF-8 文本、数组和按 UTF-8 键排序的对象,再计算 SHA-256。 整数与浮点数、超出 JavaScript 安全范围的整数必须保留区分;不要用丢失数值信息的解析方式。 逐页校验 records 后,按顺序将内容页的 pageSha256 拼成 ASCII 文本计算 SHA-256,与清单的 contentPagesSha256 对照; 清单本身按 TAX-C14N1 计算,核对交付状态的 manifestSha256。
4. 大型记录读取
largeRecord 给出 recordId、size、sha256、chunkSize、chunkCount。 从 /api/channel/data/tax/deliveries/{delivery_id}/records/{record_id} 获取,需渠道鉴权;签名开启时每次请求使用新 Nonce。
- 明文:使用
Range: bytes=起点-终点,单次最多 4 MiB;按字节顺序组装后校验完整文件 SHA-256,再解析原 JSON 值。 - SM4:用
chunkIndex从 0 开始逐块读取;禁止同时传 Range。按TaxLargeSm4Chunk契约认证解密,它与普通 JSON 的 Sm4Envelope 不同。 - 原值可能是字符串或其他 JSON 标量,不保证是对象。
5. 确认接收
全部分页读取、校验并可靠保存后,POST /api/channel/data/tax/deliveryAck:
json
{
"channelCode": "BANK",
"channelOrderNo": "BANK-20260915-0001",
"orderNo": "订单查询返回的任务或授权标识",
"deliveryId": "本次交付标识",
"snapshotId": "本次快照标识",
"manifestSha256": "本次清单哈希",
"clientBatchId": "CUSTOMER-IMPORT-20260915-001"
}成功返回 code=200,data.acknowledged=true。相同批次可幂等重试;批次号非空且最多 128 字符。
| 错误 | 处理 |
|---|---|
ACK_PAGES_INCOMPLETE | 补齐未读取的分页,完成本地保存后再确认 |
ACK_MANIFEST_MISMATCH | 核对交付、快照和清单哈希,不混用不同交付 |
ACK_BATCH_MISMATCH | 已由另一客户批次确认,检查本地幂等记录 |
DELIVERY_NOT_READY | 尚未就绪或状态变化,先重新读取状态 |
DELIVERY_EXPIRED | 原交付已过期,按当前资料权限重新发起读取 |
HTTP 401/403 是鉴权/权限失败;413 表示请求过大;429 表示容量限制。先处理 HTTP 错误,再判断 HTTP 200 内的业务码。