Skip to main content
Back to blog

Rate limiting and throttling in messaging APIs

Rate limiting and throttling are two halves of the same protection mechanism in CPaaS APIs. This explainer defines both terms, walks a worked 429 with backoff and jitter, and shows how idempotency keys keep retries safe.

Orbit Editorial Team

Rate limits and throttling decide whether your messaging traffic peaks gracefully or fails under load. The two terms show up in every CPaaS integration review, they are often used interchangeably, and they describe different parts of the same protection mechanism. Knowing the difference changes how you design senders, retries, and alerting. This explainer defines each term, maps the scopes a limit can apply to, walks a real 429 response end to end, and closes with the carrier-level ceilings that sit downstream of the API.

One-line definitions, and the scope each term owns

A rate limit is the configured budget — a published maximum for how much traffic one client may send into an API in a given window. Throttling is the enforcement behavior — what the server does when traffic meets or exceeds that budget: queue it, slow it, or reject it with a 429. One term names a number you plan around; the other names the mechanism that holds that number. Integration bugs come from treating them as synonyms, because the right client response to a planned budget is very different from the right response to an active rejection.

A rate limit is a configured budget

A rate limit always pairs a number with a scope, and the scope decides who is affected when the ceiling is crossed:

ScopeTypical unitWhat it protects
Per API keyRequests per second or minuteOne key cannot crowd out your other workloads
Per accountMessages per minute, concurrent callsYour account stays within a fair share of shared infrastructure
Per channelSender throughput, for example 10DLC messages per secondCarrier deliverability on the downstream route

Limits are published in provider documentation and enforced per key, per account, or per endpoint, so you can architect around them before you write integration code. For messaging APIs the limit also carries a deliverability function: carriers and downstream aggregators impose their own ceilings, and a provider that enforces limits at the edge protects your sender reputation as well as its own infrastructure. On Devotel Orbit the per-endpoint budgets and one global per-second request ceiling are published in the rate limits guide.

Throttling is the enforcement behavior

Throttling is what happens when traffic crosses the budget. The server queues the excess, slows the response, or rejects it, typically returning HTTP 429 with a Retry-After header. When throttling appears in your logs, the protection is working as designed — the distinction matters for monitoring, because a rate limit is a configured number while throttling is the observable behavior when that number is crossed.

The enforcement style differs by surface. Orbit's sender-velocity limits throttle rather than reject: a burst past the velocity hint is spread out around your organization's configured limit, so a burst becomes a paced delivery stream instead of a pile of failures. The global request ceiling, by contrast, rejects excess immediately. Which behavior a given surface uses is part of the published contract, so read it before you code a retry loop.

Worked example: reading a 429 and retrying correctly

Suppose a bulk send job fires 2,000 messages against a sender whose channel ceiling is 100 messages per second. The API rejects the excess with:

HTTP/1.1 429 Too Many Requests
Retry-After: 1
X-RateLimit-Limit: 100
X-RateLimit-Remaining: 0

The error body carries the same retry_after value in seconds, so header-readers and body-readers agree. A well-behaved client handles this with a sequence, not a tight loop:

  1. Read the server's hint first. If Retry-After or retry_after is present, sleep at least that long before the next attempt.
  2. Back off exponentially with jitter when no hint exists. Synchronized retries from many workers arrive as a coordinated burst and re-trip the limiter; random jitter breaks the synchronization.
  3. Cap the total attempts. A stuck limiter must not loop forever; after a fixed number of attempts, park the job and alert.

The bounded schedule looks like this:

AttemptWait before retryWhy
1retry_after value from the responseThe server named the clearing time — trust it
2~2 seconds plus random jitterExponential base with desynchronization
3~4 seconds plus random jitterContinue widening the window
StopAfter a configured attempt cap, log and alertA limiter that never clears is an incident, not a backlog

Idempotency: retries must be safe to repeat

Backoff only helps if a retried send cannot duplicate. Without an idempotency guard, aggressive retries in a messaging context can deliver the same message twice to the same customer, which is far worse than a delayed single message. The fix is a provider-supplied idempotency key: generate one Idempotency-Key per send job when you create it, and send that same key on every attempt. If the first attempt actually landed and only the response was lost, the provider recognizes the key and returns the original result instead of sending again. The idempotency and safe retries companion post walks that contract end to end.

The carrier nuance: do-not-block limits downstream of the API

The throttling you actually experience is the tightest limit in the chain, and for messaging that limit often belongs to the carrier, not the API:

  • US 10DLC routes. Carrier throughput tiers cap messages per second per brand, and a newly registered US/CA 10DLC number also carries a daily send ceiling that ramps up as it builds delivery history. Retrying in a tight loop against a daily warming cap just reorders your queue; the cap resets at midnight UTC, so the right response is to defer, not to pace harder.
  • WhatsApp. Pacing sits on the template or messaging-service layer rather than the sender number, with per-business quality-tier ceilings shaping how fast approved traffic may drain.
  • Your own application. A client-side rate limiter draining a bounded queue slightly below the published ceiling — for a 100-per-minute budget, drain near 90 — keeps your workers from ever reaching the provider or carrier gate.

Treating carrier ceilings as planning inputs, not outage conditions, is what separates stable senders from fragile ones.

Putting it into practice

When you evaluate a CPaaS provider, ask four questions. What are the published limits per endpoint? Does the provider return Retry-After on 429 responses? Are bulk endpoints and transactional endpoints on separate limits? Do limits scale as your account grows? At Devotel Orbit, the per-surface numbers are listed in the rate limits guide, the API returns standard 429 semantics so your existing backoff logic works without custom handling, and the definitions sibling post maps the error-code families that tell you whether to retry, skip a recipient, or fix a loop.

Frequently asked questions

What is the difference between rate limiting and throttling?

A rate limit is the published budget — a fixed maximum per key, account, endpoint, or channel. Throttling is the server's enforcement behavior when traffic crosses that budget: queueing, slowing, or a 429 rejection. Plan for the budget; respond to the enforcement.

What should my client do when it receives a 429?

Sleep for the Retry-After or retry_after value when one is present, otherwise back off exponentially with random jitter, and cap the total attempts so a stuck limiter cannot loop forever. Attach the same Idempotency-Key on every attempt so a retry can never double-send.

Why does jitter matter in a backoff schedule?

Without jitter, every worker that hit the limiter wakes up at the same computed moment and the retries arrive as a synchronized burst that re-trips the ceiling. A random component spreads the wake-ups so the retried traffic drains smoothly.

How do carrier limits change the picture?

The effective ceiling is the tightest limit in the chain. US 10DLC throughput tiers and warming caps, and WhatsApp's per-template or per-service pacing, sit downstream of the API and reset on their own clocks. Defer against a daily warming cap; pace against a per-second velocity hint; and keep a client-side queue draining just below the published budget so you never hit either gate.

Rate limiting and throttling in messaging APIs — Orbit by Devotel