← Blog

Claude API Error 429 Rate Limit Fix: Complete Guide

2026-11-02 · 5 min read · SubToAPI Team

Why You're Seeing Error 429

A 429 "Too Many Requests" error from the Claude API means you've exceeded one of Anthropic's rate limits — either requests per minute (RPM), tokens per minute (TPM), or in some cases a daily spend cap tied to your usage tier. The fix depends on which limit you're hitting, but in almost every case it comes down to three things: slow down your request rate, retry with backoff, or increase your allocated limits.

This guide walks through exactly how to diagnose which limit you're bumping into, how to handle 429s gracefully in code so your app doesn't crash or hang, and what longer-term options exist if your usage keeps growing past what your account tier allows.

Step 1: Read the Response Headers

Before writing any retry logic, check the response headers Anthropic sends back with a 429. They tell you exactly what limit you hit and when it resets:

curl -i https://api.anthropic.com/v1/messages \
  -H "x-api-key: $ANTHROPIC_API_KEY" \
  -H "anthropic-version: 2023-06-01" \
  -H "content-type: application/json" \
  -d '{"model":"claude-opus-4-20250514","max_tokens":1024,"messages":[{"role":"user","content":"hi"}]}'

Look for headers like:

If retry-after is present, that's the number of seconds you should wait before trying again. Don't guess — use that value.

Step 2: Implement Exponential Backoff with Jitter

The single most important fix for 429 errors is retry logic with exponential backoff. Hammering the API immediately after a 429 just triggers more 429s and can get you temporarily throttled harder.

async function callClaudeWithRetry(payload, maxRetries = 5) {
  let attempt = 0;

  while (attempt < maxRetries) {
    const res = await fetch("https://api.anthropic.com/v1/messages", {
      method: "POST",
      headers: {
        "x-api-key": process.env.ANTHROPIC_API_KEY,
        "anthropic-version": "2023-06-01",
        "content-type": "application/json"
      },
      body: JSON.stringify(payload)
    });

    if (res.status !== 429) return res.json();

    const retryAfter = res.headers.get("retry-after");
    const waitMs = retryAfter
      ? Number(retryAfter) * 1000
      : Math.min(2 ** attempt * 1000, 30000) + Math.random() * 500;

    await new Promise(r => setTimeout(r, waitMs));
    attempt++;
  }

  throw new Error("Rate limit retries exhausted");
}

The key details:

Step 3: Queue and Throttle Requests Client-Side

If you're sending lots of requests in parallel (batch jobs, bulk processing, high-traffic endpoints), backoff alone isn't enough — you need to control concurrency before hitting the API.

class RequestQueue {
  constructor(rps = 2) {
    this.interval = 1000 / rps;
    this.queue = [];
    this.running = false;
  }

  add(fn) {
    return new Promise((resolve, reject) => {
      this.queue.push({ fn, resolve, reject });
      this.run();
    });
  }

  async run() {
    if (this.running) return;
    this.running = true;
    while (this.queue.length) {
      const { fn, resolve, reject } = this.queue.shift();
      try {
        resolve(await fn());
      } catch (e) {
        reject(e);
      }
      await new Promise(r => setTimeout(r, this.interval));
    }
    this.running = false;
  }
}

This caps your outbound request rate to something safely under your limit, rather than firing everything at once and hoping backoff cleans it up afterward.

Step 4: Check Which Limit You're Actually Hitting

429s aren't all the same. Common causes:

Step 5: Reduce Token Usage to Buy Headroom

Since TPM limits count both input and output tokens, trimming unnecessary context helps you stay under the ceiling without needing a limit increase:

When to Consider an API Gateway Instead

If you're building a product on top of Claude — not just scripting one-off calls — manually juggling retry logic, queues, and per-key rate limit tracking across a team adds up fast. This is where a layer like SubToAPI becomes useful: it exposes your Claude access as a standard HTTPS API with its own sub_live_... keys, so you get usage metadata, streaming, and tool use without hand-rolling rate-limit bookkeeping for every service that calls Claude.

Instead of every microservice independently managing retries and RPM math, you route calls through one place and manage limits and visibility centrally. Check the pricing page for plan details, or jump into the quickstart to see how requests are structured — it mirrors the native Messages and streaming APIs, so migrating existing retry logic is mostly a base-URL change.

Quick Checklist

Questions

Does retrying immediately after a 429 ever work? Rarely. Immediate retries usually hit the same limit window and trigger another 429. Always wait at least the retry-after value, or use exponential backoff if that header isn't present.

Will Anthropic automatically raise my rate limits? Limits typically increase as your account's usage and billing history grow, but you can also request manual increases through Anthropic's console if you have a specific scaling need.

Can batching requests help avoid 429s? Yes. Combining multiple small prompts into a single request reduces RPM pressure, though it can increase token usage per call, so balance against your TPM limit too.

Turn your Claude access into an HTTPS API

SubToAPI gives you application API keys, streaming, tool use and usage insights on top of your existing Claude access — set up in minutes.

Start free  Read the quickstart →