Skip to content
RelationsAI
Try it uses test keys only. Requests go straight from your browser to https://voice-api.relationsai.com/v1 with a rai_test_ key, which never places a real call. It works once the API is enabled for your workspace (private preview: support@relationsai.com). Your key stays in this tab's memory; live keys are refused.
RelationsAI API

People you call, with consent and custom fields that become call variables.


List contacts

GET
https://voice-api.relationsai.com/v1
/contacts
Bearer (rai_test_... or rai_live_...)

Lists contacts, newest first. Filter by exact phone number, consent or do-not-call status.

GET /v1/contacts · Operation ID: listContacts

List contacts › query Parameters

limit
​integer · min: 1 · max: 100

Maximum number of objects to return, from 1 to 100. Defaults to 25.

Default: 25
cursor
​string · minLength: 1 · maxLength: 512

The next_cursor of the previous page. Send it with exactly the same filters as the request that returned it; a changed filter set is 400 invalid_cursor.

created_after
​string · date-time

Only objects created at or after this time (RFC 3339, UTC).

created_before
​string · date-time

Only objects created before this time (RFC 3339, UTC).

phone_number
​string · e164

Only the contact with this number (E.164). Matches the same way the do-not-call check does.

consent_granted
​boolean

Only contacts with (true) or without (false) recorded consent.

do_not_call
​boolean

Only contacts on (true) or off (false) the do-not-call list.

List contacts › Responses

A page of contacts.

A page of contacts, newest first.
object
​string · const · required

Always list.

Const value: list
has_more
​boolean · required

True when more objects exist after this page.

next_cursor
​string | null · required

Pass as cursor (with the same filters) to fetch the next page. Null on the last page.

​Contact[] · required

Contacts on this page.


Create a contact

POST
https://voice-api.relationsai.com/v1
/contacts
Bearer (rai_test_... or rai_live_...)

Creates a contact. Phone numbers are unique within a workspace and mode; creating a second contact with the same number is 409 contact_already_exists (use the upsert to create-or-update).

Setting consent_granted: true records that the person consented to be called, with the time and the API as its source. Only set it when they really did: when the workspace requires consent, it is what allows calls to this contact.

POST /v1/contacts · Operation ID: createContact

Create a contact › Headers

Idempotency-Key
​string · minLength: 1 · maxLength: 255 · pattern: ^[\x21-\x7E]+$

Optional. A unique key for this operation, 1 to 255 printable ASCII characters with no spaces (a UUID v4 is ideal). With it, a retry of the same request (same key, same body) returns the stored answer and never runs the action twice; reuse the same key for every retry, it is kept for 24 hours. Without it, every request runs: a retry after a timeout can repeat the action, so check the state with a GET before retrying.

Create a contact › Request Body

Create a contact.
phone_number
​string · e164 · required

The contact's number in E.164 format.

name
​string · minLength: 1 · maxLength: 200

Display name.

language
​string · maxLength: 50

Preferred language.

country_code
​string · minLength: 2 · maxLength: 10

Country code, for example IN.

consent_granted
​boolean

Set to true only when the person has consented to be called. Recorded with the time and the API as its source.

Default: false
​CustomFieldValues · maxProps: 100

Custom field values by field name. Each key must be a custom field defined in the console; an unknown name is 422 custom_field_not_found. Values are strings up to 500 characters. On update, a null value clears that field and omitted fields are left unchanged.

Create a contact › Responses

The contact was created.

A person you call. Phone numbers are unique within a workspace and mode. Custom field values become call variables: an agent can use `{{field_name}}` in its prompt.
id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

Contact id (ct_...).

object
​string · const · required

Always contact.

Const value: contact
livemode
​boolean · required

true for a live contact, false for a test-mode contact.

phone_number
​string · required

The contact's number. E.164 for contacts created through this API; contacts created earlier in the console may hold the number in the format it was entered.

name
​string | null · required

Display name.

language
​string | null · required

Preferred language, as free text or a language code.

country_code
​string | null · required

Country code as entered, for example IN.

consent_granted
​boolean · required

Whether the contact has consented to be called. When the workspace requires consent (a console compliance setting), calls to a contact without consent are refused. Setting this through the API records that consent was given; only set it when it really was. Consent is never recorded on a contact that is on the do-not-call list: it stays false there, and removing the entry does not restore it.

do_not_call
​boolean · required

True when the contact's number is on the do-not-call list. Read-only here: manage it with the do-not-call endpoints. Adding a number to the list also withdraws the contact's consent.

​object · required

Values of the workspace's custom fields for this contact, by field name. Fields are defined in the console.

created_at
​string | null · date-time · required

