Skip to main content
Version: next

Installation

Install

npm install @monoverse/voicebot-react

react and react-dom are peer dependencies (17, 18, or 19).

Render the widget

Render <VoiceBotWidget> once, near the root of your app. It renders nothing visible itself — the widget UI is mounted by the deployed bundle it loads into its own Shadow DOM host, so it never collides with your page's styles.

import { VoiceBotWidget } from '@monoverse/voicebot-react';

export function App() {
return (
<>
<YourApp />
<VoiceBotWidget publicKey="pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" />
</>
);
}

The widget core is a one-per-page singleton: rendering it more than once (or re-rendering across SPA route changes and React StrictMode) never injects a second script or opens a second WebSocket/microphone.

Voice or chat

<VoiceBotWidget publicKey="pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" variant="voice" />

variant="voice" (the default) loads widget-voice.js.

Props

PropTypeDefaultDescription
publicKeystring (required)Your pk_ publishable key.
variant'voice' | 'chat''voice'Which widget bundle to load.
langstringForce the widget UI language (e.g. 'uk', 'en'). Omit to let the backend pick.
scriptSrcstringhttps://api.monoverse.tech/widgetOverride the CDN base (self-hosted API).
onError(error: Error) => voidCalled on script load failure or an empty key.
onNavigate(target: VoiceBotNavTarget) => voidCalled on any bot navigation. Route it through your SPA router so the live session survives.
onActionVoiceBotActionHandlersCart / variant / filter handlers — the acting tier. See Capabilities & host actions.
capabilitiesVoiceBotCapability[]Narrow the server-granted capability set for the current page (narrow-only; never widens it).
toolHandlersVoiceBotToolHandlersLow-level override for canonical action names. Most apps use onAction instead.

The last three (onAction, capabilities, toolHandlers) and onNavigate are the acting tier — they let the bot add to cart, pick a variant, filter, and navigate. See Capabilities & host actions and Custom site integration.

Hook (imperative)

import { useVoiceBot } from '@monoverse/voicebot-react';

function WidgetMount() {
useVoiceBot({ publicKey: 'pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx', variant: 'chat' });
return null;
}

Reactivity

The React wrapper re-injects — it tears the instance down, then re-mounts — when publicKey, variant, or scriptSrc change, so you can swap the key or switch voice/chat at runtime without a manual remount. onError is deliberately not a dependency: an inline callback has a new identity every render and must never drive a re-inject.

This is the one behavioural difference from the other wrappers: Vue and Next.js are one-shot (they read props at mount). If you want full re-init on a prop change, this React package is the one to reach for.

Next.js

The component is SSR-safe — it injects the script in an effect and renders null on the server, so it works in both the App Router and the Pages Router. In the App Router, mark the host as a client boundary and render once in the root layout:

'use client';
import { VoiceBotWidget } from '@monoverse/voicebot-react';

export function VoiceBot() {
return <VoiceBotWidget publicKey="pk_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx" />;
}

You can also use Next's own next/script directly without this package — this package exists so you do not have to.

The package source, props table, and changelog live in the package README on npm.