Error code lookup
The codes the Cloud API returns most often. Each links to the full explanation below. Codes in the 130xxx–133xxx range are WhatsApp-specific; the low numbers (0, 3, 4, 10, 190, 368) come from the Graph API layer underneath and apply to any Meta API.
| Code | Meta's label | What it actually means |
|---|---|---|
0 | AuthException | The access token could not be parsed at all. Usually a truncated, quoted or empty token — check for a missing environment variable. Fix |
3 | API Method | Your app is missing a capability or permission for this endpoint. Fix |
4 | API Too Many Calls | App-level Graph API call limit. Not the same as message throughput. Fix |
10 | Permission denied | The app lacks whatsapp_business_messaging, or the token has no access to this WABA. Fix |
190 | Access token expired | Token expired, was revoked, or a password change invalidated it. Fix |
368 | Temporarily blocked | Policy violation. The account is in a temporary block. Fix |
80007 | Rate limit issues | WhatsApp Business Account-level rate limit reached. Fix |
130429 | Rate limit hit | Cloud API message throughput exceeded. You are sending too fast. Fix |
130472 | User's number is part of an experiment | Meta excluded this recipient from marketing delivery for a test. Not your fault. Fix |
131000 | Something went wrong | Generic server-side failure. Retry with backoff. Fix |
131005 | Access denied | Permission missing for the action attempted. Fix |
131008 | Required parameter missing | A required field is absent from the request body. Fix |
131009 | Parameter value not valid | A field has the wrong type, format or value. Fix |
131016 | Service unavailable | Meta-side outage or maintenance. Retry. Fix |
131021 | Recipient cannot be sender | You are sending to your own registered number. Fix |
131026 | Message undeliverable | Bad number format, not a WhatsApp user, or your quality is too low. Fix |
131031 | Account locked | The WhatsApp Business Account is restricted or disabled. Fix |
131042 | Business eligibility | Payment method missing or failing on the WABA. Fix |
131047 | Re-engagement message | The 24-hour window closed. You must use a template. Fix |
131048 | Spam rate limit hit | Quality-driven throttle. Meta is limiting you for spam signals. Fix |
131049 | Meta chose not to deliver | Per-user marketing message limit. Delivery deliberately skipped. Fix |
131051 | Unsupported message type | The message type is not supported on this endpoint. Fix |
131052 | Media download error | Meta could not fetch the media from your URL. Fix |
131053 | Media upload error | File too large, wrong format, or corrupt. Fix |
131056 | Pair rate limit hit | Too many messages between your number and this one recipient. Fix |
132000 | Parameter count mismatch | Variables supplied ≠ variables the template expects. Fix |
132001 | Template does not exist | Name or language code mismatch, or template not approved. Fix |
132005 | Hydrated text too long | Your variable values pushed the template past the length cap. Fix |
132007 | Format character policy violated | Newlines, tabs or 4+ consecutive spaces inside a variable. Fix |
132012 | Parameter format mismatch | Variable value does not match the format the template was approved with. Fix |
132015 | Template is paused | Low quality paused this template for 3 or 6 hours. Fix |
132016 | Template is disabled | Quality dropped again after pauses. Permanently disabled. Fix |
132068 | Flow is blocked | The WhatsApp Flow attached to this template is blocked. Fix |
132069 | Flow is throttled | Too many sends of this Flow. Back off. Fix |
133000 | Deregister failed | Number could not be deregistered. Fix |
133004 | Server temporarily unavailable | Registration service down. Retry later. Fix |
133005 | Two-step PIN mismatch | Wrong 6-digit two-step verification PIN. Fix |
133006 | Number needs re-verification | Verify the number again before registering it. Fix |
133008 | Too many PIN guesses | Locked out of PIN entry. Wait it out. Fix |
133009 | PIN entered too fast | Rate-limited on PIN attempts. Wait and retry. Fix |
133010 | Number not registered | You are sending from a number that was never registered on the API. Fix |
133016 | Registration rate limit | Too many register/deregister attempts. Wait before retrying. Fix |
135000 | Generic user error | Malformed request Meta could not classify. Inspect the payload. Fix |
Registration & onboarding problems
Most integrations die here, before a single message is sent. Nearly all of it comes down to one thing: the number is already in use somewhere Meta can see.
SMSI never receive the verification code
Meta's verification SMS is filtered by many carriers, and virtual, VoIP, toll-free and recently ported numbers frequently never receive it at all. Landlines obviously cannot.
Fix- Switch to voice call verification. This is the single highest-yield fix — the call succeeds on most networks where SMS silently fails. Have the phone in hand and answer it.
- Confirm the number is not still active on the WhatsApp or WhatsApp Business app on a phone. If it is, either delete that account first, or use Coexistence to keep it.
- If you have already tried several times, you are probably rate-limited with
133016. Stop and wait — more attempts extend the lockout. - For a landline, choose voice verification and have someone answer to hear the code read aloud.
In use"This number is already registered" / already in use on another account
A phone number can live in exactly one place at a time: the consumer WhatsApp app, the WhatsApp Business app, or the API — historically, never two at once. It can also be sitting on a WhatsApp Business Account you or a previous agency created and forgot about.
Fix- If it is on the WhatsApp Business app and you want to keep it there: use Coexistence. This is now the correct answer for most businesses and did not exist a few years ago.
- If you want it purely on the API: open the app, Settings → Account → Delete my account, then wait a few minutes before registering. Deleting removes the chat history on that phone — export it first if it matters.
- If it is stuck on an old WABA: you need admin access to that Business Manager to release or migrate the number. If an agency set it up and will not release it, Meta support is the only route, and it is slow.
133005133008133009Two-step verification PIN rejected or locked
133005 is a wrong 6-digit PIN. 133008 means too many wrong guesses and you are locked out. 133009 means you submitted attempts faster than allowed.
- The PIN is the two-step verification PIN set on the number, not the SMS code and not your Meta password. These get confused constantly.
- Forgotten it? Disable two-step verification from the WhatsApp Business Manager for that number, then set a new PIN.
- Locked out with
133008? Stop. Wait the lockout period out — repeated attempts restart the clock. - Store the PIN in your password manager the moment you set it. Recovering it later is far more painful than saving it.
NameDisplay name rejected or stuck in review
The display name must reflect a real business and relate to the brand people already know. Names get rejected for being generic ("Best Deals"), for being a person's name with no business connection, for including URLs, phone numbers, prices or promotional wording, or for claiming a brand you cannot prove you own.
Fix- Use the exact legal or trading name that appears on your website, invoices and storefront.
- Drop everything promotional. "Sarah's Boutique" passes; "Sarah's Boutique — 50% OFF!" does not.
- Make sure the name is discoverable: a matching website, social profile or business registration is what a reviewer looks for.
- Complete business verification in Business Manager. Unverified accounts get stricter name review.
- You can still send while the name is pending — it is not a blocker unless it is rejected.
133010Number not registered — messages fail immediately
Adding a number to Business Manager is not the same as registering it on the Cloud API. Registration is a separate /register call with the two-step PIN, and it is the step people skip.
POST https://graph.facebook.com/v21.0/{phone-number-id}/register
{
"messaging_product": "whatsapp",
"pin": "123456"
}
Confirm afterwards that the number's status reads Connected in the WhatsApp Manager. If it says Pending or Offline, registration did not complete.
133016133000133004Registration rate-limited or failing server-side
133016 means too many register or deregister attempts on this number. 133000 is a failed deregistration. 133004 is a Meta-side outage.
- For
133016: stop retrying. Each attempt during the cooldown can extend it. Wait several hours, then make one clean attempt. - For
133004: this is not yours to fix. Check Meta's platform status and retry with exponential backoff. - Never script an automatic retry loop around registration — that is how a short cooldown becomes a long one.
Access tokens & permissions
Everything worked yesterday and returns 401 today. This section covers roughly every such case.
190Access token expired, revoked, or invalid
Almost always one of: you shipped the temporary token from the Meta developer dashboard (it expires in about 24 hours); the password of the user who generated the token changed; app permissions were edited; or the token was manually revoked.
Fix- Never use the dashboard's temporary token in production. It exists for a first curl and nothing more.
- In Business Manager, create a System User, give it access to your WhatsApp Business Account and app, then generate a token with
whatsapp_business_messagingandwhatsapp_business_management. - Set that token's expiry to Never. System User tokens survive password changes; user tokens do not.
- Store it as a secret, not in the repository. A token committed to a public repo gets found and revoked automatically.
GET https://graph.facebook.com/v21.0/debug_token?input_token=TOKEN&access_token=TOKEN returns its expiry, scopes and validity.103131005Permission denied on an endpoint that should work
The token is valid but not for this. Either the app is missing the permission, or the System User behind the token has no role on the WhatsApp Business Account that owns the phone number ID.
Fix- Confirm the app has
whatsapp_business_messaging(sending) andwhatsapp_business_management(templates, number config). - In Business Manager, check the System User is explicitly assigned to that WABA with full control. Assignment to the app alone is not enough — this is the most-missed step.
- Confirm you are using the phone number ID, not the phone number itself, and that it belongs to the WABA your token can reach.
- If the app is still in Development mode, some capabilities are restricted until it goes Live.
0AuthException — cannot parse access token
The token never reached Meta in a usable form. This is a string-handling bug, not a permissions problem.
Fix- Check for an unset environment variable — the header is going out as
Bearer undefinedorBearer None. - Check for quotes or whitespace captured from a
.envfile, and for a trailing newline fromcat. - Check the token was not truncated by a column limit when stored in a database.
- Log the header length, not the token, and compare against the real token's length.
Messages that will not send
The API returned 200 and nothing arrived, or the send failed outright. Work down this list in order — the first two account for the large majority of cases.
131026Message undeliverable
A catch-all Meta returns for several distinct situations, which is why it is so frustrating. In order of frequency:
- Wrong number format. By far the most common.
- The recipient does not have WhatsApp on that number.
- The recipient has not accepted WhatsApp's latest terms of service.
- The recipient is running a very old WhatsApp version that cannot render your message type.
- Your own number's quality rating is low enough that Meta is suppressing delivery.
Format the number as country code + number, digits only — no plus sign, spaces, dashes, parentheses, or the leading zero used for domestic dialling.
| Country | Written locally | Send to the API as |
|---|---|---|
| Morocco | 0656 88 84 89 | 212656888489 |
| United States | (415) 555-0132 | 14155550132 |
| United Kingdom | 07700 900123 | 447700900123 |
| Brazil | (11) 96123-4567 | 5511961234567 |
| India | 098765 43210 | 919876543210 |
0656… becomes 212656…, never 2120656…. Sending the zero produces 131026 every time, and it is the single most common cause of this error.If the format is definitely right and it still fails, check your quality rating in WhatsApp Manager. If it is red, the problem is reputation, not this message.
200 OKThe API returns success but the customer receives nothing
A 200 from the send endpoint means Meta accepted the message for processing. It says nothing about delivery. The real outcome arrives later on your webhook as a status update.
Fix- Subscribe to the
messageswebhook field and read thestatusesarray. Every message moves throughaccepted→sent→delivered→read, or lands onfailedwith the real error attached. - A message stuck at
sentand neverdeliverednormally means the recipient's phone is off or offline. This is normal; it will deliver later. - If you have no webhook configured you are debugging blind — set one up before anything else.
wamid returned by every send. It is the only way to correlate a send with its later status webhook, and it is what Meta support will ask for.131042Business eligibility payment issue
The WhatsApp Business Account has no working payment method. Since Meta moved to per-message pricing for template messages, an account without valid billing cannot send business-initiated messages.
Fix- Add or update the payment method on the WABA in Business Manager — not on the ad account, which is a separate billing entity people confuse constantly.
- Check whether the card was declined or expired; a silent decline produces this error days later.
- Confirm the account's country and currency were set correctly at creation. Getting this wrong requires Meta support to fix.
131049130472Meta deliberately chose not to deliver
131049 means this recipient has already received their limit of marketing messages for the period. Meta caps how many marketing templates any one user receives across all businesses, to keep WhatsApp from becoming a marketing channel people abandon. 130472 means the recipient is in an experiment group excluded from marketing delivery.
- Neither is a bug and neither is fixable by retrying — the retry will fail identically.
- Both apply to marketing templates. Utility templates (order updates, appointment reminders, receipts) are not subject to this cap.
- If your utility messages are hitting this, your templates are miscategorised. Recategorising genuine transactional messages as Utility fixes both the delivery and the cost.
- Treat a rising rate of
131049as a signal that you are messaging too often.
131008131009135000Malformed request
A required field is missing or a value has the wrong shape. The error text names the parameter — read it before anything else.
FixRecurring offenders:
messaging_product: "whatsapp"omitted. It is required on every single send and is the most-forgotten field in the entire API.topassed as a number rather than a string, which silently drops leading digits in some languages.typenot matching the object supplied —type: "text"with animagebody.- Sending to the phone number instead of the phone number ID in the URL path.
Content-Type: application/jsonheader missing.
{
"messaging_product": "whatsapp",
"recipient_type": "individual",
"to": "212656888489",
"type": "text",
"text": { "preview_url": false, "body": "Hello" }
}
131021Recipient cannot be sender
You are sending to the same number you are sending from. The API cannot message itself.
FixTest with a second phone. This surfaces most often when a developer registers their personal number on the API and then tries to test against it — you need two numbers to test a WhatsApp integration end to end.
131000131016Something went wrong / service unavailable
A Meta-side failure. 131016 is an explicit outage or maintenance window; 131000 is the unclassified version of the same thing.
- Retry with exponential backoff — 1s, 2s, 4s, 8s, capped, with jitter to avoid a thundering herd when the service returns.
- Queue outbound messages rather than sending them inline from a web request, so an outage delays delivery instead of losing it.
- Make retries idempotent on your side, so a message is not sent twice when a request actually succeeded but the response was lost.
- If
131000persists for hours on a single message, the payload is likely at fault rather than the service. Send a minimal text message to the same recipient to isolate it.
The 24-hour customer service window
The rule behind more confusion than any other part of the platform, and the reason automation built on the API behaves differently from a person typing on a phone.
131047Re-engagement message — the 24-hour window has closed
WhatsApp lets a business reply freely only inside a 24-hour window that opens when the customer messages you. The clock runs from their most recent message and every new message from them restarts it. Once it lapses, free-form messages are refused with 131047, and only an approved template will go through.
- Track the last inbound message timestamp per contact and branch on it: inside 24 hours send free-form, outside send a template.
- Do not attempt to keep the window open with filler messages. It is measured on inbound messages only, and the attempt harms your quality rating.
- Get a small set of utility templates approved in advance for the common re-engagement cases. Approval takes time you will not have in the moment.
- When the customer replies to your template, the window reopens and free-form works again.
WindowsWhich messages are free and which are billed
Meta moved from conversation-based pricing to per-message pricing for template messages, and made service conversations free. The result is that replying to customers costs nothing, while initiating contact does.
How it works now| Category | Used for | Cost |
|---|---|---|
| Service | Any free-form reply inside the 24-hour window | Free |
| Utility | Order updates, receipts, appointment reminders, account alerts | Billed per message, cheaper than marketing |
| Authentication | One-time passcodes and login verification | Billed per message |
| Marketing | Promotions, offers, re-engagement, product launches | Billed per message, the most expensive |
- Rates vary substantially by recipient country — the same template costs very different amounts in Brazil and Germany.
- Categorise honestly. Meta reclassifies templates it judges to be marketing dressed as utility, and you are then billed at the higher rate anyway.
- Because service messages are free, answering inbound questions automatically has essentially no per-message cost. That is what makes automated first replies economical.
Message template problems
Templates are the only way to start a conversation, which makes a rejected, paused or disabled template an outage rather than an inconvenience.
132001Template does not exist
Meta could not find a template matching the name and language you sent. Both must match exactly.
Fix- Language code. The usual culprit.
enanden_USare different templates. Send the locale the template was actually approved under, exactly. - Name. Case-sensitive, and lowercase with underscores by convention.
Order_Updatedoes not matchorder_update. - Status. A template pending review or rejected does not exist for sending purposes. Confirm it reads Approved.
- Account. Templates belong to one WABA. Sending from a phone number ID on a different WABA produces this error even when the template is right in front of you in another tab.
132000132012132005132007Template parameter errors
The variable values you supplied do not fit the template as approved.
Fix132000— count mismatch. A template with{{1}}and{{2}}needs exactly two parameters, in order. Supplying an empty string still counts as supplying one; omitting it does not.132012— format mismatch. The value does not match the format approved for that placeholder, most often on currency and date parameters, which have a structured format rather than being free text.132005— too long after substitution. Your values pushed the rendered template past the body length cap. Truncate long values (product names, addresses) before substituting.132007— character policy. A parameter contains a newline, a tab, or four or more consecutive spaces. Collapse whitespace in every value before sending:" ".join(value.split())fixes this permanently.
132015132016Template paused or disabled
Recipients blocked your number or reported it as spam shortly after receiving this specific template. Meta tracks quality per template, so one bad template does not take down the others.
The escalation is fixed: first pause 3 hours → second pause 6 hours → disabled permanently.
Fix- Do not simply resend when the pause lifts. The same content to the same kind of audience triggers a longer pause and then permanent disablement. The pause is feedback, not a rate limit.
- Look at who received it. Templates get paused far more often for bad targeting than for bad wording — messaging people who never opted in will sink even a well-written template.
- Open with the business name and a clear reason for contacting. Recipients block what they cannot immediately place.
- Include an opt-out line in marketing templates. It reliably converts blocks into opt-outs, and blocks are what damages you.
- A disabled template (
132016) cannot be revived. Create a new one with genuinely different content — an identical copy under a new name will be rejected or disabled again.
RejectedTemplate rejected in review
Human or automated review found a policy problem. The rejection reason given is often generic, which makes this feel arbitrary. It usually is not.
The actual reasons, in order of frequency- Variable at the very start or end of the body. A template that begins or ends with a placeholder is routinely rejected because reviewers cannot tell what will be sent. Wrap it in fixed text.
- Adjacent variables.
{{1}} {{2}}with nothing between them reads as an injection point. - Category mismatch. A promotional message submitted as Utility is rejected or silently recategorised.
- Placeholder content in the sample values. Samples must look like real data, not
xxxortest. - Prohibited content — alcohol, tobacco, adult products, gambling, weapons, some financial and medical claims — varies by country.
- Spelling and grammar. Genuinely a rejection reason for marketing templates.
- URL shorteners. bit.ly-style links in templates are frequently rejected; use your own domain.
Fix the specific issue and resubmit. Resubmitting unchanged, hoping for a different reviewer, wastes days.
132068132069WhatsApp Flow blocked or throttled
132068: the Flow attached to this template is blocked, usually because its endpoint is failing health checks or it violates a policy. 132069: you are sending the Flow faster than allowed.
- For
132068, check the Flow's health in WhatsApp Manager. A Flow endpoint that returns errors or times out gets blocked automatically; fix the endpoint and republish. - Confirm the Flow is Published, not Draft, and that its version matches what the template references.
- For
132069, throttle sends and retry with backoff.
Media errors
Images, audio, video, documents and stickers each have their own limits, and Meta rejects anything outside them rather than transcoding.
131053Media upload error
The file is too large, in an unsupported format, or corrupt.
The actual limits| Type | Max size | Formats that reliably work |
|---|---|---|
| Image | 5 MB | JPEG, PNG |
| Video | 16 MB | MP4, 3GPP — H.264 video with AAC audio |
| Audio | 16 MB | AAC, AMR, MP3, MP4 audio, OGG (Opus only) |
| Document | 100 MB | PDF, Office formats, plain text |
| Sticker | 100 KB static / 500 KB animated | WebP |
- Compress before uploading. A 12 MP phone photo exceeds the 5 MB image limit routinely — resize to around 1600px on the long edge and re-encode as JPEG.
- Video must be H.264 + AAC. Other codecs in an
.mp4container are rejected even though the extension looks right. - OGG audio must use the Opus codec specifically. OGG Vorbis fails.
- Voice notes need to be sent as audio with the correct format, or they arrive as a file attachment instead of a playable note.
131052Media download error — Meta could not fetch your URL
You passed a link instead of uploading, and Meta's servers could not retrieve it.
Fix- The URL must be public. Anything behind a login, a signed URL that has expired, an IP allowlist or a firewall fails — even though it opens fine in your own browser, where you are already authenticated.
- HTTPS with a valid certificate. Self-signed certificates are rejected.
- The
Content-Typeheader must be correct. A JPEG served asapplication/octet-streamortext/htmlfails. - No redirect chains. Serve the file directly.
- Test with
curl -Ifrom a machine outside your network — not from the server that hosts the file.
/media endpoint and reuse the returned media ID. It is faster, removes this whole class of error, and Meta retains the ID for about 30 days.ExpiredMedia URL expired before I could download it
When a customer sends you media, the webhook carries a media ID. You exchange it for a download URL — and that URL is valid for only about five minutes.
Fix- Download immediately on receipt and store the file yourself. Do not persist the URL and fetch it later; it will be dead.
- The download requires your access token in an
Authorization: Bearerheader. Fetching the URL without it returns an error, which is a common first stumble. - Do the download in a background job, not inline in the webhook handler — the handler must return 200 fast.
Webhooks not firing
Without working webhooks you cannot receive customer messages or delivery statuses — the integration is effectively write-only. Debug in this order.
VerifyWebhook verification fails when saving the callback URL
Meta sends a one-time GET to your URL and expects a very specific response. Anything else and the save fails.
Meta calls your endpoint with three query parameters:
GET /webhook?hub.mode=subscribe
&hub.verify_token=YOUR_TOKEN
&hub.challenge=1234567890
You must return hub.challenge as plain text with status 200 — not JSON, not quoted, not wrapped in an object.
# Flask
@app.route("/webhook", methods=["GET"])
def verify():
if (request.args.get("hub.mode") == "subscribe"
and request.args.get("hub.verify_token") == VERIFY_TOKEN):
return request.args.get("hub.challenge"), 200
return "Forbidden", 403
- Returning
jsonify({"challenge": ...})fails. It must be the bare value. - The verify token is a string you invent and paste into both places. It is not your access token.
- The endpoint must be reachable publicly before you click save.
localhostcannot work — use a tunnel such as ngrok while developing. - Any auth middleware, login redirect or CSRF check in front of the route will break verification.
SilentVerification passed but no messages ever arrive
Verification only proves the URL is reachable. Delivery needs a subscription, and the subscription is a separate step in a different place.
Fix- Subscribe to the
messagesfield. In the app's WhatsApp configuration, tickmessagesexplicitly. The webhook is configured but subscribed to nothing by default — this is the number one cause of silent webhooks. - Subscribe the app to the WABA. Distinct from the field subscription:
POST /{waba-id}/subscribed_apps. Verify with the matchingGET. - Check the certificate. HTTPS on port 443 with a certificate from a recognised CA. Self-signed and expired certificates are rejected silently.
- Return 200 immediately. Slow responses get retried, then throttled, then dropped.
- Send a real message. Messages you send from your own registered number to itself will not produce inbound webhooks — use a second phone.
TimeoutWebhooks arrive at first, then stop or duplicate
Your endpoint is too slow. Meta retries anything that does not return 200 quickly, so a slow handler produces duplicates first and gets throttled after.
Fix- Acknowledge first, work second. Push the payload onto a queue and return 200 in the same breath. Never call another API, run a database migration or generate an AI reply before responding.
- Deduplicate on message ID. Retries mean the same
wamidcan arrive more than once; without a dedupe check your customer receives the same reply twice. - Handle batching. The payload can contain several entries and several changes. Iterate the arrays — do not read
entry[0].changes[0]and assume that is all of it. - Never return 500. Catch exceptions inside the handler, log them, and still return 200. Repeated 500s get your endpoint throttled, and then you lose messages that had nothing to do with the bug.
- Distinguish messages from statuses. Both arrive on the same field:
value.messagesis inbound customer messages,value.statusesis delivery updates for messages you sent.
@app.route("/webhook", methods=["POST"])
def receive():
payload = request.get_json(silent=True) or {}
try:
queue.enqueue(process_webhook, payload) # do the work elsewhere
except Exception:
log.exception("enqueue failed")
return "", 200 # always 200
Rate limits & throughput
Four different limits produce four different errors, and treating them as one thing leads to the wrong fix.
130429480007131056Which rate limit did I hit?
| Code | Limit | Triggered by | Response |
|---|---|---|---|
130429 | Message throughput | Sending faster than your number's per-second allowance | Slow down and retry — clears on its own |
4 | Graph API calls | Too many API calls of any kind from the app | Reduce polling; cache what does not change |
80007 | WABA-level limit | Account-wide volume across all numbers | Spread load; check for a runaway loop |
131056 | Pair limit | Too many messages to one specific recipient | Stop messaging that contact so frequently |
131048 | Spam rate limit | Low quality rating — this one is a warning | See quality; volume is not the fix |
- Queue outbound messages and drain the queue at a steady rate rather than sending in bursts. Bursting is what produces
130429. - Implement exponential backoff with jitter on every retry, and cap the number of attempts.
- Stop polling for things that arrive on webhooks. Polling message status is the most common cause of
4. 131056usually means a bug — a loop replying to your own webhook, or a follow-up that never checks whether it already fired.
130429 is about messages per second. The messaging limit (250 / 1K / 10K / 100K) is about unique customers you may start conversations with per day. Hitting the second one does not produce 130429.Quality rating & messaging limits
Quality rating governs everything else. It decides your sending limit, whether templates survive, and ultimately whether the number keeps working. It is driven almost entirely by how recipients react to you.
RedMy quality rating dropped to Medium or Low
Meta rates each phone number High (green), Medium (yellow) or Low (red), based on a rolling window of recipient behaviour — blocks, spam reports, and messages ignored after delivery. It is not affected by how much you send, only by how people respond.
Fix- Stop the outbound campaign immediately. Continuing while red is what turns a recoverable dip into a restriction.
- Find the specific template doing the damage. Per-template quality is visible in WhatsApp Manager; usually one template is responsible for most of the blocks.
- Audit the list. Every recipient should have opted in identifiably. Purchased lists, scraped numbers and "we have their number from an order two years ago" all produce blocks.
- Identify yourself in the first line and state why you are messaging. Unrecognised senders get blocked.
- Offer an opt-out and honour it within minutes. An opt-out is neutral; a block is not.
- Reduce frequency and let the rolling window pass. Recovery takes days of good behaviour, not hours.
LimitsMy number is Flagged or Restricted
Number status in WhatsApp Manager reflects the consequence of quality:
- Connected — normal.
- Flagged — quality fell to Low. You have roughly a week for it to recover before your messaging limit is cut.
- Restricted — you have hit your messaging limit, or quality did not recover. Business-initiated messages are refused until the limit period resets.
- Flagged is a warning with a deadline, and it is genuinely recoverable — stop outbound sending and let quality climb back.
- While Restricted you can still reply to customers who message you. Inbound conversations keep working, which is often enough to keep the business running.
- Do not register a second number and continue the same behaviour. Meta associates numbers under one business, and this is how a single restriction becomes an account-level one.
TiersHow do I raise my messaging limit?
Messaging limits cap how many unique customers you can start conversations with in a rolling 24 hours. Replies inside the 24-hour window do not count against it.
| Tier | Business-initiated conversations / 24h |
|---|---|
| Starting tier | 250 unique customers |
| Tier 2 | 1,000 |
| Tier 3 | 10,000 |
| Tier 4 | 100,000 |
| Top tier | Unlimited |
- Upgrades are automatic. Meta raises the tier when quality stays High and your volume approaches the current cap — you cannot apply for one.
- Complete business verification. It is a prerequisite, and unverified accounts stay at the starting tier.
- Quality gates everything: a Low rating stops upgrades and can drop you a tier.
- The practical route to a higher limit is a low block rate, not a support request.
Bans, restrictions & appeals
The outcome businesses actually fear. Worth being precise: several different things get called "banned", and they have different fixes.
BannedWhy was my WhatsApp number banned?
In rough order of how often each is responsible:
- Unofficial automation tools. Modified WhatsApp clients, browser-automation bots, and unofficial libraries that drive WhatsApp Web. These violate the terms directly, and detection has become reliable. This is the leading cause of bans, and it is the one businesses are usually unaware they are exposed to — many "WhatsApp marketing" tools sold cheaply work exactly this way.
- Bulk messaging to people who never opted in. Purchased lists, scraped numbers, or contacts imported from an unrelated source.
- A high block or report rate, whatever the source of the numbers.
- Sudden volume from a cold number. A brand-new number sending hundreds of first-contact messages on day one reads as spam infrastructure.
- Prohibited goods or services under WhatsApp's Commerce Policy.
- Manual mass-replying at volume — copy-pasting the same message to many contacts from a phone produces the same signals as a bot, without any of the protections. Businesses that got banned "without using any tool" have very often been doing exactly this.
131031368Account locked or temporarily blocked
368 is a temporary block for a policy violation. 131031 means the WhatsApp Business Account has been restricted or disabled outright — more serious and often permanent without a successful appeal.
- Open Business Manager → Account Quality. It states which policy was violated. Read it before appealing — an appeal that does not address the stated reason is refused automatically.
- Stop all sending from every number on the account. Continuing during a review guarantees rejection.
- Fix the underlying cause and be able to describe the fix concretely: the tool you removed, the list you deleted, the opt-in flow you added.
- Submit one appeal with specifics — what happened, what you changed, and evidence of opt-in consent where relevant. Filing repeated appeals hurts you.
- Wait. Reviews commonly take days. There is no way to expedite.
RecoveryMy number was banned — can I get it back?
It depends which kind of ban it is, which is why identifying it first matters.
Realistic outcomes- Restricted for messaging limits: not a ban. It clears when the limit period resets. Nothing to appeal.
- Flagged for quality: recoverable in about a week by stopping outbound sending and letting the rating climb.
- Temporary block (
368): usually lifts on its own once the violating behaviour stops. - Consumer app ban (banned in the WhatsApp Business app, not the API): appeal from inside the app. Success is realistic on a first offence and unlikely on a repeat one.
- WABA disabled (
131031): appeal through Account Quality. A genuine misclassification is often reversed; an account that really was bulk-messaging usually is not.
If a number is permanently gone, a new number on a clean account with proper opt-in is the only reliable path. Do not reuse the same lists and practices on it — repeating the behaviour on a linked account is how businesses lose the second number faster than the first.
PreventionHow do I make sure this never happens?
- Use the official API through a Meta partner. This removes the unauthorised-access ban category entirely.
- Prioritise inbound. Answering people who messaged you first carries essentially no quality risk and no per-message cost. Automating that is the safest high-volume activity on the platform.
- Collect opt-in explicitly and keep a record of when and how. It is what an appeal is judged on.
- Warm a new number up. Start with inbound and low outbound volume for the first weeks rather than launching a campaign on day one.
- Honour opt-outs immediately — an opt-out costs nothing, a block costs a great deal.
- Watch quality weekly rather than after something breaks. A drop from High to Medium is a week of warning.
- Categorise templates honestly. Marketing dressed as utility gets reclassified and hurts the account.
- Never buy contact lists. There is no version of this that ends well.
Coexistence problems
Coexistence lets one number run on the WhatsApp Business app and the official API at the same time. It removes the oldest and most painful constraint on the platform, and it has its own set of gotchas.
WhatWhat Coexistence changes
Historically a number could be on the WhatsApp Business app or on the API, never both. Moving to the API meant deleting the app account, losing the chat history on that phone, and giving up replying from the phone. For a small business whose number is printed on its packaging and running its ads, that trade was often unacceptable — which is precisely why so many ended up on unofficial tools that promised automation without the migration, and got banned for it.
What Coexistence does- The same number runs on both at once: you keep the WhatsApp Business app on the phone, and automation runs through the official API.
- Recent chat history and contacts sync across, so conversations do not restart from nothing.
- The number stays the number — no migration, no telling customers to save a new one, nothing to reprint.
- You can still reply manually from the phone whenever you want to, while automation handles the rest.
Whappl is one of the first Meta partners to support it.
SetupCoexistence setup fails or the number will not link
- The number must currently be active in the WhatsApp Business app — not the consumer WhatsApp app, and not already registered on the API.
- Update the WhatsApp Business app to a recent version. Older versions do not offer the linking flow at all.
- The phone must be online and able to complete the QR or code linking step.
- The number must not be attached to another WhatsApp Business Account. Release it there first.
- Coexistence is not available in every country or for every account type; a partner can confirm eligibility for a specific number before you start.
SyncHistory or contacts did not sync
The sync covers a recent window of history rather than everything the phone has ever held, and it runs after linking rather than instantly.
Fix- Give it time — the initial sync is not immediate on a busy account.
- Keep the phone online and the app open during the initial sync.
- Older conversations outside the sync window stay on the phone and remain readable there; they simply do not appear on the API side.
- Messages arriving after linking appear in both places, which is the point.
The pattern behind most of this
Read end to end, these failures fall into a small number of root causes.
- Number formatting. One malformed phone number produces the most common error on the platform. Normalise centrally, strip the trunk zero, store in international format.
- Tokens. Temporary tokens in production expire in a day. A System User token with the right permissions eliminates an entire error class permanently.
- The 24-hour window. Not a bug and not provider-specific. Free-form inside, templates outside — branch on it once, in one place.
- Webhook latency. Acknowledge with 200 immediately and do the work in a queue. This prevents duplicates, throttling and lost messages simultaneously.
- Recipient reaction. Quality rating, template pauses, restrictions and bans are all the same underlying signal: how many people block or report you. Everything downstream follows from it.
- Unofficial tools. The one category of failure with no fix and no appeal worth relying on. It is also the only one that is entirely avoidable by choosing a different starting point.
Or skip all of it
Everything on this page is what running your own WhatsApp API integration involves — registration, tokens, templates, webhooks, quality management, appeals. Whappl is an official Meta Tech Partner that handles the whole layer for you: a real person connects your number, and all you need on your side is a phone number that can receive one SMS. Coexistence is supported, so you keep the WhatsApp Business number you already use. It is free to test with no credit card.