Skip to main content
TFU Live is one Agent containing Brain (shared business knowledge and behaviour) and Voice (spoken delivery). Create it through the dedicated /api/tfu-live-agents module. Ordinary agents keep their existing creation body and purpose types. Runtime is not a fourth outreach/inbound/appointment purpose. Use the returned tfu_live:<profileId> public id on the TFU Live routes. The server verifies the stored tenant-owned identity; an id prefix grants no access. Runtime conversion and mixed ordinary/TFU authored bodies are refused. These changes are local development code, not a production publication. Agency owners can also create agents from the dashboard, using Build with AI or Configure myself. The same sub-account ownership and resource checks apply to manual edits and typed or spoken co-authoring. project_user access does not permit creation. Provider administration remains restricted to staff.

Prerequisites

  • An agency API key with agents:read to inspect an agent or agents:write to create, edit and prepare it. Write scope also covers reads.
  • A connected sub-account belonging to that key’s agency. A narrower credential location binding still applies. Supplying another locationId does not grant access.
  • An authorised test environment and synthetic records. A local server can still use a shared development database and external providers.
Use Authorization: Bearer YOUR_API_KEY, as described in Authentication. The examples use placeholder IDs, not working customer records. No staff credential or internal service key is required.

Step 1: Create an empty draft

Send this body to Create agent with ?locationId=YOUR_LOCATION_ID:
Choose a stable id using letters, digits, underscores or hyphens, up to 100 characters. Keep it if you lose the response: read that ID before retrying. Retry creation with the same id and original body to finish an interrupted campaign attachment. The retry keeps an existing campaign and its settings. Campaign and private cadence writes commit together, so a failed attachment cannot leave a partial campaign or duplicate cadence. A saved provider draft remains available for the same-id retry; creation is not reported as complete until the campaign is confirmed. TFU_LIVE_CAMPAIGN_PENDING reports that recoverable partial creation. TFU Live does not use the ordinary agent’s Idempotency-Key replay contract. An existing conflicting ID returns an error rather than creating another agent. The response is 201 with data.agent and data.campaign. New agents, including empty drafts, automatically receive a linked paused campaign and a private Power Dialer cadence, and start with two workflows, Schedule a callback and Stop contact, unless the body already brings a workflow that schedules an AI call or puts the lead on DND. data.campaign.id is the campaign identifier; profileId is its internal TFU Live profile binding. Caller numbers and trigger tags start empty. Choose them in Settings and the Brain trigger before going live. Read the actual data.agent object for id, ifVersion, brain, voice and setup. A draft has provisioningPolicy: "explicit". Creating and editing this draft does not provision provider agents or activate a campaign. Alternatively, supply id, name, brain and voice together to create a complete agent. Complete creation starts setup immediately. A successful create still does not mean setup has finished. Or start from a Brain template, a ready-made agent: send id, brainTemplateId and the values it needs (a calendar, who takes transfers) to create an explicit draft that already has its workflows and a starting prompt. List them with List TFU Live Brain templates; the workflows contract describes each and what it needs.

Step 2: Discover only the capabilities you need

Read Discover TFU Live capabilities at /api/tfu-live-agents/tfu_live:example_agent/brain/catalog?locationId=YOUR_LOCATION_ID. An agent’s abilities are workflows: each has a name (the AI’s tool name), a description (when the AI should run it) and steps built from nodes. The catalog’s data.workflows lists every node with its settings (in words and as JSON Schema), outputs, timing and the arguments it takes, the templates to start from (Live transfer, Book appointment, Cancel appointment, Human assistance, Stop contact, Check tag, Add tag, Schedule a callback, Check service area) and which of their settings must be filled before saving, the path rules and the limits. data.subAccount says which CRM the sub-account uses: on the native CRM (nativeCrm: true) there are no tags, so tag nodes are refused. The catalog is not an agent’s saved configuration; read the agent separately for its current state. Create a draft before requesting its catalog. The workflows contract describes every shape. data.capabilities is the short index of the tool groups that stay tools. Add group=outreach to retrieve that group’s tool schema, configuration and business questions. supported reports the connected runtime’s support, not business readiness. The catalog also lists voices and background rooms. Do not invent names or infer what a voice sounds like from its name. Resolve calendars, tags, custom fields, pipelines, reps and teams with Look up TFU Live resources (GET /api/tfu-live-agents/{id}/resources/{kind}). It reads the same lookups a save verifies against, with this module’s scope and sub-account checks. An unavailable lookup (status: "unavailable") is unknown, not an empty list. Calendars come from the sub-account’s CRM. A native sub-account lists its own native calendars (source: "native"): they work in roleplay, but a real call cannot book on them yet, so going live needs GoHighLevel. A GoHighLevel sub-account lists its GoHighLevel calendars only (source: "gohighlevel"), and a save there refuses a native calendar. sources reports each source on its own: a source that could not be read is unavailable while the others are still listed. Read data.agent.authoring.editable before editing an existing agent. A false value with legacy_voice_contract, unrepresented_capability or outdated_format in authoring.reasons means the API cannot represent that agent losslessly; outdated_format is an agent saved before the workflow model. Edits and preparation return 409 until an explicit migration is completed. Reading it does not change existing behaviour.

Step 3: Translate the business request into a reviewed edit

