Skip to content

Widget ​

One <script> tag, a floating button, a modal or an inline panel (§61).

Not published yet

@callagent/web-sdk is private: true, so neither the npm package nor the cdn.callagent.dev bundle referenced below is published. The script tag is the shape the widget will ship with; today it is built from a checkout (pnpm --filter @callagent/web-sdk build produces dist/widget.global.js) and served yourself. The widget also depends on the same unimplemented POST /api/v1/client/calls route as the Web SDK, so it cannot start a call against a real control plane yet.

html
<script
  src="https://cdn.callagent.dev/widget.js"
  data-public-key="ca_pk_…"
  data-assistant-id="01J…"
  data-mode="voice"
  data-theme="auto"
  data-accent="#4f46e5"
  data-position="bottom-right"
  data-locale="en"
  data-greeting="Hi! Ask me anything about your order."></script>

17.38 KB gzipped (15.39 KB brotli), no framework runtime, no jQuery, no global CSS.

Attributes ​

AttributeValuesDefault
data-public-keyca_pk_…required (or data-token)
data-tokena JWT your backend minted—
data-assistant-idassistant ULID—
data-api-urlcontrol-plane originhttps://api.callagent.dev
data-modevoice, chat, voice+chatvoice
data-themelight, dark, autoauto
data-accentany CSS colour#4f46e5
data-positionbottom-right, bottom-left, top-right, top-leftbottom-right
data-variantfloating, inlinefloating
data-targetselector, required for inline—
data-localeen, ro, fr, debrowser language
data-greetingtext shown before the call starts—
data-variables / data-metadataJSON objects—
data-auto-opentrue / falsefalse
data-brandingfalse hides the attributiontrue
data-z-indexinteger2147483000
data-autofalse to mount from JavaScript insteadtrue

A malformed JSON attribute is ignored rather than preventing the widget from mounting.

From JavaScript ​

html
<script src="https://cdn.callagent.dev/widget.js" data-auto="false"></script>
<script>
  const widget = CallAgentWidget.mount({
    publicKey: 'ca_pk_…',
    assistantId: '01J…',
    variant: 'inline',
    target: '#assistant',
    strings: { launcherLabel: 'Call the vet' },   // override any built-in string
  });

  widget.open();
  widget.close();
  widget.destroy();
</script>

widget.client is the underlying CallAgent, so client-side tools are registered on it exactly as in the SDK.

Isolation ​

Everything renders in a Shadow DOM with all: initial on :host. Nothing the widget defines can reach the host page, and nothing on the host page — a Tailwind preflight, an aggressive reset — can reach in. The widget adds exactly one element to document.body and zero stylesheets to the document.

Accessibility ​

  • The launcher and every control are keyboard reachable, with a visible focus ring.
  • The panel is role="dialog" aria-modal="true" with an accessible name, and traps Tab; Escape closes it and returns focus to the launcher.
  • The transcript is role="log" aria-live="polite". Interim results reuse one element rather than appending each revision, so a screen reader is not read the same sentence five times.
  • prefers-reduced-motion: reduce disables the entrance animation, the pulse and smooth scrolling.
  • Host-supplied strings are escaped, not injected as markup.

Localization ​

en, ro, fr and de ship in the bundle; a regional tag falls back to its base language and then to English. Any string can be overridden through strings, so a customer can ship their own language without waiting for a release.

Demo ​

bash
pnpm --filter @callagent/web-sdk build
pnpm --filter @callagent/web-sdk demo

apps/web-sdk/demo/index.html mounts both variants, exposes every option as a control and registers a demo client-side tool.

Documented against the code. Anything not yet implemented is labelled, never described as working.