Authentication
There are three kinds of auth in SIP.IO: API credentials (how you call the API), SIP device authentication (how a phone proves who it is), and internal gating (how the platform’s own edge endpoints are protected).
API authentication
Section titled “API authentication”Every request to the public API carries one of two credentials in a header, and is authorized against per-resource scopes.
API keys (machine-to-machine)
Section titled “API keys (machine-to-machine)”curl https://api.sip.io/v1/whoami -H 'x-api-key: sk_…'- Created per account; the secret is shown once at creation (
sk_…) and stored only as a hash, so keep it safe. - Each key carries a set of scopes (below). A key never expires until revoked.
- Presented as the
x-api-keyheader.
Session tokens (user / console)
Section titled “Session tokens (user / console)”A console login exchanges email + password for a short-lived JSON Web Token:
curl -X POST https://console.sip.io/login \ -H 'content-type: application/json' \ -d '{ "email": "you@acme.com", "password": "…" }'# → { "ok": true, "token": "…", "token_type": "Bearer", "expires_in": 43200, "scopes": ["*"] }Use the token on subsequent requests:
curl https://api.sip.io/v1/account -H 'Authorization: Bearer <jwt>'Tokens are stateless (HS256), carry the account, user, and scopes, and expire in 12 hours.
Scopes
Section titled “Scopes”Each credential is limited to a set of scopes; a request to a resource requires the matching scope (a missing scope returns 403 with the scope it needs). * grants all.
| Scope | Grants |
|---|---|
cdr | Calls / CDR read & export |
agents | Read agent state; drive agent state |
queues | Read queues & KPIs |
numbers | Read numbers |
dnc | Manage the do-not-call list |
campaign | Manage dialer campaigns |
webhooks | Manage webhooks |
messaging | Send messages (the messaging service) |
caller_id | Manage per-user caller-ID (console) |
wallboard | The realtime wallboard data & socket |
* | Everything |
Credentials are header-only; there’s no query-string key. (The one exception is the wallboard WebSocket, which can’t send headers; it uses a short-lived single-use ticket minted from a scoped request.)
SIP device authentication
Section titled “SIP device authentication”Phones authenticate to register and place calls using SIP digest auth: the credential is a digest hash, never a plaintext password.
- A device sends
REGISTER/INVITE; the signaling layer issues the401challenge. - The device responds with the digest
Authorization. - The signaling layer asks the control plane (
/auth) to verify it. - The platform looks up the device by
(auth_username, realm), verifies the storedha1, checks that device and account areactive, and returns the account context to bind to the registration.
{ "ok": true, "account_id": "acc_acme", "user_id": "us_dana", "device_id": "dev_dana_desk", "webrtc": false }sip_device field | Meaning |
|---|---|
auth_username | The SIP username. |
realm | The account’s SIP domain (the digest realm). |
ha1 / ha1b | MD5(username:realm:password) and the @domain variant. |
Because the realm is the account’s SIP domain, the same extension in two tenants (1002@acmeA vs 1002@acmeB) is two isolated credentials. WebRTC endpoints register over WSS and authenticate the same way.
Internal gating
Section titled “Internal gating”The edge control plane’s own endpoints aren’t public; they’re for the SIP nodes and operator tooling:
| Surface | Gate |
|---|---|
SIP-facing (/auth, /route, /flow, /presence, /agent, /cac, /media, /calls) | App-layer IP allowlist (node + operator IPs). |
/media/* | Restricted to media-node IPs (keeps object storage private). |
/admin/* (key minting, console-user provisioning) | x-admin-token shared secret. |
| Node push | A secure tunnel + per-node agent token. |
| Outbound PSTN | Must originate from an active, account-owned device (toll-fraud gate). |
The management (console.sip.io), realtime (realtime.sip.io), and public API (api.sip.io) services use the per-account API-key / session model above, not the internal x-admin-token.