For “cover postal code 10001, explain the boundary elsewhere, and speak calmly”, send the complete authored object below to Update agent with ?locationId=YOUR_LOCATION_ID:
Replace ifVersion with the value from your last read. This is a complete TFU Live authoring replacement, unlike the ordinary agent’s partial config patch. To change one workflow without sending the rest, use Replace TFU Live workflow and its neighbours, which run the same checks. Preserve unrelated prompt text, capability configuration and existing workflows. The response returns the next ifVersion. A workflow id is wf_ followed by 8 lowercase letters or digits; keep an existing workflow’s id when you change it, so its tool keeps its history. Brain text may remain incomplete while an explicit draft is being built. Voice instructions must remain non-empty. Fields outside this authoring contract, including model selection, runtime changes and campaign activation, are refused. For appointments, build a workflow from the Book appointment template. Find slots offers times from one calendar, or from ordered routing rules over collected answers: the first matching rule’s calendar is used, an unknown answer is asked for, and there is no default calendar, so add a last rule with is_set for a catch-all. When one choice item decides, every one of its answers must choose a calendar. Every calendar must be active in this sub-account. The calendar’s CRM sub-account supplies its timezone at runtime; do not ask for an appointment timezone. Collect information gathers the answers during the call, before availability and booking; post-call extraction is too late for this decision.

Step 4: Prepare the exact saved version

Explicit drafts stay unprovisioned until you send this body to Prepare TFU Live agent at /api/tfu-live-agents/tfu_live:example_agent/prepare?locationId=YOUR_LOCATION_ID:
Preparation accepts only ifVersion, not authored fields. Preparation validates the saved configuration and starts setup for that exact version. Read the agent again to observe progress. Existing agents without the explicit draft policy start setup when edited. A 202 response means the request was accepted. setupStarted reports whether setup was requested; setupError reports an edit saved without confirmed setup. setup.status can be draft, queued, provisioning, ready, provisioning_blocked or provisioning_uncertain. Inspect failureCode on a blocked or uncertain revision before retrying. setup.revision and setup.verifiedAt describe verified setup, not campaign activation. An edit can be pending while the prior verified version remains in service. Always use the newly returned ifVersion and the current setup.status; an old verification timestamp does not make a pending edit ready. To go back to an earlier save, send ifVersion and that save’s revision number from the agent’s changeHistory to POST /api/tfu-live-agents/{id}/restore. The authored text of that revision comes back as a new revision, through the same save and setup as an edit. History is never rewritten, and the last fifty saves can be restored.

Boundaries

  • Creating, saving and preparing an agent do not create or activate a campaign. Campaign permissions and activation checks remain separate. Campaign settings stay shared; current customer TFU campaign mutation adapters remain incomplete. Ordinary outcome prompts and workflow graphs are intentionally not applicable, not aliases for Brain text.
  • TFU Live create/get/update own complete authored revisions. Use GET /api/tfu-live-agents?locationId=... for its list and GET /api/tfu-live-agents/{id}/operations for current runtime support. Clone, delete and split-test are not implemented for TFU.
  • The agent’s abilities are brain.capabilityConfig.workflows, part of the complete authored aggregate. Each workflow is a tool for the AI: its name gives the tool name, its description is when to run it, and renaming it renames the tool. There are no special workflows; every node can be used in any workflow. Collect information is the only way the AI supplies inputs: its items become the tool’s arguments. A node with outputs ends its list: the steps after it go on its outputs. Tags are never chosen by the AI: Check tag, Add tag and Remove tag each hold one tag. A Transfer node has the outputs Connected, Nobody available and Not connected; a call makes one transfer attempt, a fallback transfer goes only on Nobody available, and after Connected only actions and Conditions may follow. Put on DND ends the lead’s journey, so nothing follows it. The catalog’s workflows contract lists the node formats and limits. Saving validates the workflows with the runtime validator but executes nothing, and refuses an invalid workflow with 422, naming the workflow and step. Custom fields, pipelines and calendars a new or changed step names must exist in this sub-account. HTTPS webhooks also pass outbound URL policy. A webhook sends the call’s context (workflow, sentAt, ids, contact, call) plus its fields, each from fixed text, a contact field, a call detail or a collected answer. Authentication headers must be secret: send {"secret":{"value":"…"}} once, and the value is stored encrypted and read back only as {"secret":{"id":"…"}}, which you send back unchanged to keep it. The formats workflows replaced (brain.hooks, followUps, outcomeSteering, customTools, appointments, per-tool settings such as transfer_call or check_area_code, and workflows keyed by tool id) are refused until the agent’s migration has run.
  • A Notify teammate node sending to Slack uses symbolic main or alerts channels, resolved by the runtime from the call tenant. authoring.bindingWarnings distinguishes an unverified mapping from a ready integration.
  • Transfer destinations and team-channel mappings require existing authorised configuration. A Transfer node names its destination; it does not create one.
  • Split/master authoring and provider-specific tuning are not supported by this contract. Voice delivery instructions do not implement numeric provider controls.
  • The internal conversational builder retrieves focused authoring guidance and capability details through its own authenticated tools. Customer backends can use this guide and the discovery requests above; this API does not expose the internal builder conversation, voice session or arbitrary tool executor.

Shared campaign controls, separate authoring

Caller-number ownership, calling windows, timezones and concurrency use shared campaign services and checks. Follow-up timing uses the campaign-bound cadence. TFU Live still has its own verified profile and call lifecycle. Workflows run when the AI calls their tool, during the conversation. They are not the ordinary campaign outcome workflow graph. Some action implementations are shared, but this API does not accept that graph’s schema or claim its endpoint compatibility. Campaign association requires the TFU Live profile and the campaign binding to be visible to the runtime that validates them. A local setup with separate SaaS and voice databases does not prove this association works end to end. This change does not switch databases or migrate records.

Handle errors

TFU Live errors use { "success": false, "error": "Explanation", "code": "…" }, and a workflow refusal also names workflowId, stepId and field. Branch on code, never on the words: the codes are listed in the workflows contract. Missing-scope responses also identify requiredScope.

In the API