Skip to main content

How it works

Voxfra accepts inbound webhooks from voice AI providers (Vapi, Retell, Bland, etc.) on a per-client basis. Each client in your organization gets a unique webhook URL per provider. When a call ends, your provider posts the call report to that URL — Voxfra handles validation, normalization, and storage.
POST https://api.voxfra.com/webhook/{provider}/{slug}
PartDescription
providerOne of vapi, retell, bland, livekit, elevenlabs, custom
slugClient-specific identifier that maps to your organization and client
Example:
POST https://api.voxfra.com/webhook/vapi/abc-motors-vapi-xe9k2a7f

Authentication

Each webhook URL uses a unique slug as its authentication mechanism. The slug is:
  • Unique across the entire platform
  • Scoped to exactly one organization + client + provider combination
  • Revocable from the admin console at any time
No request headers are required for basic delivery. For additional security, you can optionally enable HMAC signature verification when creating or updating a webhook endpoint — Voxfra will validate the provider’s request signature before processing the payload.

Processing flow

When a webhook arrives:
  1. Slug resolved — maps to the correct organization and client
  2. Schema validated — provider-specific payload checked; returns 400 on mismatch
  3. Idempotency checked — duplicate call IDs within a 24-hour window are accepted but not reprocessed
  4. Normalized and stored — call data is extracted, normalized into a unified format, and written to Voxfra
  5. Available — the call appears in the admin console and via the Management API

Limits

ParameterLimit
Rate limit1,000 requests / minute per endpoint
Body size1 MB
Idempotency window24 hours (by call ID)

Managing webhook URLs

Webhook endpoints are managed in the Voxfra admin console under Settings → Webhooks → Inbound for each client. You can:
  • Create a new URL for a provider
  • Copy the URL to paste into your provider’s dashboard
  • View last_used_at and request_count per endpoint
  • Toggle an endpoint inactive without revoking it
  • Revoke and replace a URL if it’s compromised
  • Configure an IP allowlist or HMAC secret per endpoint
Each client can have at most one active webhook per provider.

Responses

A successful ingestion returns:
{
  "success": true,
  "requestId": "req_xe9k2a7f"
}
All error responses include a requestId for tracing:
StatusMeaning
200Accepted and processed
400Payload failed schema validation
404Slug not found or endpoint inactive
429Rate limit exceeded — check Retry-After header
500Internal error — contact support with requestId