Skip to main content
A partner key is account-level, so every Verify call says which application it is for. Everything else about those endpoints is exactly as the Quickstart describes: same shapes, same statuses, same errors, plus the ones below. A client application is Verify only: it sends one-time codes, never WhatsApp messages.

The application field

Pass your external_id as application:
  • in the JSON body of POST /v1/verify/start, POST /v1/verify/check, POST /v1/verify/{id}/resend and POST /v1/verify/{id}/cancel;
  • as a query parameter, ?application=store_88, on GET /v1/verify/{id}, since a GET has no body.
The legacy name service is accepted identically everywhere. A key can only check, read, resend or cancel a verification started under the same application; another application’s id answers 404 not_found.
Then check with the same application:
The message carries the application’s reviewed brand, never anything from the request, and the code is charged to your balance at your price. An Idempotency-Key is scoped to your key and the application together, so the same key under two applications is two sends.

What blocks a send

Checked in this order, before the endpoint’s own logic. The first three are the partner-key branch of the shared ladder on the Errors page. Everything after that is the ordinary ladder on the Errors page: request shape, channel and destination, the per-destination hourly cap, the guard, your balance (402 insufficient_credits is your balance, not the merchant’s), then the send itself. A partner key always has full access, so 403 insufficient_scope on the shared ladder never answers it.

Reading what was sent

GET /v1/partner/verifications lists the codes your key sent across every client application, newest first. Each row is the public shape of GET /v1/verify/{id} plus application_id and your external_id, the key mode it was sent under (partner for your key), the lang and the price_halalas it was charged at.
  • Filters. application (your external_id; one that is not yours answers 404 not_found), reference (exact), from and to (ISO 8601, on created_at), status (pending, verified, failed, expired, canceled, read by the clock like GET /v1/verify/{id}) and mode. A value outside the vocabulary answers 400 invalid_request with the field named.
  • Paging. Keyset, no totals: limit is 1 to 100 (50 when omitted), next_cursor points after the last row you received whether or not more rows exist now, and has_more says whether another page is waiting. Pass it back as cursor; an empty page answers null. Rows created in the same second are ordered by id, so a cursor never skips or repeats one.
  • Archived applications keep their rows, with their external_id.
For sums rather than rows, GET /v1/partner/usage reports codes sent, verified codes and spend per application over a window.

Rate limit

The per-key limit of 120 requests per minute counts every call your key makes, codes and partner-API calls together. Spread bursts across a minute, or ask support for a higher limit.

The sandbox key

A partner sandbox key (tk_partner_test_..., created in the console under Clients → API and webhook, Sandbox key) is the same account and the same endpoints with the sandbox limits, so the code you write against it is the code you ship:
  • One destination. Sends reach only the phone the partner account’s owner verified at signup (the Sandbox key card shows it). Anything else answers 422 sandbox_unverified_destination.
  • A visible stamp. Every message carries the [TEST] / [تجريبي] stamp, and is charged like a live send.
  • Daily caps instead of the lifetime one: 20 sends per application and 200 per account a day (Riyadh time), answering 429 sandbox_quota_exceeded.
  • Applications in review can send, so a merchant can be tested before it is approved; rejected, suspended, disabled and archived ones cannot (403 account_not_active).
  • Reads work, writes do not. Every partner management write (provisioning, updates, suspend, archive, the webhook, retries) answers 403 live_key_required with the sandbox key, so a key that leaks into a test runner can change nothing. Provision test merchants with the live key, then send with the sandbox key.
The logs show these sends with mode: "partner_test", and GET /v1/partner/profile answers key.mode accordingly. One sandbox key is active at a time; rotating it revokes the old one at once.

Your own applications

Your account’s own applications are not sent for with the partner key: they are managed in the console like any other account’s, with Verify, Notifications and Chat, and send with their own keys (Application settings → API keys on the application). The WhatsApp number and its templates are under the application’s Notifications, and the inbox under Chat. See the Verify quickstart and Tawked Notifications.
Last modified on October 6, 2026