Skip to content

公开 API 大数据导出与断点续取 ​

当账号拥有较多记录、成绩或相片时,浏览器一次性加载会导致内存、超时和重复问题。本页给导出工具和高级客户端提供分块读取、断点、校验和取消策略。

导出前估算 ​

导出前确认:

  • 当前账号和权限;
  • 预计记录数或页数;
  • 每页大小;
  • 本地可用空间;
  • 目标文件是否含个人信息;
  • 网络和维护窗口;
  • 是否允许导出全部范围。

不要在公共设备或移动网络上无提示执行全量导出。

分块读取 ​

采用固定页大小但按实际返回推进:

js
async function exportRange(readPage, pageSize = 50) {
  let start = 0;
  const output = [];
  while (true) {
    const page = await readPage(start, start + pageSize);
    const rows = Array.isArray(page.items) ? page.items : [];
    output.push(...rows);
    if (rows.length === 0 || rows.length < pageSize) break;
    start += rows.length;
  }
  return output;
}

实际字段以对应接口为准。导出器应保存当前页起止范围、返回数量和最后一次成功时间。

检查点文件 ​

检查点可以包含:

json
{
  "account_alias": "account-a",
  "kind": "playlog",
  "next_start": 500,
  "page_size": 50,
  "completed_pages": 10,
  "updated_at": "<RFC3339_TIME>",
  "output_file": "<PROTECTED_PATH>"
}

检查点不应包含 Token、完整账号名、文件内容或地址。它只能在同一账号和同一导出任务中使用。

中断与恢复 ​

发生网络、浏览器关闭或用户取消时:

  1. 保存最后一个完整页;
  2. 写入检查点;
  3. 关闭未完成请求;
  4. 下次验证 Token;
  5. 从最后一个未确认范围继续;
  6. 对重叠范围去重。

不要把“请求已经发出”当成页面已经成功写入检查点。只有解析并验证结构后才推进游标。

去重 ​

优先使用服务返回的稳定记录标识。没有稳定 ID 时保留原始页并采用谨慎的复合键,例如时间、曲目和序号,但要明确这可能误合并。导出完成后报告:总页数、原始条数、去重后条数和疑似重复数。

顺序 ​

服务可能在导出期间新增数据。不要把返回顺序当成永久时间顺序。导出后按字段排序,并保留原始读取范围。跨页出现相同记录时,选择更新时间较新的对象或保留两个版本并标记冲突。

文件导出 ​

导出文件应:

  • 保存到受保护位置;
  • 使用不包含凭据的文件名;
  • 写入导出时间和账号脱敏别名;
  • 完成后计算哈希;
  • 分享前去掉个人信息;
  • 不自动上传到第三方。

图片导出应限制并发和总大小;下载失败时只重试当前文件,不要重新读取全部列表。

取消操作 ​

取消全量导出只停止客户端,不应删除已经保存的文件或服务器数据。UI 要区分“取消导出”和“删除导出文件”,后者需要用户明确操作。

限频和退避 ​

读取请求使用有限并发和退避。遇到 429 时尊重服务提示;遇到 401/403 先停止;遇到解析错误保留原响应摘要,不要快速重试相同错误。

导出完成校验 ​

  • [ ] 最后一页已确认;
  • [ ] 没有未处理的检查点;
  • [ ] 总数和去重数已记录;
  • [ ] 数据结构逐页通过校验;
  • [ ] 文件可重新解析;
  • [ ] 账号和时间范围已记录;
  • [ ] 文件位置受保护;
  • [ ] 日志没有凭据或个人数据原文;
  • [ ] 导出目的和保留时间已明确。

Released under the CC BY-NC-SA 4.0 License.