This documents the v1 product. It is kept for integrations already running
on it. If you are building something new, start with the
Quickstart.
callbackUrl when you initiate a call and v1
POSTs events there as the call progresses.
v2 signs differentlyv1 uses
x-signature (a bare hex HMAC over the raw body) plus x-public-key.
v2 uses X-Mirai-Signature: t=…,v1=… with a replay window. If
you run both, use two separate routes — the schemes are not interchangeable.Envelope
Lifecycle events
Failure and retry events
retryProtocol on the assistant decides how many attempts follow a failure.
call.lifecycle-ended is what tells you the chain is over — that is the
event to close your record on, not call.failed.
end-of-call
Carries the analysis plan output and credit
usage.
action events
Fired when the conversation produced a business action for you to execute.
reason is set when the action exists because something was missing:
missing_address, missing_first_name, invalid_cart_data.
Signature verification
Every delivery carries two headers:
There is no timestamp and no replay window in v1. Recompute the HMAC over the
raw bytes and compare in constant time.
- Python
- Node.js
Rules
- Use the raw body. Sign the exact bytes received, before any JSON parsing. Re-serialising changes key order and spacing, and the digest with it.
- Constant-time compare.
hmac.compare_digest/crypto.timingSafeEqual. - Keep the private key out of the browser. It signs webhooks and authenticates API calls.
- Return
200fast. Enqueue the work; do not do it inline. - Expect duplicates. v1 events carry no event ID — dedupe on
event.type+call.id, and make handlers idempotent.