When the contact was created. Null for some contacts created before this was recorded.


Create or update a contact by phone number

POST
https://voice-api.relationsai.com/v1
/contacts/upsert
Bearer (rai_test_... or rai_live_...)

Creates the contact with this phone number, or updates it if one exists, in one request. The number is matched the same way the do-not-call check matches numbers, so a contact entered without the + and country code in the console is found too. Fields you omit are left unchanged on an existing contact. The response is 201 when a contact was created and 200 when one was updated. This is the recommended way to sync contacts from your CRM.

POST /v1/contacts/upsert · Operation ID: upsertContact

Create or update a contact by phone number › Headers

Idempotency-Key
​string · minLength: 1 · maxLength: 255 · pattern: ^[\x21-\x7E]+$

Optional. A unique key for this operation, 1 to 255 printable ASCII characters with no spaces (a UUID v4 is ideal). With it, a retry of the same request (same key, same body) returns the stored answer and never runs the action twice; reuse the same key for every retry, it is kept for 24 hours. Without it, every request runs: a retry after a timeout can repeat the action, so check the state with a GET before retrying.

Create or update a contact by phone number › Request Body

Create the contact with this phone number, or update it if it exists. Matching is by phone number in the same way the do-not-call check matches numbers.
phone_number
​string · e164 · required

The contact's number in E.164 format. Identifies the contact.

name
​string | null · maxLength: 200

Display name. Null clears it.

language
​string | null · maxLength: 50

Preferred language. Null clears it.

country_code
​string | null · maxLength: 10

Country code. Null clears it.

consent_granted
​boolean

Set to true only when the person has consented to be called; false records withdrawal. Omit to leave unchanged.

​CustomFieldValues · maxProps: 100

Custom field values by field name. Each key must be a custom field defined in the console; an unknown name is 422 custom_field_not_found. Values are strings up to 500 characters. On update, a null value clears that field and omitted fields are left unchanged.

Create or update a contact by phone number › Responses

An existing contact was updated.

A person you call. Phone numbers are unique within a workspace and mode. Custom field values become call variables: an agent can use `{{field_name}}` in its prompt.
id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

Contact id (ct_...).

object
​string · const · required

Always contact.

Const value: contact
livemode
​boolean · required

true for a live contact, false for a test-mode contact.

phone_number
​string · required

The contact's number. E.164 for contacts created through this API; contacts created earlier in the console may hold the number in the format it was entered.

name
​string | null · required

Display name.

language
​string | null · required

Preferred language, as free text or a language code.

country_code
​string | null · required

Country code as entered, for example IN.

consent_granted
​boolean · required

Whether the contact has consented to be called. When the workspace requires consent (a console compliance setting), calls to a contact without consent are refused. Setting this through the API records that consent was given; only set it when it really was. Consent is never recorded on a contact that is on the do-not-call list: it stays false there, and removing the entry does not restore it.

do_not_call
​boolean · required

True when the contact's number is on the do-not-call list. Read-only here: manage it with the do-not-call endpoints. Adding a number to the list also withdraws the contact's consent.

​object · required

Values of the workspace's custom fields for this contact, by field name. Fields are defined in the console.

created_at
​string | null · date-time · required

When the contact was created. Null for some contacts created before this was recorded.


Retrieve a contact

GET
https://voice-api.relationsai.com/v1
/contacts/{contact_id}
Bearer (rai_test_... or rai_live_...)

Returns one contact, with its consent, do-not-call status and custom field values. The ETag header is the version to send as If-Match when you update it.

GET /v1/contacts/{contact_id} · Operation ID: getContact

Retrieve a contact › path Parameters

contact_id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

The contact id (ct_...).

Retrieve a contact › Responses

The contact.

A person you call. Phone numbers are unique within a workspace and mode. Custom field values become call variables: an agent can use `{{field_name}}` in its prompt.
id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

Contact id (ct_...).

object
​string · const · required

Always contact.

Const value: contact
livemode
​boolean · required

true for a live contact, false for a test-mode contact.

phone_number
​string · required

The contact's number. E.164 for contacts created through this API; contacts created earlier in the console may hold the number in the format it was entered.

name
​string | null · required

Display name.

language
​string | null · required

Preferred language, as free text or a language code.

country_code
​string | null · required

Country code as entered, for example IN.

consent_granted
​boolean · required

Whether the contact has consented to be called. When the workspace requires consent (a console compliance setting), calls to a contact without consent are refused. Setting this through the API records that consent was given; only set it when it really was. Consent is never recorded on a contact that is on the do-not-call list: it stays false there, and removing the entry does not restore it.

do_not_call
​boolean · required

