Troubleshooting: TEN_DLC_NOT_REGISTERED on US SMS sends
Your SMS request returned HTTP 422 with codeTEN_DLC_NOT_REGISTERED, or
the send went through but carries a ten_dlc_advisory on the message
metadata. Both point to the same finding: the pre-send gate found no
approved TCR (The Campaign Registry) brand+campaign registration for the
sending number. The full code table is in the
messaging error codes reference; this page maps
the gate’s verdict to the corrective step.
Since February 2025 every US carrier (AT&T, T-Mobile, Verizon) silently
filters A2P SMS sent from an unregistered 10-digit long code (10DLC).
The gate is protective: it stops you from paying for a message the
carrier will drop.
Two ways the verdict surfaces
How the gate treats an unregistered sender depends on your tenant’s settings:-
HTTP 422
TEN_DLC_NOT_REGISTERED— your tenant has strict enforcement enabled (Settings → Compliance → 10DLC). The send is rejected at the platform edge; no message row is created and no charge is made. -
Advisory in the response — with strict enforcement off (the
default), the send is handed to delivery anyway, and the verdict comes
back as a structured
ten_dlc_advisoryon the message metadata:
Diagnose the scope
Answer three questions before you touch anything:-
Which sender? The 422 error details and the advisory carry the
masked sender in
from. If you omitfrom, the pipeline resolves to the platform-default US number, which is registered at the platform level and exempt from this gate — so the flag only appears when you send from one of your own numbers. - Is this sender in the 10DLC class? A US toll-free number routes through the TFV gate instead; a short code is registered upstream outside TCR. If the flagged sender you expect to be toll-free or a short code is being treated as a 10DLC, check the number format you sent — the gate classifies by the E.164 digits, not by what your inventory calls the number.
-
Is any of your org’s campaigns approved? Read the status endpoint:
The gate counts the org as registered only when at least one campaign id sits in a terminal-approved TCR state. A campaign at
PENDING,FAILED, suspended, or never reconciled does not count.
Symptom → cause → fix
Choose the resolution path
Three legitimate resolutions, in order of preference:- Register the sender. File a TCR brand + campaign for the number — the 10DLC registration guide walks the full flow (brand → campaign → approval, expected 1–5 business days). This is the durable fix and the only one that protects deliverability.
- Route through an exempt sender. Omit
fromto fall back to the platform-default US number, or move US traffic to a toll-free number (subject to TFV — see Toll-free TFV required) or a short code. Use this when you cannot finish registration yet and cannot afford carrier filtering. - Keep strict mode of your own choosing. The advisory is a nudge, the 422 is a refuse. If you opted into strict enforcement previously and now want sends to dispatch with the advisory while registration proceeds, turn the toggle off; if you previously ran advisory and your compliance policy requires a hard block, turn it on.
What not to do
- Do not keep retrying on the same verdict. The gate reads your org’s registration state; until an approved campaign exists the result is the same, and strict-mode retries just re-eat the 422.
- Do not treat
PENDINGas passed. Expect the advisory/422 to clear only when a campaign is in a terminal-approved state — the gate never accepts a pending one. - Do not stop at “the campaign is approved” if one carrier still
reads
REVIEW/FAILED. ThemnoStatusesmap is per-carrier; hold traffic to any carrier still not approved until that entry flips. The message undelivered or failed page covers the send-side symptoms when registered traffic still fails.
When to escalate
Escalate to support@devotel.io when you have an approved campaign instatus but the verdict still flags your sends,
or when the status endpoint shows no campaigns at all despite a
submission that returned a campaign id. Include:
- Your tenant ID (dashboard → Settings → Organization, or
organizationIdonGET /api/v1/me). - The masked sender from the error
details.from(or the advisory’sfrom). - The full
GET .../campaigns/<id>/statusresponse so support can see the reconciliation state.
See also
- 10DLC registration guide — the full brand → campaign → approval flow, use-case codes, and throughput tiers
- 10DLC campaign rejected — the resubmission-side page this one defers to
- Toll-free TFV required — the sibling US sender-registration gate for toll-free numbers
- Message undelivered or failed — the send-side page for traffic that is registered and still fails