Skip to main content
After an Omni call ends, PyAI can run an extraction pass over the transcript and deliver a structured JSON object, captured fields, intent, outcome, to your webhook. No client code and no engine integration required: you declare a JSON Schema on the agent and point it at an HTTPS endpoint.
This is post-call capture (after the call, fully PyAI-run). For in-call function calling where your code executes mid-conversation, see Function calling. For the difference between the tool systems, see Tools overview.

Configure

Set two fields on the agent, a JSON Schema of the fields to capture and a signed delivery URL:
Or use the console: Agents → your agent → Data capture. Both fields are required to enable extraction. Set either to null to turn it off. extraction_webhook_url must be https.

How a call is matched to your agent

Omni is zero-state, a call is authorized by your key’s org, not a stored agent. To attribute a call to a specific agent’s extraction config, set the connect URL’s session_label to that agent’s id:
PyAI resolves the agent only when the session_label equals an agent id in the same org, so another tenant’s id can never trigger your extraction.

The delivery (engine → your webhook)

When the call completes, PyAI POSTs the extracted object, signed with X-PyAI-Signature (same scheme as transcription webhooks):
Correlating to your own call leg. call_id is PyAI-generated. To map it back to your telephony leg (Twilio/SIP), set a meta object on the session (e.g. a meta.external_id you control); PyAI echoes meta verbatim and lifts a string meta.external_id to the top-level external_id. session_label is also echoed, but it doubles as the agent_… resolution id, so prefer meta.external_id for a per-call key. Both external_id and meta are null when nothing was set.

Verify the signature

The signature is t=<unix_seconds>,v1=<hmac> where the HMAC-SHA256 is computed over `${t}.${rawBody}` with your webhook signing secret:
Get your signing secret with POST /v1/webhooks/signing-secret, it’s scoped to your org and returned once. Check status (configured? last 4) with GET /v1/webhooks/signing-secret. To rotate with no dropped events: deploy verification that accepts both the old and new secret, call the endpoint again, then drop the old one.

Behavior & limits

  • Best-effort / fail-open. Extraction never blocks or fails a call. If the transcript is empty, the model can’t produce valid JSON, or your webhook is down, the call is unaffected and nothing is delivered.
  • Fields you can’t determine come back null, values are never invented.
  • The transcript is truncated for very long calls before the extraction pass.
  • Delivery retries up to 3 times with a short backoff on a transient failure (network error, 429, or 5xx); a 4xx is treated as a permanent client error and is not retried. Return 2xx quickly. Delivery is at-most-once per attempt and not strongly durable, treat a missed event as best-effort.

See also

Tools overview

Knowledge vs function-calling tools.

Function calling

In-call tools your client executes.

Omni protocol

Connect URL, session_label, frames.

Conversation intelligence

Transcripts, summaries, recordings.