Retry-After
最该优先听的客户端提示: 等这么多秒, 或等到这个 HTTP 日期之后再重试。
最常和 429 Too Many Requests 一起出现, 有时也会跟 503 Service Unavailable 一起出现。只要它存在, 客户端就应优先按它等, 而不是自己瞎猜退避时间。
Retry-After: 60
搜索限流响应头、重试规则与厂商差异,粘贴 429 响应头即可解释下一次安全重试时间
粘贴限流响应头或 JSON 错误即可解释重试时间。下方速查仍可直接搜索。
最该优先听的客户端提示: 等这么多秒, 或等到这个 HTTP 日期之后再重试。
最常和 429 Too Many Requests 一起出现, 有时也会跟 503 Service Unavailable 一起出现。只要它存在, 客户端就应优先按它等, 而不是自己瞎猜退避时间。
Retry-After: 60
当前窗口的标准额度上限, 通常是 100 这样的请求数, 或 100;w=60 这样的策略项。
它适合用来给队列和进度条定上限, 但不能单独决定重试时间。要和 RateLimit-Remaining、RateLimit-Reset 一起看。
RateLimit-Limit: 100;w=60
当前窗口里还剩多少请求数或成本单位。
剩 0 不一定代表这次请求失败; 也可能是这次请求刚好用掉最后一格。要结合 HTTP 状态码和 Retry-After 再决定重试。
RateLimit-Remaining: 0
标准重置延迟, 单位是秒, 表示当前额度窗口多久后刷新。
不要把它和旧式 X-RateLimit-Reset 混在一起, 后者在很多 API 里是 Unix 秒级时间戳。标准字段表达的是延迟秒数。
RateLimit-Reset: 60
紧凑的限流策略描述, 例如 100;w=60, 或用逗号分隔的多个窗口。
当 API 同时暴露短突发窗口和长日配额时很有用。客户端应按当前最紧的那个窗口来规划请求。
RateLimit-Policy: 100;w=60, 5000;w=3600
旧式厂商头, 很多时候是 Unix 秒级时间戳, 不是延迟秒数。
GitHub 风格的 API 经常在这里返回 epoch 值。1717171717 这种应按时间戳读, 但标准 RateLimit-Reset: 60 应按延迟读。
X-RateLimit-Reset: 1717171717
重试等待逐步变长, 再给每次等待加随机抖动, 避免大量客户端同时重打。
如果有 Retry-After, 先听它。没有时再用有上限的指数退避加 full jitter, 并限制最大重试次数。
delay = random(0, min(cap, base * 2 ** attempt))
客户端生成的键, 让支付、下单、写操作接口可以安全重试。
在会创建资源的 POST 上使用。没有它, 超时后的重试可能造成重复创建或重复扣费。
Idempotency-Key: 5f2c3d1f-8f4b-4a42-9f2b-1dd8d6b7e1aa
在客户端本地排队, 按已知安全速率释放请求, 而不是等 429 打回来才反应。
它最适合批处理和同步 worker。并发上限和时间窗口额度要分开控制, 因为两者失败方式不同。
maxConcurrent = 4; minIntervalMs = 250
先减少请求数, 再谈重试: 合并读请求、缓存 GET、复用正在飞行的重复调用。
最快的 429 修复往往是删掉没必要的调用。缓存不变的元数据, 并把页面加载时的重复请求合并掉。
const cached = memoize(fetchPlanLimits, { ttl: 60000 })令牌按固定速率补充; 每个请求消耗令牌。允许短时间突发, 上限是桶容量。
公共 API 常用的默认方案, 因为它允许短突发, 同时长期平均速率稳定。
capacity=100, refill=10 tokens/second
统计滚动时间范围内的请求数, 减少固定窗口边界处的突刺问题。
比固定窗口更准确, 但通常需要更多状态。常见实现是计数器加插值。
effective = current + previous * overlapRatio
昂贵操作扣更多额度, 便宜操作扣更少额度, 而不是每个请求都算 1。
GraphQL、搜索、AI、报表导出很常见。必须清楚暴露剩余成本单位, 否则客户端无法规划。
RateLimit-Remaining: 870 # cost units
限制同时飞行中的请求数, 和每分钟请求数不是一回事。
客户端可能小时额度没超, 但同时打开了太多慢请求, 仍会被拒。
429 with message: too many concurrent requests
X-RateLimit-Limit、X-RateLimit-Remaining、X-RateLimit-Reset, 其中 reset 是 Unix 秒。
经典旧式头组合。reset 是绝对时间, 展示倒计时时要先换算。
X-RateLimit-Remaining: 0 X-RateLimit-Reset: 1717171717
Stripe 可能返回 Stripe-Rate-Limited-Reason, 区分全局、端点、资源、并发等限流原因。
这个原因决定修法: 降低全局吞吐、隔离热点端点, 或减少同一个对象上的并发写操作。
Stripe-Rate-Limited-Reason: endpoint-rate
AI API 常同时限制每分钟请求数和每分钟 token 数; 重试要按更紧的那个限制来。
请求数看起来没超, 但 token 吞吐可能已经耗尽。日志里要同时记录两个维度。
x-ratelimit-remaining-tokens: 0
RateLimit-Remaining 只说明剩余额度, 不说明该睡多久。等待时间看 Retry-After 或 reset。
把剩余额度当秒数 sleep 是常见 bug: remaining=0 绝不代表睡 0 秒。
if (retryAfter) sleep(retryAfter)
把 epoch reset 时间戳换成倒计时时, 本机时钟会影响结果。
有 Retry-After 时优先用它。只有 epoch reset 时, 负延迟要夹到 0, 并记录原始时间戳。
delay = Math.max(0, resetEpochMs - Date.now())
限流 key 可能是用户、token、应用、IP、工作区或端点; 猜错会掩盖真正热点。
日志里要同时记录限流维度和路由。单个用户超限和整个应用超限, 修法完全不同。
limit_key = workspace_id + ":" + route_group
面向开发者的浏览器本地 API 限流速查,用于排查 429、额度耗尽和重试 策略问题。可以搜索 Retry-After、RateLimit-Limit、RateLimit-Remaining、 RateLimit-Reset、RateLimit-Policy、旧式 X-RateLimit 响应头、令牌桶、 滑动窗口、带抖动的指数退避、客户端排队、并发上限、幂等键、GitHub 风格 epoch reset、Stripe 限流原因、AI API 的每分钟 token 限制。把原始 HTTP 响应头或 JSON 错误体粘进去,解释器会提取建议等待时间、剩余额度、 重置延迟、策略文本、来源字段,并提示 malformed JSON、429 缺少重试时机、 remaining 大于 limit 等异常。所有解析都在当前标签页完成,大输入会在解析 前拦截,复制出的报告可直接放进工单、运行手册或团队沟通里。
把内容粘贴或拖入工具面板。
点击按钮,在浏览器内本地处理,文件不上传。
一键复制结果或下载到本地。
适合穿插在写代码、查问题、做 Review、上线前的小任务里。
这些入口会把当前任务接到更完整的工具链里。
把失败任务里的响应头粘进来,直接看 Retry-After 是秒数还是 HTTP 日期,再复制一段包含剩余额度、重置延迟、来源字段的简短记录。排障 时不用再靠猜来回答"什么时候能重试"。
写同步 worker 时搜索 "jitter" 或"幂等键",在一页里看清 Retry-After、有上限指数退避、本地排队、批量请求和幂等键如何配合。 这样客户端能礼貌重试,又不会重复创建记录。
当 API 同时返回 RateLimit-* 和 X-RateLimit-* 字段时,解释器会帮助 区分标准 reset 延迟和旧式 epoch 时间戳。这正是最常见的坑:把一分钟 等待变成离谱长睡眠,或者反过来制造立即重试风暴。
把 RateLimit-Remaining 当成 sleep 秒数。remaining 是剩余额度,不是时间;等待时间看 Retry-After 或 reset。
以为所有 reset 响应头都是延迟秒数。标准 RateLimit-Reset 是延迟,但很多 X-RateLimit-Reset 是 Unix 秒级时间戳。
超时后直接重试非幂等 POST,却没有 Idempotency-Key,可能导致重复扣费或重复创建。
粘贴的响应只在浏览器内解析。工具只把安全的搜索词和分类写进 URL 方便 分享,不会把粘贴的响应头或 JSON 错误写进 URL,也不会保存到本地存储。
做你这行的人, 还会一起用这些。