2xx response, and the event is marked as delivered. This is the most reliable way to keep your CRM, data warehouse, or billing system in sync with call activity on your TalkChief account.
Setting Up a Webhook
1
Expose a public HTTPS endpoint
Deploy a route on your server that accepts
POST requests and is reachable over the public internet with a valid TLS certificate. HTTP (non-TLS) endpoints are not accepted. During local development, tools like ngrok or Cloudflare Tunnel can create a temporary public HTTPS tunnel to your localhost.2
Navigate to webhook settings
In your TalkChief dashboard, go to Settings → Developers → Webhooks.
3
Add a new webhook
Click Add Webhook and enter the full HTTPS URL of your endpoint (e.g.,
https://your-app.example.com/webhooks/talkchief).4
Select event types
Choose the events you want to receive. Select call.completed to receive CDR records for every finished call. Additional event types may be available depending on your plan.
5
Copy your signing secret
After saving the webhook, TalkChief displays a one-time signing secret. Copy it immediately and store it securely — treat it like a password. You will use it to verify the
TalkChief-Signature header on incoming requests.6
Deploy your handler and test
Deploy your webhook handler, then place a real call on your TalkChief account. Check your server logs for the incoming payload and confirm that your signature verification passes. Use the Resend button in the dashboard to replay events during development.
Event Types
Additional event types (e.g.,
call.missed, call.transferred) may be available on your plan. Check Settings → Developers → Webhooks → Event Types in your dashboard for the full list.Webhook Payload
TalkChief delivers the following JSON body for acall.completed event. All fields are present on every delivery; fields that are not applicable for a given call (e.g., recording_url when recording is disabled) are included as null.
Payload Field Reference
string
The event type string. Always
"call.completed" for CDR events. Use this to route payloads if your endpoint handles multiple event types.string
The unique identifier for this call, prefixed with
c_. Use this as the idempotency key — if your endpoint receives the same call_id twice (due to a retry), process it only once.string
Whether the call was
"inbound" (originated externally and arrived at your TalkChief number) or "outbound" (initiated by your team or via the Click-to-Call API).string
The E.164-formatted phone number of the call originator. For inbound calls, this is the caller’s number. For outbound calls, this is your TalkChief caller ID.
string
The E.164-formatted phone number that was dialled. For inbound calls, this is your TalkChief number. For outbound calls, this is the destination number.
integer
The total connected call duration in whole seconds. This is the billable talk time, not the total time including ringing.
string
The final disposition of the call. Common values include
"completed" (answered and ended normally), "no-answer", "busy", and "failed".string
ISO 8601 UTC timestamp of when the call ended (e.g.,
"2024-11-15T14:32:00Z").string
A pre-signed HTTPS URL to the call recording audio file, if call recording is enabled on your account.
null if recording is disabled or the call was not recorded. Pre-signed URLs expire after 24 hours — download the file promptly if you need to retain it.string
The ID of the queue the call passed through, if any.
null for calls that bypassed queueing.string
The TalkChief user ID of the agent who handled the call.
null for unanswered calls.object
The key-value metadata object you passed when initiating an outbound call via the Click-to-Call API. Empty object
{} for inbound calls or outbound calls initiated without metadata.Verifying Webhook Signatures
TalkChief signs every webhook request using HMAC-SHA256. The signature is sent in theTalkChief-Signature HTTP header as a hex-encoded digest of the raw request body, computed using your webhook signing secret.
To verify a request, recompute the HMAC-SHA256 digest of the raw request body using your secret, then compare it to the value in the header using a constant-time comparison function. Always use a constant-time comparison — standard string equality (===, ==) is vulnerable to timing attacks.
- Node.js
- Python
Retry Behavior
If your endpoint returns a non-2xx HTTP status code, or does not respond within 10 seconds, TalkChief marks the delivery as failed and retries with exponential backoff:
After five failed retries, the event is marked as permanently undelivered. You can replay individual events manually from Settings → Developers → Webhooks → Event Log in your dashboard.
Because the same event may be delivered more than once during retries, your handler must be idempotent. Use the
call_id field as a natural idempotency key — check whether you have already processed a record with that ID before writing to your database or triggering downstream actions.

