Quickstart
From nothing to a delivered message in five steps, using a shared sandbox test number. Every command here is real; two values in them are yours to fill in.
Two values are yours
The samples will not run as pasted. Replace the API key with your own test key, and replace every elided id (written as a prefix followed by an ellipsis) with the id the previous step returned. Nothing else needs changing.
Five steps
Create an account and verify your email address
Sign up, then click the link in the verification email. Sign-in is refused until the address is verified, and a workspace is created for you at sign-up.
Create a test API key
In the console, go to Developers → API keys and create a key in
testmode. The secret is shown once, at creation, and cannot be retrieved later. Put it in your environment rather than in a file:shellexport WA_API_KEY="wa_test_..."Every request authenticates with
Authorization: Bearerand that key. There is nox-api-keyheader — see Authentication for the whole picture.Allocate a sandbox test number
The sandbox is a pool of shared test numbers the platform owns. Allocating one creates a channel for you and returns a verification code. You cannot choose which number you get.
curlcurl -X POST https://whats.azzamkh.sa/api/v1/sandbox/sessions \ -H "Authorization: Bearer $WA_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "recipient": "+9665XXXXXXXX" }' # 201 Created # { # "id": "sbx_...", # "status": "waiting_for_verification", # "sandbox_number": "+999...", # "channel_id": "ch_...", # "recipient": "+9665XXXXXXXX", # "verification": { # "code": "482910", # "send_from": "+9665XXXXXXXX", # "send_to": "+999...", # "attempts_remaining": 5, # "expires_at": "2026-08-13T10:10:00.000Z" # } # }Prove you own the recipient number
Send the code as an ordinary WhatsApp message from the recipient's handset to the number in send_to, then call verify. Possession is proven by the sender address, so the code alone is not enough. The code is valid for 10 minutes and you have 5 attempts.
curlcurl -X POST https://whats.azzamkh.sa/api/v1/sandbox/sessions/sbx_.../verify \ -H "Authorization: Bearer $WA_API_KEY" \ -H "Content-Type: application/json" \ -d '{ "code": "482910" }' # 200 OK # { "id": "sbx_...", "status": "verified", "channel_id": "ch_...", ... }Send your first message
The channel is connected and the recipient is verified. Send.
curl -X POST https://whats.azzamkh.sa/api/v1/messages \ -H "Authorization: Bearer $WA_API_KEY" \ -H "Idempotency-Key: $(uuidgen)" \ -H "Content-Type: application/json" \ -d '{ "channel_id": "ch_...", "to": "+9665XXXXXXXX", "type": "text", "text": { "body": "Your code is 481902" } }' # 201 Created # { # "id": "msg_...", # "status": "queued", # "channel_id": "ch_...", # "to": "+9665XXXXXXXX", # "type": "text", # "category": "utility", # "created_at": "2026-08-13T10:00:00.000Z" # }A 201 means the message was accepted, not delivered:
statusisqueuedand delivery is asynchronous. Follow it with the message endpoints or with a webhook.
What the sandbox will and will not do
The sandbox exists so you can integrate before you own a number. It is deliberately narrow: a test-mode key is required, only verified recipients can be messaged, and the allocation is temporary.
The allocation expires
A sandbox session lives for 24 hours. When it expires, sends are refused and you allocate a new one. Build against it, then move to a real channel before you go live.
Next
Receive replies and delivery updates with webhooks. Move off the sandbox with channels. Learn what the API does when something goes wrong in errors and limits.