@vanira/sdk 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +85 -0
- package/dist/api/services/ChatService.d.ts +23 -0
- package/dist/api/services/ConfigService.d.ts +5 -0
- package/dist/cdn.d.ts +1 -0
- package/dist/core/SessionManager.d.ts +78 -0
- package/dist/core/VaniraAI.d.ts +141 -0
- package/dist/core/WebRTCClient.d.ts +62 -0
- package/dist/index.d.ts +9 -0
- package/dist/types.d.ts +43 -0
- package/dist/ui/VaniraWidget.d.ts +16 -0
- package/dist/ui/abstraction/AbstractWidgetProvider.d.ts +11 -0
- package/dist/ui/abstraction/interfaces.d.ts +11 -0
- package/dist/ui/adapters/VaniraChatAdapter.d.ts +7 -0
- package/dist/ui/components/AvatarView.d.ts +8 -0
- package/dist/ui/components/ChatWindow.d.ts +32 -0
- package/dist/ui/components/FloatingButton.d.ts +17 -0
- package/dist/ui/components/FloatingWelcomeChips.d.ts +15 -0
- package/dist/ui/components/Panel.d.ts +25 -0
- package/dist/ui/components/VoiceOrb.d.ts +6 -0
- package/dist/ui/components/VoiceOverlay.d.ts +45 -0
- package/dist/ui/components/index.d.ts +7 -0
- package/dist/ui/factory/WidgetFactory.d.ts +10 -0
- package/dist/ui/icons_data.d.ts +2 -0
- package/dist/ui/providers/VaniraInternalProvider.d.ts +67 -0
- package/dist/ui/styles/index.d.ts +22 -0
- package/dist/ui/styles/keyframes.d.ts +1 -0
- package/dist/ui/styles/theme.d.ts +26 -0
- package/dist/ui/styles/widget.css.d.ts +1 -0
- package/dist/ui/views/AbstractChatView.d.ts +23 -0
- package/dist/ui/views/AbstractVoiceView.d.ts +18 -0
- package/dist/ui/views/AvatarOnlyView.d.ts +11 -0
- package/dist/ui/views/ChatAvatarView.d.ts +6 -0
- package/dist/ui/views/ChatOnlyView.d.ts +10 -0
- package/dist/ui/views/ChatVoiceView.d.ts +5 -0
- package/dist/ui/views/VoiceOnlyView.d.ts +6 -0
- package/dist/ui/views/index.d.ts +5 -0
- package/dist/vanira-sdk.es.js +1110 -0
- package/dist/vanira-sdk.js +1111 -0
- package/dist/vanira-sdk.js.map +1 -0
- package/package.json +50 -0
package/README.md
ADDED
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
# AvinAI Widget SDK
|
|
2
|
+
|
|
3
|
+
A lightweight widget SDK for integrating AvinAI voice and chat assistants into any website.
|
|
4
|
+
|
|
5
|
+
## Installation
|
|
6
|
+
|
|
7
|
+
### NPM
|
|
8
|
+
```bash
|
|
9
|
+
npm install vanira-ai
|
|
10
|
+
```
|
|
11
|
+
|
|
12
|
+
### CDN
|
|
13
|
+
```html
|
|
14
|
+
<script src="https://unpkg.com/vanira-ai@latest/dist/vanira-ai.js" widget-id="YOUR_WIDGET_ID" defer></script>
|
|
15
|
+
```
|
|
16
|
+
|
|
17
|
+
## Widget Modes
|
|
18
|
+
|
|
19
|
+
| Mode | Description |
|
|
20
|
+
|------|-------------|
|
|
21
|
+
| `voice_only` | Voice call with transcript |
|
|
22
|
+
| `chat_voice` | Chat interface with voice button |
|
|
23
|
+
| `avatar_only` | AI avatar video call |
|
|
24
|
+
| `chat_avatar` | Chat + avatar video |
|
|
25
|
+
|
|
26
|
+
## Local Development
|
|
27
|
+
|
|
28
|
+
### 1. Install dependencies
|
|
29
|
+
```bash
|
|
30
|
+
cd sdk
|
|
31
|
+
npm install
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
### 2. Build the SDK
|
|
35
|
+
```bash
|
|
36
|
+
npm run build
|
|
37
|
+
```
|
|
38
|
+
|
|
39
|
+
### 3. Test locally
|
|
40
|
+
|
|
41
|
+
Create a test HTML file:
|
|
42
|
+
|
|
43
|
+
```html
|
|
44
|
+
<!doctype html>
|
|
45
|
+
<html lang="en">
|
|
46
|
+
<head>
|
|
47
|
+
<meta charset="UTF-8">
|
|
48
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
49
|
+
<title>Widget Test</title>
|
|
50
|
+
</head>
|
|
51
|
+
<body>
|
|
52
|
+
<h1>Widget Local Test</h1>
|
|
53
|
+
<p>The widget should appear in the bottom-right corner.</p>
|
|
54
|
+
|
|
55
|
+
<!-- Load from local build -->
|
|
56
|
+
<script src="./dist/vanira-ai.js" widget-id="YOUR_WIDGET_ID" defer></script>
|
|
57
|
+
</body>
|
|
58
|
+
</html>
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
### 4. Serve the files
|
|
62
|
+
```bash
|
|
63
|
+
npx serve .
|
|
64
|
+
```
|
|
65
|
+
|
|
66
|
+
Open `http://localhost:3000/test_widget.html` in your browser.
|
|
67
|
+
|
|
68
|
+
## Publishing
|
|
69
|
+
|
|
70
|
+
```bash
|
|
71
|
+
# Bump version in package.json
|
|
72
|
+
npm version patch
|
|
73
|
+
|
|
74
|
+
# Build and publish
|
|
75
|
+
npm run build
|
|
76
|
+
npm publish --access public
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
## Configuration Attributes
|
|
80
|
+
|
|
81
|
+
| Attribute | Description |
|
|
82
|
+
|-----------|-------------|
|
|
83
|
+
| `widget-id` | Widget ID from dashboard (required) |
|
|
84
|
+
| `position` | `bottom-right`, `bottom-left`, `top-right`, `top-left` |
|
|
85
|
+
| `primary-color` | Hex color (e.g., `#6366f1`) |
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
export interface ChatMessage {
|
|
2
|
+
role: 'user' | 'assistant';
|
|
3
|
+
content: string;
|
|
4
|
+
widget?: {
|
|
5
|
+
type: 'carousel' | 'button_list';
|
|
6
|
+
data: any;
|
|
7
|
+
};
|
|
8
|
+
}
|
|
9
|
+
export declare class ChatService {
|
|
10
|
+
static setChatUrl(url: string): void;
|
|
11
|
+
static createChatProspect(prospectGroupId: string): Promise<string>;
|
|
12
|
+
static fetchWelcomeMessage(agentId: string, prospectId: string, widgetId?: string): Promise<ChatMessage & {
|
|
13
|
+
chatId?: string;
|
|
14
|
+
}>;
|
|
15
|
+
static sendChatMessage(agentId: string, prospectId: string, message: string, chatId: string | null, onChunk: (text: string) => void, onWidget: (widget: any) => void, onDone: (newChatId: string | null) => void, widgetId?: string): Promise<void>;
|
|
16
|
+
static listenForAdminReplies(inboxId: string, sender: string, onMessage: (content: string) => void): {
|
|
17
|
+
close: () => void;
|
|
18
|
+
};
|
|
19
|
+
static createCall(agentId: string, clientId: string | null, prospectId: string | null, widgetMode: string): Promise<{
|
|
20
|
+
callId: string;
|
|
21
|
+
workerUrl: string;
|
|
22
|
+
}>;
|
|
23
|
+
}
|
package/dist/cdn.d.ts
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* SessionManager
|
|
3
|
+
* ==============
|
|
4
|
+
* Manages per-tab widget sessions using:
|
|
5
|
+
* - sessionStorage → tab_id (unique per browser tab, survives refresh, gone on tab close)
|
|
6
|
+
* - localStorage → session data (prospect_id, chat_id, messages — persists across refreshes)
|
|
7
|
+
* - BroadcastChannel → real-time cross-tab communication
|
|
8
|
+
* - Heartbeat → detect dead tabs (no heartbeat for 15s → tab considered gone)
|
|
9
|
+
*
|
|
10
|
+
* Key behaviours:
|
|
11
|
+
* 1. Each tab gets a unique tab_id.
|
|
12
|
+
* 2. Only one tab is "active" at a time (owns the session).
|
|
13
|
+
* 3. When a second tab loads the widget, it detects the conflict and fires onTabConflict().
|
|
14
|
+
* 4. Chat messages, prospect_id and chat_id are persisted so a page refresh restores the session.
|
|
15
|
+
* 5. Tab closure is detected via heartbeat expiry — the next tab to init auto-claims.
|
|
16
|
+
*/
|
|
17
|
+
export interface StoredMessage {
|
|
18
|
+
role: 'user' | 'assistant';
|
|
19
|
+
content: string;
|
|
20
|
+
timestamp: number;
|
|
21
|
+
}
|
|
22
|
+
export interface SessionData {
|
|
23
|
+
tabId: string;
|
|
24
|
+
prospectId: string;
|
|
25
|
+
chatId: string | null;
|
|
26
|
+
messages: StoredMessage[];
|
|
27
|
+
lastActive: number;
|
|
28
|
+
}
|
|
29
|
+
export type SessionEvent = 'tab_conflict' | 'session_claimed' | 'session_restored' | 'tab_took_over' | 'session_cleared';
|
|
30
|
+
export declare class SessionManager {
|
|
31
|
+
private tabId;
|
|
32
|
+
private sessionKey;
|
|
33
|
+
private channelName;
|
|
34
|
+
private channel;
|
|
35
|
+
private heartbeatTimer;
|
|
36
|
+
private listeners;
|
|
37
|
+
/** How often (ms) the active tab broadcasts its heartbeat */
|
|
38
|
+
private static readonly HEARTBEAT_INTERVAL_MS;
|
|
39
|
+
/** How old (ms) a heartbeat must be before we consider the tab dead */
|
|
40
|
+
private static readonly HEARTBEAT_TIMEOUT_MS;
|
|
41
|
+
constructor(widgetId: string);
|
|
42
|
+
/** Returns this tab's unique ID (stable across same-tab page refreshes). */
|
|
43
|
+
getTabId(): string;
|
|
44
|
+
/**
|
|
45
|
+
* Try to claim the session for this tab.
|
|
46
|
+
* Returns true → session claimed (or restored after stale prior tab).
|
|
47
|
+
* Returns false → another live tab already owns the session.
|
|
48
|
+
*/
|
|
49
|
+
claimSession(): boolean;
|
|
50
|
+
/**
|
|
51
|
+
* Force-claim the session even if another tab owns it.
|
|
52
|
+
* Call this when the user explicitly clicks "Use here" in the conflict UI.
|
|
53
|
+
*/
|
|
54
|
+
forceClaimSession(): void;
|
|
55
|
+
/** Save / update the prospect and chat IDs for this session. */
|
|
56
|
+
saveIds(prospectId: string, chatId: string | null): void;
|
|
57
|
+
/** Append a message to the persisted history. */
|
|
58
|
+
pushMessage(role: 'user' | 'assistant', content: string): void;
|
|
59
|
+
/** Update the content of the last assistant message (streaming). */
|
|
60
|
+
updateLastAssistantMessage(content: string): void;
|
|
61
|
+
/** Returns the currently persisted session data (null if none). */
|
|
62
|
+
getSession(): SessionData | null;
|
|
63
|
+
/** Clears ALL session data (prospect_id, chat_id, messages). */
|
|
64
|
+
clearSession(): void;
|
|
65
|
+
/** Stop the heartbeat and release resources. Call on widget destroy. */
|
|
66
|
+
destroy(): void;
|
|
67
|
+
on(event: SessionEvent, cb: Function): this;
|
|
68
|
+
off(event: SessionEvent, cb: Function): this;
|
|
69
|
+
private _getOrCreateTabId;
|
|
70
|
+
private _setupChannel;
|
|
71
|
+
private _broadcast;
|
|
72
|
+
private _startHeartbeat;
|
|
73
|
+
private _stopHeartbeat;
|
|
74
|
+
private _loadSession;
|
|
75
|
+
private _saveSession;
|
|
76
|
+
private _blankSession;
|
|
77
|
+
private _emit;
|
|
78
|
+
}
|
|
@@ -0,0 +1,141 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* VaniraAI SDK
|
|
3
|
+
* ============
|
|
4
|
+
* A simple, developer-friendly Voice AI client.
|
|
5
|
+
* Hides all WebRTC complexity behind a clean event-emitter API.
|
|
6
|
+
*
|
|
7
|
+
* @example
|
|
8
|
+
* ```ts
|
|
9
|
+
* const client = new VaniraAI({ agentId: 'your-agent-id', token: 'Bearer your-token' });
|
|
10
|
+
* client.on('tool_call', ({ name, arguments: args, tool_call_id, execution_mode }) => {
|
|
11
|
+
* // render your UI component here
|
|
12
|
+
* if (execution_mode === 'blocking') {
|
|
13
|
+
* client.sendToolResult(tool_call_id, { success: true });
|
|
14
|
+
* }
|
|
15
|
+
* });
|
|
16
|
+
* await client.start();
|
|
17
|
+
* ```
|
|
18
|
+
*/
|
|
19
|
+
export type VaniraAIStatus = 'idle' | 'connecting' | 'connected' | 'disconnected' | 'error';
|
|
20
|
+
export interface VaniraAIConfig {
|
|
21
|
+
/** Your Vanira agent ID from the dashboard */
|
|
22
|
+
agentId: string;
|
|
23
|
+
/** Bearer token for authentication. Required for ICE server fetching. */
|
|
24
|
+
token?: string;
|
|
25
|
+
/** Override the WebRTC server URL. Auto-detected if omitted. */
|
|
26
|
+
serverUrl?: string;
|
|
27
|
+
/** Override the GraphQL endpoint for config fetching. */
|
|
28
|
+
graphqlEndpoint?: string;
|
|
29
|
+
/** Optional: pre-supply your own ICE servers (skips auto-fetch). */
|
|
30
|
+
iceServers?: RTCIceServer[];
|
|
31
|
+
/** Optional call ID override. Auto-generated if omitted. */
|
|
32
|
+
callId?: string;
|
|
33
|
+
}
|
|
34
|
+
export interface ClientToolCall {
|
|
35
|
+
/** The ref_code of the triggered action */
|
|
36
|
+
name: string;
|
|
37
|
+
/** The mapped payload from client_action_fields */
|
|
38
|
+
arguments: Record<string, any>;
|
|
39
|
+
/** Unique ID for this execution. Required when sending a result back for blocking tools. */
|
|
40
|
+
tool_call_id: string;
|
|
41
|
+
/** Whether the AI is paused waiting for result ('blocking') or keeps talking ('fire_and_forget') */
|
|
42
|
+
execution_mode: 'blocking' | 'fire_and_forget';
|
|
43
|
+
}
|
|
44
|
+
export interface TranscriptionEvent {
|
|
45
|
+
text: string;
|
|
46
|
+
isFinal: boolean;
|
|
47
|
+
}
|
|
48
|
+
type EventMap = {
|
|
49
|
+
/** Fired when WebRTC connection is fully established */
|
|
50
|
+
connected: void;
|
|
51
|
+
/** Fired when the connection is lost or explicitly disconnected */
|
|
52
|
+
disconnected: void;
|
|
53
|
+
/** Fired on connection or protocol error. Payload is an error message string. */
|
|
54
|
+
error: string;
|
|
55
|
+
/** Fired whenever the AI transcribes speech (both interim and final) */
|
|
56
|
+
transcription: TranscriptionEvent;
|
|
57
|
+
/** Fired when the AI triggers a client-side tool (action) */
|
|
58
|
+
tool_call: ClientToolCall;
|
|
59
|
+
/** Fired when a remote media track (like video) is received */
|
|
60
|
+
track: {
|
|
61
|
+
track: MediaStreamTrack;
|
|
62
|
+
stream: MediaStream;
|
|
63
|
+
};
|
|
64
|
+
};
|
|
65
|
+
type EventCallback<T> = T extends void ? () => void : (payload: T) => void;
|
|
66
|
+
export declare class VaniraAI {
|
|
67
|
+
private config;
|
|
68
|
+
private _status;
|
|
69
|
+
private client;
|
|
70
|
+
private listeners;
|
|
71
|
+
constructor(config: VaniraAIConfig);
|
|
72
|
+
/** Current connection status */
|
|
73
|
+
get status(): VaniraAIStatus;
|
|
74
|
+
/** Shorthand: true when status is 'connected' */
|
|
75
|
+
get isConnected(): boolean;
|
|
76
|
+
/**
|
|
77
|
+
* Register an event listener.
|
|
78
|
+
* @param event - Event name
|
|
79
|
+
* @param callback - Handler function
|
|
80
|
+
* @returns `this` for chaining
|
|
81
|
+
*/
|
|
82
|
+
on<K extends keyof EventMap>(event: K, callback: EventCallback<EventMap[K]>): this;
|
|
83
|
+
/**
|
|
84
|
+
* Remove a previously registered event listener.
|
|
85
|
+
* @param event - Event name
|
|
86
|
+
* @param callback - The exact same function reference that was registered
|
|
87
|
+
*/
|
|
88
|
+
off<K extends keyof EventMap>(event: K, callback: EventCallback<EventMap[K]>): this;
|
|
89
|
+
private emit;
|
|
90
|
+
/**
|
|
91
|
+
* Connect to the Voice AI agent and start the call.
|
|
92
|
+
* Requests microphone permission, establishes WebRTC, and opens the data channel.
|
|
93
|
+
*/
|
|
94
|
+
start(): Promise<void>;
|
|
95
|
+
/**
|
|
96
|
+
* Disconnect the call and release all resources (microphone, WebRTC connection).
|
|
97
|
+
*/
|
|
98
|
+
stop(): void;
|
|
99
|
+
/**
|
|
100
|
+
* Send the result of a **blocking** client-side tool back to the AI.
|
|
101
|
+
* The AI is paused and will resume once it receives this.
|
|
102
|
+
*
|
|
103
|
+
* @param toolCallId - The `tool_call_id` from the `tool_call` event
|
|
104
|
+
* @param result - Arbitrary JSON payload the AI needs to continue
|
|
105
|
+
*
|
|
106
|
+
* @example
|
|
107
|
+
* client.sendToolResult(tool_call_id, { selected_store: 'Store #5' });
|
|
108
|
+
*/
|
|
109
|
+
sendToolResult(toolCallId: string, result: Record<string, any>): void;
|
|
110
|
+
/**
|
|
111
|
+
* Send an error result for a **blocking** client-side tool.
|
|
112
|
+
* Use when the user cancelled or the UI crashed.
|
|
113
|
+
*
|
|
114
|
+
* @param toolCallId - The `tool_call_id` from the `tool_call` event
|
|
115
|
+
* @param errorMessage - Human-readable error description
|
|
116
|
+
*/
|
|
117
|
+
sendToolError(toolCallId: string, errorMessage: string): void;
|
|
118
|
+
/**
|
|
119
|
+
* Silently update the AI's context with what the user is currently doing on screen.
|
|
120
|
+
* Does NOT interrupt the AI's current speech.
|
|
121
|
+
*
|
|
122
|
+
* @example
|
|
123
|
+
* client.updateContext({ active_page: 'Checkout', item: 'Nike Shoes', price: 149.99 });
|
|
124
|
+
*/
|
|
125
|
+
updateContext(context: Record<string, any>): void;
|
|
126
|
+
/**
|
|
127
|
+
* Force the AI to stop speaking and immediately react to a UI event.
|
|
128
|
+
* Use when the user performs a significant action (e.g., clicks a button, opens a page).
|
|
129
|
+
*
|
|
130
|
+
* @param actionName - A descriptive name for the action (e.g., 'user_clicked_cart')
|
|
131
|
+
* @param data - Optional context about the action
|
|
132
|
+
*
|
|
133
|
+
* @example
|
|
134
|
+
* client.triggerInterrupt('user_opened_checkout', { cart_value: 299 });
|
|
135
|
+
*/
|
|
136
|
+
triggerInterrupt(actionName: string, data?: Record<string, any>): void;
|
|
137
|
+
private _setStatus;
|
|
138
|
+
private _inferServerUrl;
|
|
139
|
+
private _assertConnected;
|
|
140
|
+
}
|
|
141
|
+
export {};
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
import { WebRTCClientConfig } from '../types';
|
|
2
|
+
|
|
3
|
+
export declare class WebRTCClient {
|
|
4
|
+
private serverUrl;
|
|
5
|
+
private agentId;
|
|
6
|
+
private callId;
|
|
7
|
+
private onConnected;
|
|
8
|
+
private onDisconnected;
|
|
9
|
+
private onError;
|
|
10
|
+
private onTranscription;
|
|
11
|
+
private onRemoteTrack;
|
|
12
|
+
private onClientToolCall;
|
|
13
|
+
private pc;
|
|
14
|
+
private dataChannel;
|
|
15
|
+
private audioElement;
|
|
16
|
+
connected: boolean;
|
|
17
|
+
private iceServers?;
|
|
18
|
+
private token?;
|
|
19
|
+
constructor(config: WebRTCClientConfig);
|
|
20
|
+
/**
|
|
21
|
+
* Connect via HTTP signaling (no WebSocket)
|
|
22
|
+
*/
|
|
23
|
+
connect(): Promise<void>;
|
|
24
|
+
/**
|
|
25
|
+
* Wait for ICE gathering to complete
|
|
26
|
+
*/
|
|
27
|
+
private waitForIceGathering;
|
|
28
|
+
/**
|
|
29
|
+
* Send control event via DataChannel
|
|
30
|
+
*/
|
|
31
|
+
sendEvent(event: string, data?: {}): void;
|
|
32
|
+
/**
|
|
33
|
+
* Handle control events from server
|
|
34
|
+
*/
|
|
35
|
+
private handleControlEvent;
|
|
36
|
+
/**
|
|
37
|
+
* Disconnect and cleanup
|
|
38
|
+
*/
|
|
39
|
+
disconnect(): void;
|
|
40
|
+
/**
|
|
41
|
+
* Generate unique call ID
|
|
42
|
+
*/
|
|
43
|
+
generateCallId(): string;
|
|
44
|
+
/**
|
|
45
|
+
* Send client-side tool execution result back to the AI server.
|
|
46
|
+
* Use this to unblock a 'blocking' execution mode tool.
|
|
47
|
+
*/
|
|
48
|
+
sendToolResult(callId: string, result: any): void;
|
|
49
|
+
/**
|
|
50
|
+
* Silently update the AI's context with what the user is currently viewing.
|
|
51
|
+
* Does NOT interrupt the AI's current speech.
|
|
52
|
+
*/
|
|
53
|
+
sendSilentContext(context: string): void;
|
|
54
|
+
/**
|
|
55
|
+
* Trigger a client-side interrupt — cuts AI audio and forces it to react to a UI event.
|
|
56
|
+
*/
|
|
57
|
+
triggerActionInterrupt(): void;
|
|
58
|
+
/**
|
|
59
|
+
* Static helper to fetch ICE servers from Hasura
|
|
60
|
+
*/
|
|
61
|
+
static fetchIceServers(token: string, graphqlEndpoint?: string): Promise<RTCIceServer[]>;
|
|
62
|
+
}
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export { VaniraAI } from './core/VaniraAI';
|
|
2
|
+
export type { VaniraAIConfig, VaniraAIStatus, ClientToolCall, TranscriptionEvent } from './core/VaniraAI';
|
|
3
|
+
export { VaniraWidget } from './ui/VaniraWidget';
|
|
4
|
+
export { WebRTCClient } from './core/WebRTCClient';
|
|
5
|
+
export { ConfigService } from './api/services/ConfigService';
|
|
6
|
+
export { ChatService } from './api/services/ChatService';
|
|
7
|
+
export { SessionManager } from './core/SessionManager';
|
|
8
|
+
export type { SessionData, StoredMessage, SessionEvent } from './core/SessionManager';
|
|
9
|
+
export * from './types';
|
package/dist/types.d.ts
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
export interface TTSProvider {
|
|
2
|
+
root_name: string;
|
|
3
|
+
provider_country?: string;
|
|
4
|
+
}
|
|
5
|
+
export interface TTSVoice {
|
|
6
|
+
provider: TTSProvider;
|
|
7
|
+
}
|
|
8
|
+
export interface Agent {
|
|
9
|
+
tts_voice?: TTSVoice;
|
|
10
|
+
}
|
|
11
|
+
export type WidgetMode = 'voice_only' | 'chat_voice' | 'avatar_only' | 'chat_avatar' | 'chat_only';
|
|
12
|
+
export interface WidgetConfig {
|
|
13
|
+
agent_id: string;
|
|
14
|
+
client_id: string;
|
|
15
|
+
mode: WidgetMode;
|
|
16
|
+
icon?: string;
|
|
17
|
+
gradient?: string;
|
|
18
|
+
agent?: Agent;
|
|
19
|
+
client?: {
|
|
20
|
+
base_prospect_group_id?: string;
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
export interface WebRTCClientConfig {
|
|
24
|
+
serverUrl: string;
|
|
25
|
+
agentId: string;
|
|
26
|
+
callId?: string;
|
|
27
|
+
onConnected?: () => void;
|
|
28
|
+
onDisconnected?: () => void;
|
|
29
|
+
onError?: (error: any) => void;
|
|
30
|
+
onTranscription?: (text: string, isFinal: boolean) => void;
|
|
31
|
+
onRemoteTrack?: (track: MediaStreamTrack, stream: MediaStream) => void;
|
|
32
|
+
onClientToolCall?: (toolCall: any) => void;
|
|
33
|
+
iceServers?: RTCIceServer[];
|
|
34
|
+
token?: string;
|
|
35
|
+
}
|
|
36
|
+
export interface ControlEvent {
|
|
37
|
+
event: string;
|
|
38
|
+
text?: string;
|
|
39
|
+
isFinal?: boolean;
|
|
40
|
+
name?: string;
|
|
41
|
+
tool_call?: any;
|
|
42
|
+
data?: any;
|
|
43
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export declare class VaniraWidget extends HTMLElement {
|
|
2
|
+
private shadow;
|
|
3
|
+
private provider;
|
|
4
|
+
private widgetId;
|
|
5
|
+
private agentId;
|
|
6
|
+
private serverUrl;
|
|
7
|
+
private position;
|
|
8
|
+
private primaryColor;
|
|
9
|
+
private secondaryColor;
|
|
10
|
+
private gradient;
|
|
11
|
+
static get observedAttributes(): string[];
|
|
12
|
+
constructor();
|
|
13
|
+
connectedCallback(): void;
|
|
14
|
+
private readAttributes;
|
|
15
|
+
initializeExpandedConfig(): Promise<void>;
|
|
16
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { IWidgetProvider } from './interfaces';
|
|
2
|
+
|
|
3
|
+
export declare abstract class AbstractWidgetProvider implements IWidgetProvider {
|
|
4
|
+
protected config: any;
|
|
5
|
+
protected root: ShadowRoot | null;
|
|
6
|
+
constructor(config: any);
|
|
7
|
+
abstract create_call(): Promise<void>;
|
|
8
|
+
abstract end_call(): void;
|
|
9
|
+
abstract ui_renderer(root: ShadowRoot): void;
|
|
10
|
+
initialize(config: any): Promise<void>;
|
|
11
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export interface IChatAdapter {
|
|
2
|
+
sendMessage(text: string, agentId: string, prospectId: string, chatId: string | null, onResponse: (response: any) => void, onStream?: (text: string) => void): Promise<void>;
|
|
3
|
+
sendFile?(file: File): Promise<void>;
|
|
4
|
+
likeDislike?(messageId: string, action: 'like' | 'dislike'): Promise<void>;
|
|
5
|
+
}
|
|
6
|
+
export interface IWidgetProvider {
|
|
7
|
+
create_call(): Promise<void>;
|
|
8
|
+
end_call(): void;
|
|
9
|
+
ui_renderer(root: ShadowRoot): void;
|
|
10
|
+
initialize(config: any): Promise<void>;
|
|
11
|
+
}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { IChatAdapter } from '../abstraction/interfaces';
|
|
2
|
+
|
|
3
|
+
export declare class VaniraChatAdapter implements IChatAdapter {
|
|
4
|
+
sendMessage(text: string, agentId: string, prospectId: string, chatId: string | null, onResponse: (response: any) => void, onStream?: (text: string) => void, onChatIdUpdate?: (newId: string) => void, widgetId?: string): Promise<void>;
|
|
5
|
+
sendFile(file: File): Promise<void>;
|
|
6
|
+
likeDislike(messageId: string, action: 'like' | 'dislike'): Promise<void>;
|
|
7
|
+
}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
export interface ChatMessage {
|
|
2
|
+
role: 'user' | 'assistant';
|
|
3
|
+
content: string;
|
|
4
|
+
}
|
|
5
|
+
export declare class ChatWindow {
|
|
6
|
+
private onSend;
|
|
7
|
+
private element;
|
|
8
|
+
private messageContainer;
|
|
9
|
+
private inputArea;
|
|
10
|
+
private input;
|
|
11
|
+
private sendBtn;
|
|
12
|
+
private typingIndicator;
|
|
13
|
+
constructor(onSend: (message: string) => void);
|
|
14
|
+
getElement(): HTMLDivElement;
|
|
15
|
+
private formatTime;
|
|
16
|
+
addMessage(role: 'user' | 'assistant', content: string, timestamp?: number): void;
|
|
17
|
+
updateLastAssistantMessage(content: string): void;
|
|
18
|
+
addButtons(buttons: Array<{
|
|
19
|
+
title: string;
|
|
20
|
+
payload: string;
|
|
21
|
+
}>): void;
|
|
22
|
+
private handleSend;
|
|
23
|
+
setTyping(isTyping: boolean): void;
|
|
24
|
+
/**
|
|
25
|
+
* Inject a "Voice call ended" card into the message list.
|
|
26
|
+
* @param durationMs call duration in milliseconds
|
|
27
|
+
* @param timestamp unix ms when the call started (for ordering across restore)
|
|
28
|
+
*/
|
|
29
|
+
addCallRecord(durationMs: number, timestamp?: number): void;
|
|
30
|
+
clearMessages(): void;
|
|
31
|
+
private scrollToBottom;
|
|
32
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export declare class FloatingButton {
|
|
2
|
+
private onClick;
|
|
3
|
+
private element;
|
|
4
|
+
private iconContainer;
|
|
5
|
+
private isDragging;
|
|
6
|
+
private startX;
|
|
7
|
+
private startY;
|
|
8
|
+
private currentX;
|
|
9
|
+
private currentY;
|
|
10
|
+
private hasMoved;
|
|
11
|
+
constructor(onClick: () => void, initialIcon?: string);
|
|
12
|
+
private dragStart;
|
|
13
|
+
getElement(): HTMLButtonElement;
|
|
14
|
+
setIcon(iconHtml: string): void;
|
|
15
|
+
setPosition(positionStyle: string): void;
|
|
16
|
+
static get styles(): string;
|
|
17
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
export interface WelcomeChip {
|
|
2
|
+
title: string;
|
|
3
|
+
payload?: string;
|
|
4
|
+
}
|
|
5
|
+
export declare class FloatingWelcomeChips {
|
|
6
|
+
private onChipClick;
|
|
7
|
+
private element;
|
|
8
|
+
private chips;
|
|
9
|
+
constructor(onChipClick: (text: string) => void);
|
|
10
|
+
setChips(chips: WelcomeChip[]): void;
|
|
11
|
+
getElement(): HTMLElement;
|
|
12
|
+
setPosition(positionStyle: string): void;
|
|
13
|
+
private render;
|
|
14
|
+
static get styles(): string;
|
|
15
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
export declare class Panel {
|
|
2
|
+
private onClose;
|
|
3
|
+
private title;
|
|
4
|
+
private element;
|
|
5
|
+
private header;
|
|
6
|
+
private titleElement;
|
|
7
|
+
private contentArea;
|
|
8
|
+
private maximizeBtn;
|
|
9
|
+
private closeBtn;
|
|
10
|
+
private isMaximized;
|
|
11
|
+
constructor(onClose: () => void, title?: string);
|
|
12
|
+
getElement(): HTMLDivElement;
|
|
13
|
+
setContent(content: HTMLElement): void;
|
|
14
|
+
addToContent(element: HTMLElement): void;
|
|
15
|
+
setTitle(title: string): void;
|
|
16
|
+
open(position: {
|
|
17
|
+
bottom?: string;
|
|
18
|
+
right?: string;
|
|
19
|
+
top?: string;
|
|
20
|
+
left?: string;
|
|
21
|
+
}): void;
|
|
22
|
+
close(): void;
|
|
23
|
+
toggleMaximize(): void;
|
|
24
|
+
static get styles(): string;
|
|
25
|
+
}
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
export declare class VoiceOverlay {
|
|
2
|
+
private onHangup;
|
|
3
|
+
private primaryColor;
|
|
4
|
+
private secondaryColor;
|
|
5
|
+
private onCallEnded?;
|
|
6
|
+
private element;
|
|
7
|
+
private contentContainer;
|
|
8
|
+
private orbWrapper;
|
|
9
|
+
private connectingRing;
|
|
10
|
+
private errorRing;
|
|
11
|
+
private waveLayers;
|
|
12
|
+
private outerGlow;
|
|
13
|
+
private wave1;
|
|
14
|
+
private wave2;
|
|
15
|
+
private wave3;
|
|
16
|
+
private centerIcon;
|
|
17
|
+
private statusArea;
|
|
18
|
+
private connectingLabel;
|
|
19
|
+
private connectedBadge;
|
|
20
|
+
private errorLabel;
|
|
21
|
+
private retryBtn;
|
|
22
|
+
private timerEl;
|
|
23
|
+
private transcriptionEl;
|
|
24
|
+
private hangupBtn;
|
|
25
|
+
private videoContainer;
|
|
26
|
+
private videoElement;
|
|
27
|
+
private prepareBadge;
|
|
28
|
+
private statusBadge;
|
|
29
|
+
private startTime;
|
|
30
|
+
private timerInterval;
|
|
31
|
+
private isAvatarMode;
|
|
32
|
+
private callStartedAt;
|
|
33
|
+
constructor(onHangup: () => void, primaryColor?: string, secondaryColor?: string, onCallEnded?: ((durationMs: number, startedAt: number) => void) | undefined);
|
|
34
|
+
getElement(): HTMLDivElement;
|
|
35
|
+
setMode(mode: 'voice' | 'avatar'): void;
|
|
36
|
+
setVideoTrack(track: MediaStreamTrack): void;
|
|
37
|
+
setStatus(status: 'connecting' | 'connected' | 'disconnected' | 'error'): void;
|
|
38
|
+
setTranscription(text: string, isFinal: boolean): void;
|
|
39
|
+
show(): void;
|
|
40
|
+
hide(): void;
|
|
41
|
+
reset(): void;
|
|
42
|
+
private startTimer;
|
|
43
|
+
private stopTimer;
|
|
44
|
+
setFullScreen(enable: boolean): void;
|
|
45
|
+
}
|