Anatomy
An agent is assembled from these fields:
At dispatch time the prompt is assembled in a fixed order — Objective → Instructions → Task → FAQs → Samples — and placeholders are substituted from the session’s
custom_variables. Only those, and the built-in {{callee_name}}, fill placeholders: a call’s metadata and the platform’s own values, such as phone numbers, never do.
{{callee_name}} is built in. Every voice agent can use it in its prompt, opening greeting and closing statement without declaring it. It is filled from the call’s callee name — callee_name on POST /calls, name on the Ringg-compatible call API, participant_name on a session, or a callee_name (else name) column on a campaign recipient — unless custom_variables.callee_name is set. The name is spoken in Title Case, so VIKAS AWASTHI is read as “Vikas Awasthi” instead of being spelled out letter by letter. When no name is known the placeholder renders empty. What you send is stored and echoed back unchanged.Post-call sentiment
Setsentiment_analysis to { "enabled": true } and each finished call is classified as positive, negative or neutral from the customer’s side of the transcript. The verdict appears as sentiment on the session, on a call’s attempts, and in the call_completed webhook.
It is opt-in per agent because it costs an extra model call per session, and it is skipped when the customer barely spoke — there is nothing to classify. It is independent of a campaign’s qualification verdict: sentiment is how the customer felt, not whether they qualified.
Lifecycle: draft → published
Agents are immutable once published. This guarantees a campaign always runs the exact configuration it was bound to.- Created
draftand fully editable viaPUT /agent/{id}.PUTreplaces the whole agent, so send every field you want to keep, including the fullconfig. - Publish (
POST /agent/{id}/publish) locks the config and makes the agent bindable by campaigns. One-way:422if the agent has nonameor itsconfigfails the save-time checks (such as a key the agent editor doesn’t set),409if already published. - Once published,
PUTis rejected with409. To change a published agent, clone it (POST /agent/{id}/clone) — cloning always yields a newdraft. - Campaigns bind only published agents. Creating or updating a campaign with a
draftagent returns400. - Deletion is guarded:
DELETE /agent/{id}returns409while any campaign still references the agent.
status (draft | published) and published_at are read-only response fields — status moves only through the publish endpoint, never as a body field.
Preview and testing (
GET /agent/{id}, WhatsApp test-reply, and test sessions) work on drafts too — you don’t need to publish to try an agent.Visibility
workspaceagents are visible to everyone in the workspace.privateagents are visible only to their owner (and admins). Personal copies of catalog agents are createdprivateand suffixed “(My copy)”.
Endpoints
Test your agent
Simulate callers and grade the transcript before publishing.
Sessions
Run an agent as a live call.
Providers & Models
Configure LLM, STT, and TTS.

