Web calls
A phone number isn’t the only way to reach an agent. With web calls, a visitor presses a button on your site and is talking to your flow over WebRTC a second later — no dial pad, no telephony charge, and a live transcript you can render next to the button. The browser SDK handles the media and signalling; you bring the UI.
This is the browser SDK. For placing phone calls and managing the account from a backend, use the server SDKs.
How it works
The key point: the browser never holds your API key. A publishable key (pk_live_…) is safe in page source. It is bound to one flow, valid only from origins you allowlist, and rate-limited per key, per visitor session and per IP. Talkif exchanges it for a short-lived session token; everything after that is scoped to that one session.
Packages
Both are headless — no UI ships with them. Source: Talkif-ai/webrtc-js (MIT).
Two modes
Public (embed)
Authenticated
For widgets on any web page. Ship the publishable key; the flow is bound to the key.
Get the key from the flow: Flow Builder → open the flow → Flow Settings → Web calls. Publish the flow first — web calls always run the published version.
Setting up a public widget
Enable web calls on the flow
Flow Settings → Web calls → Enable. A publishable key is generated and shown once; copy it. Regenerating issues a new key and invalidates the old one immediately.
Allowlist your origins
Add every origin the widget will run on (https://www.example.com, https://app.example.com). Requests from anywhere else are refused — with a response that reveals nothing about which check failed.
If the flow’s bot gate is on, the SDK completes a Cloudflare Turnstile challenge invisibly — nothing to set up. To supply your own token, pass turnstileToken: () => Promise<string> in the config.
What you can render live
Every call event arrives on the SDK instance (and as hook callbacks), so a page can show more than a spinner:
The core also handles what you’d otherwise get wrong: relay-only ICE with fast first-candidate connect, the data-channel keepalive, a reconnecting events WebSocket with server-side replay after a gap, a liveness check before tearing down a silent call, and deterministic release of the microphone and peer connection on hangup, error or unmount. One active call per hook; starting another disposes the first.
Limits that protect you
An unauthenticated endpoint that spends your money needs guardrails. These apply to every public call, in this order:
A public call is billed like any other call minus telephony — STT, LLM, TTS and infrastructure — and appears in history with providerType: webrtc.