npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@equos/react

v3.1.13

Published

React components for building real-time AI avatar conversations with [Equos](https://equos.ai).

Readme

@equos/react

React components for building real-time AI avatar conversations with Equos.

Provides a full conversation UI out of the box -- character video, media toggles, screenshare, hangup -- or lets you compose individual components for a custom layout.

Installation

npm install @equos/react @equos/browser-sdk @equos/core lucide-react react

Import the styles in your app entry:

import '@equos/react/dist/styles.css';

Quick Start

import {
  EquosConversationRenderer,
} from '@equos/react';

function App({ conversation, accessToken, onHangUp }) {
  return (
    <EquosConversationRenderer
      conversation={conversation}
      accessToken={accessToken}
      allowMic
      allowCamera
      allowScreenshare
      allowHangUp
      onHangUp={onHangUp}
    />
  );
}

conversation is an EquosConversationWithCharacter object and accessToken is the consumer access token -- both returned by the Equos API when starting a conversation (via @equos/core or @equos/node-sdk).

Creating a conversation with @equos/node-sdk

Important: @equos/node-sdk is a server-side only package. It requires an API key that must never be exposed to the browser. Use it from a backend (Node.js, Next.js API routes, etc.) and pass the conversation and consumerAccessToken to your frontend.

// Server-side only (e.g. Next.js API route, Express handler)
import { EquosClient } from '@equos/node-sdk';

const client = EquosClient.create(process.env.EQUOS_API_KEY, {
  endpoint: 'https://api.equos.ai',
});

const response = await client.conversations.startConversation({
  createEquosConversationRequest: {
    name: 'my-session',
    characterId: CHARACTER_ID,
    consumer: { name: 'User', identity: 'user-1' },
  },
});

// Send these to the client
const { conversation, consumerAccessToken } = response;

Components

EquosConversationRenderer

The main integration component. Orchestrates all media controls, character video, and user video tiles.

<EquosConversationRenderer
  conversation={conversation}
  accessToken={accessToken}
  allowMic={true}
  allowCamera={true}
  allowScreenshare={false}
  allowHangUp={true}
  className="fixed inset-0"
  characterVideoClassName="rounded-2xl"
  locale={EquosLocale.EN}
  onHangUp={() => { /* stop conversation */ }}
/>

| Prop | Type | Default | Description | |------|------|---------|-------------| | conversation | EquosConversationWithCharacter \| null | -- | Conversation object from the API | | accessToken | string \| null | -- | Consumer access token | | allowMic | boolean | true | Show mic toggle | | allowCamera | boolean | true | Show camera toggle | | allowScreenshare | boolean | false | Show screenshare toggle | | allowHangUp | boolean | true | Show hangup button | | className | string | -- | Container class | | characterVideoClassName | string | -- | Character video tile class | | locale | EquosLocale | EN | UI language | | onHangUp | () => void \| Promise<void> | -- | Called when hang up is triggered |

Renders a bottom toolbar with controls (mic, hangup, camera/screenshare) and overlays draggable camera and screenshare preview tiles when enabled.


EquosCharacterTile

Displays the AI character's video with connection status and remaining time.

<EquosCharacterTile
  name="Tommy"
  startedAt={conversation.startedAt}
  maxSeconds={300}
  locale={EquosLocale.EN}
  recoveryTimeInSeconds={3}
  showTimeLeft
  onShouldLeave={handleHangUp}
/>

| Prop | Type | Default | Description | |------|------|---------|-------------| | name | string | -- | Character display name | | startedAt | Date | -- | Conversation start time | | maxSeconds | number | -- | Max duration in seconds | | locale | EquosLocale | EN | Language for status messages | | recoveryTimeInSeconds | number | 3 | Grace period before auto-leave when agent disconnects | | showTimeLeft | boolean | true | Show remaining time badge | | onShouldLeave | () => void \| Promise<void> | -- | Called when the conversation should end (agent not joining, agent left) | | className | string | -- | Container class |

Shows localized status messages: "joining...", "having trouble joining", and a countdown before auto-ending if the agent doesn't connect within 20 seconds.

Must be used inside an EquosConversationProvider.


EquosVideoTile

Local user video preview tile (camera or screenshare) with expand/collapse.

<EquosVideoTile source="camera" />
<EquosVideoTile source="screenshare" stream={screenshareStream} />

| Prop | Type | Default | Description | |------|------|---------|-------------| | source | 'camera' \| 'screenshare' | 'camera' | Video source type | | stream | MediaStream \| null | -- | External stream (required for screenshare) | | className | string | -- | Container class |

For camera source, automatically acquires a getUserMedia stream. For screenshare, expects a stream passed via props (managed by EquosScreenshareToggle).


EquosMicToggle

Microphone toggle button.

<EquosMicToggle onToggle={(enabled) => console.log(enabled)} />

| Prop | Type | Default | Description | |------|------|---------|-------------| | onToggle | (enabled: boolean) => void | -- | Called when state changes | | className | string | -- | Button class |

Defaults to enabled. Must be used inside an EquosConversationProvider.


EquosCameraToggle

Camera toggle button.

<EquosCameraToggle onToggle={(enabled) => console.log(enabled)} />

| Prop | Type | Default | Description | |------|------|---------|-------------| | onToggle | (enabled: boolean) => void | -- | Called when state changes | | className | string | -- | Button class |

Defaults to disabled. Must be used inside an EquosConversationProvider.


EquosScreenshareToggle

Screenshare toggle button. Manages the display media stream internally.

<EquosScreenshareToggle
  onToggle={(enabled, stream) => {
    setScreenshareEnabled(enabled);
    setScreenshareStream(stream);
  }}
/>

| Prop | Type | Default | Description | |------|------|---------|-------------| | onToggle | (enabled: boolean, stream: MediaStream \| null) => void | -- | Called with state and stream | | className | string | -- | Button class |

Calls getDisplayMedia() when enabled. Automatically detects when the user stops sharing via the browser's native "Stop sharing" UI and syncs the toggle state back.


EquosHangupButton

Red hangup button with loading spinner.

<EquosHangupButton onHangup={handleHangUp} loading={isHangingUp} />

| Prop | Type | Default | Description | |------|------|---------|-------------| | onHangup | () => void \| Promise<void> | -- | Called on click | | loading | boolean | false | Shows spinner instead of icon | | className | string | -- | Button class |


EquosLogo

Equos branding logo.

<EquosLogo className="size-16 rounded-xl" animate link />

| Prop | Type | Default | Description | |------|------|---------|-------------| | className | string | -- | Image/link class | | animate | boolean | false | Enable pulse animation | | link | boolean | true | Wrap in link to equos.ai |

Hooks

useEquosConversation

Access the conversation instance and connection state from any component inside an EquosConversationProvider.

const { conversation, connectionState, agentConnected } = useEquosConversation();

Returns:

| Field | Type | Description | |-------|------|-------------| | conversation | EquosConversation \| null | SDK conversation instance | | connectionState | EquosConnectionStateType | 'disconnected' \| 'connecting' \| 'connected' \| 'reconnecting' | | agentConnected | boolean | Whether the AI agent has joined |

EquosConversationProvider

Context provider that creates and manages the EquosConversation lifecycle.

<EquosConversationProvider
  config={{ wsUrl, token, agentIdentity }}
  autoPublishMic={true}
>
  {children}
</EquosConversationProvider>

| Prop | Type | Default | Description | |------|------|---------|-------------| | config | EquosConversationConfig | -- | { wsUrl, token, agentIdentity? } | | autoPublishMic | boolean | -- | Auto-enable mic on connect | | mode | EquosModeType | -- | 'text' \| 'audio' \| 'video' | | children | ReactNode | -- | Child components |

Connects on mount, disconnects on cleanup. Re-creates the connection when wsUrl, token, or agentIdentity change.

Utilities

cn

Tailwind CSS class name merger (wraps clsx + tailwind-merge).

import { cn } from '@equos/react';

cn('p-4 bg-red-500', condition && 'bg-blue-500', className);

EquosLocale

Enum of supported locales for UI text.

import { EquosLocale } from '@equos/react';

// EN, FR, ES, DE, IT, PT, NL, RU, ZH, JA, KO, AR, HI

CopyUtils

Static class providing localized UI strings.

import { CopyUtils, EquosLocale } from '@equos/react';

CopyUtils.joiningCopy(EquosLocale.FR, 'Tommy');
// "Tommy se connecte..."

CopyUtils.timeLeftCopy(EquosLocale.EN, 120);
// "02m00s left"

| Method | Description | |--------|-------------| | talkToCopy(locale, name?) | "Chat with [name]" | | availableNowCopy(locale) | "Available" | | timeLeftCopy(locale, seconds) | Formatted remaining time | | joiningCopy(locale, name) | "[name] is joining..." | | notJoiningCopy(locale, name) | "[name] is having trouble joining" | | endingConversationCopy(locale, countdown) | "Auto ending in Ns..." | | failedToHangupCopy(locale) | "We failed to hang up" |

Custom Layouts

For full control, use individual components with the provider:

import {
  EquosConversationProvider,
  useEquosConversation,
  EquosCharacterTile,
  EquosMicToggle,
  EquosHangupButton,
} from '@equos/react';

function CustomConversation({ conversation, accessToken, onHangUp }) {
  return (
    <EquosConversationProvider
      config={{
        wsUrl: conversation.serverUrl,
        token: accessToken,
        agentIdentity: conversation.character.livekitIdentity,
      }}
      autoPublishMic
    >
      <div className="flex flex-col h-screen">
        <EquosCharacterTile
          name={conversation.character.name}
          startedAt={conversation.startedAt}
          maxSeconds={conversation.maxSeconds}
          onShouldLeave={onHangUp}
        />
        <div className="flex gap-2 p-4 justify-center">
          <EquosMicToggle onToggle={() => {}} />
          <EquosHangupButton onHangup={onHangUp} />
        </div>
      </div>
    </EquosConversationProvider>
  );
}

Equos SDKs

| SDK | Platform | Package | |-----|----------|---------| | @equos/browser-sdk | Browser (vanilla JS/TS) | npm | | @equos/react | Browser (React) | npm | | @equos/node-sdk | Node.js (server-side only) | npm | | equos | Python (server-side only) | PyPI |

Reach Us

Documentation

Authors