Skip to main content
Voicemail turns an unanswered inbound call into a message. Arm a Wave number, and when a call to it goes no-answer, Wave plays a greeting, records the caller, and files the recording as a voicemail you can list, play, mark heard, and delete.
Voicemail ships behind a per-environment flag. Until it is enabled for your account every endpoint returns 503 VOICEMAIL_DISABLED.

Arm a number

PUT /v1/numbers/{id}/voicemail turns voicemail on or off for one of your Wave numbers. Needs the voicemail:write scope.

A custom greeting

By default Wave plays a standard greeting. To play your own, first upload a WAV with POST /v1/callflows/audio — that returns an audio_ref — then set it as greeting_ref:
greeting_ref must be a prompt your organization uploaded — an arbitrary URL returns 400 VOICEMAIL_GREETING_INVALID. Send null to clear it back to the default; omit the key to leave the current greeting unchanged.

List the box

GET /v1/voicemails returns your messages newest-first with cursor pagination. Needs the voicemail:read scope.
Pass next_cursor back as ?cursor= to page. Narrow the list with ?number= (one number’s box) and ?listened=true|false (heard vs new). Fetch one message with GET /v1/voicemails/{id}.
Two fields are reserved for later additions: transcription_status is pending for now (automatic transcription comes later, and transcription_text stays null until then), and duration_seconds is null until the telephony engine reports a message length.

Play a message

GET /v1/voicemails/{id}/recording-url returns a time-limited playback URL (valid ~60 minutes). Needs the voicemail:read scope and a production key.
A message has audio only once the recording has been captured and storage is provisioned; until then this returns 404 VOICEMAIL_RECORDING_NOT_FOUND or 503 VOICEMAIL_SERVICE_UNAVAILABLE. Sandbox keys get 400 SANDBOX_KEY_NOT_ALLOWED.

Mark heard, and delete

POST /v1/voicemails/{id}/listened stamps the message as heard (the first time only, so the “first heard” instant is stable). DELETE /v1/voicemails/{id} soft-deletes it and clears its recording. Both need the voicemail:write scope.

Get notified

Instead of polling the box, subscribe to the voicemail.received webhook — Wave posts it once a new message’s recording is ready:

Next steps

WaveML

The <Play> and <Record> verbs behind the voicemail flow.

Webhooks

Get voicemail.received pushed to you instead of polling.