API v3
POST /number_orders
Order a number. Prepaid from your account balance.
The first payment is taken from your account balance before the number is ordered. A balance that does not cover it is 402 insufficient_balance and nothing is ordered. If the order cannot be placed, the payment is returned to your balance exactly once and the answer is 503. One Idempotency-Key never charges or orders twice. No refund when a number is later released or cancelled.
Addresshttps://api.voicepro.plus/v3/number_orders
Key permissionorders:write
Idempotency-KeyRequired. A retry with the same key and body replays the first answer, so it never acts twice.
ChargesPaid from your account balance before it runs; a short balance is 402 and nothing runs.
Fields
| Name | In | Type | |
|---|---|---|---|
| Idempotency-Key * | header | string | Required on every POST. 8-128 characters: letters, digits, dot, colon, hyphen or underscore. The first response is stored for 24 hours and replayed for any retry with the same key and the same body. Two rules, set per operation by x-charged. Charged or partner-side operations (x-charged true: dips, dip batches, orders, SMS, porting) never re-run while a first attempt is unfinished: a retry answers 409 idempotency_key_in_use (outcome pending) until the first outcome is stored, and the key is also given to the partner as its own reference, so one key never causes more than one order, charge or message, even across failures. A charged operation that fails part-way stores that failure as the key's answer; only a refusal before anything ran (400, 401, 402, 403, 404, 429) frees the key for a retry. Operations with no outside effect (x-charged false) hold their key for at most 2 minutes; after that a retry runs fresh. Missing: 400 missing_parameter (param Idempotency-Key). Malformed: 400 invalid_parameter. Same key, different body: 409 idempotency_key_reused. First request still running: 409 idempotency_key_in_use. |
| offer_id * | body | string | |
| currency | body | string | The currency the first payment is paid in, from your prepaid balance in that currency; left out, your account's own currency. Each price is the catalogue figure converted at today's rate and rounded up to a clean price (.49 or .99, or 50 whole units for JPY and KRW). |
* required
Example
curl -X POST "https://api.voicepro.plus/v3/number_orders" \
-H "Authorization: Bearer vpkey_YOUR_KEY" \
-H "Idempotency-Key: $(uuidgen)" \
-H "Content-Type: application/json" \
-d '{"offer_id":"nof_m3xk7q2zrw4pdn6hc5tbvfya"}'Response
{
"object": "number_order",
"id": "nord_p6wz2kq7mx4rd3nh5cbtvfya",
"status": "completed",
"offer_id": "nof_m3xk7q2zrw4pdn6hc5tbvfya",
"phone_number": "+442079460188",
"number_id": "num_r5kx2wq7mz4pd3nh6cbtvfya",
"charged": {
"amount": 150,
"currency": "USD"
},
"balance_after": {
"amount": 4850,
"currency": "USD"
},
"created_at": "2026-10-28T09:30:00Z"
}Errors
Every error has the same shape: { "error": { "type", "code", "message", "param", "request_id" } }.
missing_api_key401: No Authorization header, or not a Bearer key.
invalid_api_key401: The key is not recognised.
api_key_revoked401: The key was revoked in the portal.
api_key_expired401: The key passed the expiry date set on it.
missing_scope403: The key lacks the scope this endpoint needs; param names the scope.
ip_not_allowed403: The key has an IP allowlist and this request came from elsewhere.
account_not_active403: The workspace is suspended or closed.
invalid_parameter400: A query parameter or body field has a bad value; param names it.
missing_parameter400: A required parameter or field is missing; param names it.
unknown_parameter400: A parameter or field that this endpoint does not accept; param names it.
invalid_json400: The body is not valid JSON.
invalid_cursor400: The cursor is malformed, expired or from a different list.
invalid_time_range400: from or to is not an ISO 8601 date-time, or to is not after from.
range_too_long400: The time range is longer than this endpoint allows (stated in the endpoint).
body_too_large413: The body is over 1 MiB.
route_not_found404: No such path in v3.
resource_not_found404: No object with that id on this account.
service_not_enabled404: The account does not have this service (voice trunk, IoT, numbers); param names it.
idempotency_key_reused409: This Idempotency-Key was used within 24 hours with a different request.
idempotency_key_in_use409: A request with this Idempotency-Key is still running, or its outcome at a partner is not yet known (message: outcome pending); retry shortly with the same key. If a charged request never finished, the message says so: check your balance and orders before sending it again with a new key.
state_conflict409: The object is not in a state that allows this action (for example resuming an active SIM).
insufficient_balance402: Prepaid funds or the account's order limit do not cover this charged action (a dip, an SMS or an order).
rate_limited429: Too many requests for this key or for the whole account (the message says which); wait Retry-After seconds.
upstream_unavailable503: A network partner or data service behind this endpoint is unavailable.
network_action_unavailable503: This network action is not switched on for the account yet (for example SIM suspend).
internal_error500: Our fault. Quote the request_id to support.
service_unavailable503: API v3 itself is briefly unavailable (for example a configuration problem on our side); the rest of VoicePro is unaffected. Retry later.