True when the contact's number is on the do-not-call list. Read-only here: manage it with the do-not-call endpoints. Adding a number to the list also withdraws the contact's consent.

​object · required

Values of the workspace's custom fields for this contact, by field name. Fields are defined in the console.

created_at
​string | null · date-time · required

When the contact was created. Null for some contacts created before this was recorded.


Delete a contact

DELETE
https://voice-api.relationsai.com/v1
/contacts/{contact_id}
Bearer (rai_test_... or rai_live_...)

Permanently deletes a contact, its custom field values and its consent history, and removes it from every campaign's recipient list (a campaign that has already started keeps calling the recipients its run began with). Calls to the contact remain in the call list. A contact on the do-not-call list cannot be deleted (409 contact_on_dnc_list), so a deletion never removes a do-not-call protection.

DELETE /v1/contacts/{contact_id} · Operation ID: deleteContact

Delete a contact › path Parameters

contact_id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

The contact id (ct_...).

Delete a contact › Headers

Idempotency-Key
​string · minLength: 1 · maxLength: 255 · pattern: ^[\x21-\x7E]+$

Optional. A unique key for this operation, 1 to 255 printable ASCII characters with no spaces (a UUID v4 is ideal). With it, a retry of the same request (same key, same body) returns the stored answer and never runs the action twice; reuse the same key for every retry, it is kept for 24 hours. Without it, every request runs: a retry after a timeout can repeat the action, so check the state with a GET before retrying.

Delete a contact › Responses

The contact was deleted.

Returned by a successful delete. The object no longer exists.
id
​string · required

Id of the deleted object.

object
​string · required

Type of the deleted object, for example contact.

livemode
​boolean · required

true for live mode, false for test mode.

deleted
​boolean · const · required

Always true.

Const value:

Update a contact

PATCH
https://voice-api.relationsai.com/v1
/contacts/{contact_id}
Bearer (rai_test_... or rai_live_...)

Changes the fields you send. custom_fields merges: listed fields are set, a null value clears a field, omitted fields are kept. consent_granted records consent (true) or its withdrawal (false) with the time and the API as source. The do-not-call status cannot be changed here; use the do-not-call endpoints. Requires If-Match with the contact's current ETag.

PATCH /v1/contacts/{contact_id} · Operation ID: updateContact

Update a contact › path Parameters

contact_id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

The contact id (ct_...).

Update a contact › Headers

If-Match
​string · minLength: 1 · maxLength: 128 · required

The ETag from your most recent read of this resource. The update is refused if the resource has changed since. * matches any current version: the update is applied without the concurrency check.

Update a contact › Request Body

Fields to change. Omitted fields are left as they are.
phone_number
​string · e164

New number in E.164 format. Must not belong to another contact.

name
​string | null · maxLength: 200

Display name. Null clears it.

language
​string | null · maxLength: 50

Preferred language. Null clears it.

country_code
​string | null · maxLength: 10

Country code. Null clears it.

consent_granted
​boolean

True records that consent was given; false records that it was withdrawn.

​CustomFieldValues · maxProps: 100

Custom field values by field name. Each key must be a custom field defined in the console; an unknown name is 422 custom_field_not_found. Values are strings up to 500 characters. On update, a null value clears that field and omitted fields are left unchanged.

Update a contact › Responses

The updated contact, with its new ETag.

A person you call. Phone numbers are unique within a workspace and mode. Custom field values become call variables: an agent can use `{{field_name}}` in its prompt.
id
​string · pattern: ^ct_[A-Za-z0-9_-]{1,… · required

Contact id (ct_...).

object
​string · const · required

Always contact.

Const value: contact
livemode
​boolean · required

true for a live contact, false for a test-mode contact.

phone_number
​string · required

The contact's number. E.164 for contacts created through this API; contacts created earlier in the console may hold the number in the format it was entered.

name
​string | null · required

Display name.

language
​string | null · required

Preferred language, as free text or a language code.

country_code
​string | null · required

Country code as entered, for example IN.

consent_granted
​boolean · required

Whether the contact has consented to be called. When the workspace requires consent (a console compliance setting), calls to a contact without consent are refused. Setting this through the API records that consent was given; only set it when it really was. Consent is never recorded on a contact that is on the do-not-call list: it stays false there, and removing the entry does not restore it.

do_not_call
​boolean · required

True when the contact's number is on the do-not-call list. Read-only here: manage it with the do-not-call endpoints. Adding a number to the list also withdraws the contact's consent.

​object · required

Values of the workspace's custom fields for this contact, by field name. Fields are defined in the console.

created_at
​string | null · date-time · required

When the contact was created. Null for some contacts created before this was recorded.