| name | elevenlabs-webhooks-events |
| description | Implement ElevenLabs webhook HMAC signature verification and event handling.
Use when setting up webhook endpoints for transcription completion,
call recording, or agent conversation events from ElevenLabs.
Trigger: "elevenlabs webhook", "elevenlabs events",
"elevenlabs webhook signature", "handle elevenlabs notifications",
"elevenlabs post-call webhook", "elevenlabs transcription webhook".
|
| allowed-tools | Read, Write, Edit, Bash(curl:*) |
| version | 1.0.0 |
| license | MIT |
| author | Jeremy Longshore <jeremy@intentsolutions.io> |
| tags | ["saas","voice","ai","elevenlabs","webhooks","events"] |
| compatible-with | claude-code |
ElevenLabs Webhooks & Events
Overview
ElevenLabs webhooks send HTTP POST notifications when async operations complete. Supported event types include transcription completion, post-call data from Conversational AI agents, and call initiation failures. Webhooks use HMAC-SHA256 signatures for verification.
Prerequisites
- ElevenLabs account (webhooks configured in Settings > Webhooks)
- HTTPS endpoint accessible from the internet
- Webhook secret (generated during webhook creation in dashboard)
Instructions
Step 1: Webhook Event Types
| Event Type | Payload | When Triggered |
|---|
post_call_transcription | Full conversation transcript, analysis, metadata | After Conversational AI call ends |
post_call_audio | Base64-encoded call audio, minimal metadata | After call ends (if audio recording enabled) |
call_initiation_failure | Failure reason, metadata | When an outbound call fails to connect |
speech_to_text.completed | Transcription result, word timestamps | Async STT job completes |
Step 2: Webhook Setup
Step 3: HMAC Signature Verification
import crypto from "crypto";
export function verifyWebhookSignature(
rawBody: string | ,
: ,
:
): { : ; ?: } {
(!signatureHeader || !secret) {
{ : , : };
}
parts = (
signatureHeader.().( {
[key, ...val] = p.();
[key, val.()] [, ];
})
);
timestamp = parts.();
signature = parts.();
(!timestamp || !signature) {
{ : , : };
}
age = .(.() / ) - (timestamp);
(age > ) {
{ : , : };
}
signedPayload = ;
expected = crypto
.(, secret)
.(signedPayload)
.();
{
isValid = crypto.(
.(signature, ),
.(expected, )
);
{ : isValid };
} {
{ : , : };
}
}