限流发生时,最该保护的往往不是“继续跑完”,而是已经拿到的那部分结果。若脚本没有把每次成功响应立即落盘,限流后重试就可能覆盖或混入半成品数据,导致后续判断失真。正确做法是先冻结已有结果,再决定是否续跑,而不是直接加大重试次数。
很多脚本把结果先放在内存列表里,等全部请求结束后再统一写文件。限流触发时,进程可能被中断,或者重试逻辑把同一批任务重新跑一遍,最终文件里出现重复、错位甚至旧数据覆盖新数据的情况。此时你看到的不是“少了一部分”,而是“结果看起来完整,实际已经不可信”。
另一种情况是脚本用同一个输出文件持续追加,但没有记录每条结果对应的请求参数。限流恢复后继续追加,新旧批次混在一起,去重和核对都变得困难。问题不在于限流本身,而在于结果没有和请求状态绑定。
遇到限流时,通常有两种解释。第一种是服务端确实在限制请求频率,属于外部约束;第二种是脚本自身没有保存中间状态,导致限流后无法区分哪些已完成、哪些未完成。两者表现相似,但处理方式不同。
如果是外部限流,等待一段时间后按更低频率重试,通常能继续获得响应。如果是脚本状态丢失,即使等待再久,重跑也会重复消耗配额,而且已有结果仍可能被覆盖。区分它们的关键证据是:限流前后是否有一份带请求标识的持久化记录。若没有,就无法判断是服务端拒绝,还是脚本自己把进度弄丢了。
这些证据不需要复杂工具,只要在脚本里增加一个落盘步骤就能获得。动作本身很小,但它决定了下一步是“等待后继续”还是“先修脚本再跑”。
假设一个脚本需要查询 200 个页面状态,跑到第 80 个时被限流。若脚本每成功一个就把参数和结果写入独立文件,那么限流后你至少能确认前 79 个结果可用。此时可以只对剩余 121 个任务降低频率重试,而不必重跑全部 200 个。
反过来,如果脚本只在最后统一写入,限流中断后可能一个结果都没保存。即使重跑成功,也无法确认两次运行之间页面是否发生变化。这个对比说明:保护已有结果的核心不是“更聪明的重试”,而是“更早的持久化”。
先暂停脚本,把当前输出文件复制一份并加上时间标记,避免后续写入覆盖。然后检查日志和中间文件,确认已完成的任务范围。若中间文件完整,就只对未完成任务重新排队,并把请求间隔调大到限流前的两到三倍作为起点。若中间文件缺失,先补上落盘逻辑,再决定是否重跑。
重跑后不要立刻把新结果和旧结果合并。先对比两批结果中重叠部分是否一致。若一致,说明旧结果可信,可以合并;若不一致,说明页面或接口在此期间发生了变化,需要以时间较晚的一批为准,并记录变化范围。这个动作的结果会直接影响下一步:是继续扩大查询范围,还是先回到脚本层面修正状态记录。