Platform API · Product API · Project setup
Channel readiness
The same readiness report narrowed to SMS or RCS: the channel's own setup steps, the countries a sender still ought to be registered for, and the countries it can actually send to right now.
The project report answers "is this project set up". This one answers the two questions you actually ask before sending on a channel: what is still missing here, and who can I reach right now.
It returns the same object, with scope: "channel", and fills in the two fields the project scope always leaves empty: warnings and reach.
What it does not answer is what a carrier or a regulator did to a registration you already submitted. That moved out on 2026-09-05 — see What moved to the attention endpoint.
Setup steps, the recommended-registrations warning and real send reach for one channel.
channel is sms or rcs. Any other value returns 404 — it is a route constraint, not a validation error, so don't expect a field-level message back.
curl "https://api.instasent.com/v1/project/$INSTASENT_PROJECT/readiness/channel/sms" \
-H "Authorization: Bearer $INSTASENT_TOKEN"{
"entity": {
"scope": "channel",
"projectType": "standard",
"channel": "sms",
"percent": 50,
"operational": true,
"steps": [
{ "key": "add-sender", "completed": true, "isBlocker": true, "disabled": false, "skipped": false, "skippable": true },
{ "key": "send-first-sms-campaign", "completed": false, "isBlocker": false, "disabled": false, "skipped": false, "skippable": true }
],
"warnings": [
{
"key": "recommended-registrations",
"severity": "error",
"count": 2,
"rows": [
{ "channel": "sms", "senderId": "5f3a9b2c4d1e0f00112233ab", "senderName": "MYBRAND", "country": "ES", "source": "regulation", "urgency": "urgent", "audienceCount": null, "audienceShare": null, "reason": null },
{ "channel": "sms", "senderId": "5f3a9b2c4d1e0f00112233ab", "senderName": "MYBRAND", "country": "FR", "source": "audience", "urgency": null, "audienceCount": 412, "audienceShare": 0.0824, "reason": null }
]
}
],
"reach": {
"reachableCountries": ["PT"],
"senders": { "MYBRAND": ["PT"] },
"senderCount": 1,
"defaultSender": "MYBRAND"
},
"computedAt": "2026-09-04T16:20:31Z"
}
}Steps
Same step object as the project report — stable key, no copy — with a set that depends on the channel and the project type:
projectType | channel | Steps, in order |
|---|---|---|
standard | sms | add-sender, send-first-sms-campaign |
standard | rcs | add-agent, register-country, send-first-rcs-campaign |
api_sms | sms | add-sender, send-sms-recent |
api_sms | rcs | add-agent, register-countries, send-rcs-recent |
api_sms is the wire value for what the customer knows as an A2P Messaging project — the one that sends through the A2P Messaging API. Never show the raw value in a screen someone reads: it is the one field on this endpoint whose value has a customer-facing name that doesn't look like it.
The first step of each list is the blocker; the rest are disabled until it is done. register-country / register-countries completes as soon as one RCS registration has been submitted — submitted, not approved, because approval is the carrier's and the regulator's timeline, not a step the customer can complete. The *-recent steps look at the last 30 days, so they re-open on a quiet integration.
SMS has no per-country step. Registration exists on SMS too, but it is not something the customer starts by hand, so it never becomes a checklist item. What it does produce is the warning below.
Warnings
Steps are what the customer can complete. A warning is what the customer should act on but cannot tick off — a country a sender ought to be registered for and is not. It appears only once the channel has an active sender: before that there is nothing to recommend registering.
One key:
key | severity | What it means |
|---|---|---|
recommended-registrations | error | Countries a sender should be registered for and is not. count is the total and may exceed rows, which is capped at 8. |
warnings stays an array discriminated by key even with a single member, so narrowing on the key is still the right thing to write: the next warning to arrive inherits that shape instead of adding nullable fields to this one.
Every warning carries key, severity, count and rows. rows is discriminated by the parent's key, never by which fields came back null.
Rows of recommended-registrations describe a registration that does not exist, so they carry no status. Instead they say why the country is recommended:
channelstringsms or rcs.
senderIdstringThe sender the recommendation is for.
senderNamestringIts alias — the SMS from, or the RCS agent name.
countrystringISO 3166-1 alpha-2.
sourcestringregulation — a regulator requires it; audience — you hold contacts there; org — it is the organization's own country.
urgencystring | nullurgent, upcoming or far. How close the regulator's deadline is; null unless source is regulation.
audienceCountinteger | nullReachable contacts in that country; null unless source is audience.
audienceSharenumber | nullThat country's audienceCount over the project's contacts with a mobile phone, between 0 and 1 and unrounded: round it yourself for display. It is the same base the audience threshold is measured against, since a country is recommended for its audience only when it holds at least 1% of those contacts and at least 25 of them. null unless source is audience.
reasonstring | nullsender-substituted when that sender can already reach the country, but only with a different sender shown to the recipient. The recommendation stays, and stays urgent: that delivery is a temporary last resort, and registering is what fixes it. null otherwise.
A country already covered by a non-archived registration on that sender never appears here, whatever its status.
What moved to the attention endpoint
Until 2026-09-05 this array carried two more keys, and if you integrated before that date they are what you are missing:
| Old warning key | Where it lives now |
|---|---|
pending-review | GET /project/{project}/attention, same key |
rejected-registration | GET /project/{project}/attention, same key |
The key names survived the move, so the switch you already wrote still matches; what changed is the endpoint it reads from and the shape around it — an attention item is one occurrence with entities and data, not a warning with rows.
The reason is the boundary the two engines are built on: readiness answers what is left to configure, attention answers what has broken. A registration a carrier is still reviewing, or one a regulator turned down, is something that happened to a registration the customer already submitted — an event, not a configuration gap. recommended-registrations stayed because it is the opposite: a registration that does not exist yet.
Reach
reach is the positive counterpart of the warnings: the countries this channel can send to right now.
reachableCountriesstring[]The union across the channel's active senders, ISO 3166-1 alpha-2, deduplicated and sorted.
sendersobjectPer-sender breakdown, keyed by alias. A sender that reaches no country is omitted, so this map can be shorter than the sender list — and it may arrive as [] rather than {} when it is empty. Normalise both to an empty map before you index it.
senderCountintegerHow many active senders the channel has, including those that reach nothing. This is not the size of senders, and the gap is the interesting part: an RCS agent with no accepted registration counts here and is absent there.
defaultSenderstring | nullThe project's default sender, when it is one of the active ones. It matters because a send that names no sender uses it — so the union above can promise more than a single send would actually reach. Always null on api_sms (A2P Messaging) projects, where nothing picks a default.
Reach is registration-aware, but not every pending register costs you a country. A country drops out when a registration is required and missing, when the register is waiting on the regulator axis (not yet classified, or filed and awaiting a decision), or when it is rejected or revoked. A register still being processed by the operators does not drop it: on SMS the country stays reachable while that runs. Reach is not a delivery gate: a country that drops out of reach can still receive messages — they go out, they are billed, and delivery is best-effort, so the operator may replace the sender or filter the message. What reach tells you is where the sender is cleared to arrive as itself. The two channels start from opposite defaults, which is why the same project can look very different on each:
- SMS allows by default over the operator catalogue — the same set as the sender's
acceptedCountries— and subtracts what regulation blocks. - RCS is registration-driven, so it can be stricter than the agent's
acceptedCountries, which reflects carrier support only.
operational on a channel
On this scope operational asks for more than the project one does: no incomplete blocker step and at least one reachable country.
That second clause is not redundant. Holding a sender is not the same as being able to deliver with it: an RCS agent with no accepted registration completes add-agent and still reaches nobody. operational claims capability, so it answers to reach.
What a country requires before you get there
reach tells you where this project can arrive today. It doesn't tell you what a
country asks for — the paperwork, who files it, how long it takes, whether it costs
anything — and that is exactly what you need when a country is missing from the list and
you want it in.
Those rules are documented once, for the dashboard and for the API alike:
Every destination, with what it asks for on each channel.
Coverage & deliveryWhat happens on SMS while a registration is still being filed.
Asking the API instead
Those pages say what a country asks of anyone. Two endpoints say what it still asks of one sender in this project:
One row per sender and country that has recorded paperwork, with how much of it the customer can act on right now.
The steps one country still asks of this sender, and which of them are startable today.
Start with the progress endpoint, always. Most destinations record no paperwork at all, so it is the only thing that tells you which sender-and-country pairs are worth a checklist call; a country that publishes nothing is left out of the rows rather than returned as zeroes, because "nothing to do here" and "nothing is written up for this country" are different answers.