@humeai/voice-embed 0.0.0-beta.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/dist/index.js ADDED
@@ -0,0 +1,334 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/index.ts
21
+ var src_exports = {};
22
+ __export(src_exports, {
23
+ COLLAPSE_WIDGET_ACTION: () => COLLAPSE_WIDGET_ACTION,
24
+ EXPAND_WIDGET_ACTION: () => EXPAND_WIDGET_ACTION,
25
+ EmbeddedVoice: () => EmbeddedVoice,
26
+ LanguageModelOption: () => import_voice3.LanguageModelOption,
27
+ MINIMIZE_WIDGET_ACTION: () => MINIMIZE_WIDGET_ACTION,
28
+ RESIZE_FRAME_ACTION: () => RESIZE_FRAME_ACTION,
29
+ TRANSCRIPT_MESSAGE_ACTION: () => TRANSCRIPT_MESSAGE_ACTION,
30
+ WIDGET_IFRAME_IS_READY_ACTION: () => WIDGET_IFRAME_IS_READY_ACTION,
31
+ parseClientToFrameAction: () => parseClientToFrameAction
32
+ });
33
+ module.exports = __toCommonJS(src_exports);
34
+
35
+ // src/lib/embed.ts
36
+ var import_voice2 = require("@humeai/voice");
37
+
38
+ // src/lib/embed-messages.ts
39
+ var import_voice = require("@humeai/voice");
40
+ var import_zod = require("zod");
41
+ var WindowDimensionsSchema = import_zod.z.object({
42
+ width: import_zod.z.number(),
43
+ height: import_zod.z.number()
44
+ });
45
+ var ClientToFrameActionSchema = import_zod.z.union([
46
+ import_zod.z.object({
47
+ type: import_zod.z.literal("update_config"),
48
+ payload: import_voice.ConfigSchema
49
+ }),
50
+ import_zod.z.object({
51
+ type: import_zod.z.literal("cancel")
52
+ }),
53
+ import_zod.z.object({
54
+ type: import_zod.z.literal("expand_widget_from_client"),
55
+ payload: WindowDimensionsSchema
56
+ }),
57
+ import_zod.z.object({
58
+ type: import_zod.z.literal("send_window_size"),
59
+ payload: WindowDimensionsSchema
60
+ })
61
+ ]);
62
+ var UPDATE_CONFIG_ACTION = (config) => ({
63
+ type: "update_config",
64
+ payload: config
65
+ });
66
+ var EXPAND_FROM_CLIENT_ACTION = (dimensions) => ({
67
+ type: "expand_widget_from_client",
68
+ payload: dimensions
69
+ });
70
+ var SEND_WINDOW_SIZE_ACTION = (dimensions) => ({
71
+ type: "send_window_size",
72
+ payload: dimensions
73
+ });
74
+ var parseClientToFrameAction = (data) => {
75
+ return new Promise((resolve, reject) => {
76
+ try {
77
+ const value = ClientToFrameActionSchema.parse(data);
78
+ resolve(value);
79
+ } catch (error) {
80
+ reject(error);
81
+ }
82
+ });
83
+ };
84
+ var FrameToClientActionSchema = import_zod.z.union([
85
+ import_zod.z.object({
86
+ type: import_zod.z.literal("expand_widget")
87
+ }),
88
+ import_zod.z.object({
89
+ type: import_zod.z.literal("collapse_widget")
90
+ }),
91
+ import_zod.z.object({
92
+ type: import_zod.z.literal("minimize_widget")
93
+ }),
94
+ import_zod.z.object({
95
+ type: import_zod.z.literal("widget_iframe_is_ready")
96
+ }),
97
+ import_zod.z.object({
98
+ type: import_zod.z.literal("transcript_message"),
99
+ payload: import_zod.z.union([
100
+ import_voice.UserTranscriptMessageSchema,
101
+ import_voice.AgentTranscriptMessageSchema
102
+ ])
103
+ }),
104
+ import_zod.z.object({
105
+ type: import_zod.z.literal("resize_frame"),
106
+ payload: import_zod.z.object({
107
+ width: import_zod.z.number(),
108
+ height: import_zod.z.number()
109
+ })
110
+ })
111
+ ]);
112
+ var EXPAND_WIDGET_ACTION = {
113
+ type: "expand_widget"
114
+ };
115
+ var COLLAPSE_WIDGET_ACTION = {
116
+ type: "collapse_widget"
117
+ };
118
+ var MINIMIZE_WIDGET_ACTION = {
119
+ type: "minimize_widget"
120
+ };
121
+ var WIDGET_IFRAME_IS_READY_ACTION = {
122
+ type: "widget_iframe_is_ready"
123
+ };
124
+ var TRANSCRIPT_MESSAGE_ACTION = (message) => {
125
+ return {
126
+ type: "transcript_message",
127
+ payload: message
128
+ };
129
+ };
130
+ var RESIZE_FRAME_ACTION = (dimensions) => {
131
+ return {
132
+ type: "resize_frame",
133
+ payload: {
134
+ width: dimensions.width,
135
+ height: dimensions.height
136
+ }
137
+ };
138
+ };
139
+
140
+ // src/lib/embed.ts
141
+ var EmbeddedVoice = class _EmbeddedVoice {
142
+ iframe;
143
+ isMounted = false;
144
+ managedContainer = null;
145
+ config;
146
+ onMessage;
147
+ onClose;
148
+ constructor({
149
+ onMessage = () => {
150
+ },
151
+ onClose = () => {
152
+ },
153
+ ...config
154
+ }) {
155
+ this.config = config;
156
+ this.iframe = this.createIframe(config);
157
+ this.onMessage = onMessage;
158
+ this.onClose = onClose;
159
+ this.messageHandler = this.messageHandler.bind(this);
160
+ }
161
+ static create({
162
+ rendererUrl,
163
+ onMessage,
164
+ onClose,
165
+ ...config
166
+ }) {
167
+ const parsedConfig = (0, import_voice2.createConfig)(config);
168
+ return new _EmbeddedVoice({
169
+ rendererUrl: rendererUrl ?? "https://voice-widget.hume.ai",
170
+ onMessage,
171
+ onClose,
172
+ ...parsedConfig
173
+ });
174
+ }
175
+ mount(container) {
176
+ const messageHandler = (event) => {
177
+ this.messageHandler(event);
178
+ };
179
+ const resizeHandler = () => {
180
+ this.sendWindowSize();
181
+ };
182
+ const el = container ?? this.createContainer();
183
+ this.managedContainer = el;
184
+ try {
185
+ window.addEventListener("message", messageHandler);
186
+ window.addEventListener("resize", resizeHandler);
187
+ el.appendChild(this.iframe);
188
+ this.isMounted = true;
189
+ } catch (e) {
190
+ this.isMounted = false;
191
+ }
192
+ const unmount = () => {
193
+ try {
194
+ window.removeEventListener("message", messageHandler);
195
+ window.removeEventListener("resize", resizeHandler);
196
+ this.iframe.remove();
197
+ this.isMounted = false;
198
+ } catch (e) {
199
+ this.isMounted = true;
200
+ }
201
+ if (!container) {
202
+ el.remove();
203
+ }
204
+ };
205
+ return unmount;
206
+ }
207
+ createContainer() {
208
+ const div = document.createElement("div");
209
+ Object.assign(div.style, {
210
+ background: "transparent",
211
+ position: "fixed",
212
+ bottom: "0",
213
+ right: "0",
214
+ padding: "24px",
215
+ zIndex: "999999",
216
+ fontSize: "0px",
217
+ pointerEvents: "none"
218
+ });
219
+ div.id = "hume-embedded-voice-container";
220
+ document.body.appendChild(div);
221
+ return div;
222
+ }
223
+ createIframe({ rendererUrl }) {
224
+ const el = document.createElement("iframe");
225
+ Object.assign(el.style, {
226
+ backgroundColor: "transparent",
227
+ backgroundImage: "none",
228
+ border: "none",
229
+ height: "0px",
230
+ width: "0px",
231
+ opacity: "0"
232
+ });
233
+ el.id = "hume-embedded-voice";
234
+ el.src = `${rendererUrl}`;
235
+ el.setAttribute("frameborder", "0");
236
+ el.setAttribute("allowtransparency", "true");
237
+ el.setAttribute("scrolling", "no");
238
+ el.setAttribute("allow", "microphone");
239
+ if (el.contentWindow) {
240
+ el.contentWindow.document.documentElement.style.backgroundColor = "transparent";
241
+ el.contentWindow.document.body.style.backgroundColor = "transparent";
242
+ }
243
+ return el;
244
+ }
245
+ messageHandler(event) {
246
+ if (!this.iframe) {
247
+ return;
248
+ }
249
+ if (event.origin !== new URL(this.iframe.src).origin) {
250
+ return;
251
+ }
252
+ const action = FrameToClientActionSchema.safeParse(event.data);
253
+ if (!action.success) {
254
+ return;
255
+ }
256
+ switch (action.data.type) {
257
+ case WIDGET_IFRAME_IS_READY_ACTION.type: {
258
+ this.showIframe();
259
+ this.sendConfigObject();
260
+ this.sendWindowSize();
261
+ break;
262
+ }
263
+ case "resize_frame": {
264
+ this.resizeIframe(action.data.payload);
265
+ break;
266
+ }
267
+ case "transcript_message": {
268
+ this.onMessage(action.data.payload);
269
+ break;
270
+ }
271
+ case "collapse_widget": {
272
+ this.onClose();
273
+ break;
274
+ }
275
+ }
276
+ }
277
+ openEmbed() {
278
+ const action = EXPAND_FROM_CLIENT_ACTION({
279
+ width: window.document.body.clientWidth,
280
+ height: window.document.body.clientHeight
281
+ });
282
+ this.sendMessageToFrame(action);
283
+ }
284
+ sendConfigObject() {
285
+ const action = UPDATE_CONFIG_ACTION(this.config);
286
+ this.sendMessageToFrame(action);
287
+ }
288
+ sendWindowSize() {
289
+ const action = SEND_WINDOW_SIZE_ACTION({
290
+ width: window.document.body.clientWidth,
291
+ height: window.document.body.clientHeight
292
+ });
293
+ this.sendMessageToFrame(action);
294
+ }
295
+ sendMessageToFrame(action) {
296
+ const frame = this.iframe;
297
+ if (!frame.contentWindow) {
298
+ return;
299
+ }
300
+ frame.contentWindow.postMessage(action, new URL(frame.src).origin);
301
+ }
302
+ showIframe() {
303
+ this.iframe.style.opacity = "1";
304
+ if (this.managedContainer) {
305
+ this.managedContainer.style.pointerEvents = "all";
306
+ }
307
+ }
308
+ hideIframe() {
309
+ this.iframe.style.opacity = "0";
310
+ if (this.managedContainer) {
311
+ this.managedContainer.style.pointerEvents = "none";
312
+ }
313
+ }
314
+ resizeIframe({ width, height }) {
315
+ this.iframe.style.width = `${width}px`;
316
+ this.iframe.style.height = `${height}px`;
317
+ }
318
+ };
319
+
320
+ // src/index.ts
321
+ var import_voice3 = require("@humeai/voice");
322
+ // Annotate the CommonJS export names for ESM import in node:
323
+ 0 && (module.exports = {
324
+ COLLAPSE_WIDGET_ACTION,
325
+ EXPAND_WIDGET_ACTION,
326
+ EmbeddedVoice,
327
+ LanguageModelOption,
328
+ MINIMIZE_WIDGET_ACTION,
329
+ RESIZE_FRAME_ACTION,
330
+ TRANSCRIPT_MESSAGE_ACTION,
331
+ WIDGET_IFRAME_IS_READY_ACTION,
332
+ parseClientToFrameAction
333
+ });
334
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/index.ts","../src/lib/embed.ts","../src/lib/embed-messages.ts"],"sourcesContent":["export * from './lib/embed';\n\nexport {\n COLLAPSE_WIDGET_ACTION,\n EXPAND_WIDGET_ACTION,\n MINIMIZE_WIDGET_ACTION,\n RESIZE_FRAME_ACTION,\n TRANSCRIPT_MESSAGE_ACTION,\n WIDGET_IFRAME_IS_READY_ACTION,\n parseClientToFrameAction,\n type FrameToClientAction,\n type WindowDimensions,\n} from './lib/embed-messages';\n\nexport type {\n AgentTranscriptMessage,\n Config,\n JSONMessage,\n UserTranscriptMessage,\n EmotionScores,\n} from '@humeai/voice';\n\nexport { LanguageModelOption } from '@humeai/voice';\n","import type {\n AgentTranscriptMessage,\n Config,\n UserTranscriptMessage,\n} from '@humeai/voice';\nimport { createConfig } from '@humeai/voice';\n\nimport type { ClientToFrameAction } from './embed-messages';\nimport {\n EXPAND_FROM_CLIENT_ACTION,\n FrameToClientActionSchema,\n SEND_WINDOW_SIZE_ACTION,\n UPDATE_CONFIG_ACTION,\n WIDGET_IFRAME_IS_READY_ACTION,\n} from './embed-messages';\n\nexport type EmbeddedVoiceConfig = {\n rendererUrl: string;\n} & Config;\n\nexport type TranscriptMessageHandler = (\n message: UserTranscriptMessage | AgentTranscriptMessage,\n) => void;\n\nexport type CloseHandler = () => void;\n\nexport class EmbeddedVoice {\n private iframe: HTMLIFrameElement;\n\n private isMounted: boolean = false;\n\n private managedContainer: HTMLElement | null = null;\n\n private config: EmbeddedVoiceConfig;\n\n private onMessage: TranscriptMessageHandler;\n\n private onClose: CloseHandler;\n\n private constructor({\n onMessage = () => {},\n onClose = () => {},\n ...config\n }: {\n onMessage?: TranscriptMessageHandler;\n onClose?: CloseHandler;\n } & EmbeddedVoiceConfig) {\n this.config = config;\n this.iframe = this.createIframe(config);\n this.onMessage = onMessage;\n this.onClose = onClose;\n this.messageHandler = this.messageHandler.bind(this);\n }\n\n static create({\n rendererUrl,\n onMessage,\n onClose,\n ...config\n }: Partial<EmbeddedVoiceConfig> & {\n onMessage?: TranscriptMessageHandler;\n onClose?: CloseHandler;\n } & NonNullable<Pick<EmbeddedVoiceConfig, 'auth'>>): EmbeddedVoice {\n const parsedConfig = createConfig(config);\n\n return new EmbeddedVoice({\n rendererUrl: rendererUrl ?? 'https://voice-widget.hume.ai',\n onMessage,\n onClose,\n ...parsedConfig,\n });\n }\n\n mount(container?: HTMLElement) {\n const messageHandler = (event: MessageEvent<unknown>) => {\n this.messageHandler(event);\n };\n\n const resizeHandler = () => {\n this.sendWindowSize();\n };\n\n const el = container ?? this.createContainer();\n\n this.managedContainer = el;\n\n try {\n window.addEventListener('message', messageHandler);\n window.addEventListener('resize', resizeHandler);\n el.appendChild(this.iframe);\n this.isMounted = true;\n } catch (e) {\n this.isMounted = false;\n }\n\n const unmount = () => {\n try {\n window.removeEventListener('message', messageHandler);\n window.removeEventListener('resize', resizeHandler);\n this.iframe.remove();\n this.isMounted = false;\n } catch (e) {\n this.isMounted = true;\n }\n\n if (!container) {\n el.remove();\n }\n };\n\n return unmount;\n }\n\n private createContainer() {\n const div = document.createElement('div');\n\n Object.assign(div.style, {\n background: 'transparent',\n position: 'fixed',\n bottom: '0',\n right: '0',\n padding: '24px',\n zIndex: '999999',\n fontSize: '0px',\n pointerEvents: 'none',\n });\n\n div.id = 'hume-embedded-voice-container';\n\n document.body.appendChild(div);\n\n return div;\n }\n\n private createIframe({ rendererUrl }: EmbeddedVoiceConfig) {\n const el = document.createElement('iframe');\n\n Object.assign(el.style, {\n backgroundColor: 'transparent',\n backgroundImage: 'none',\n border: 'none',\n height: '0px',\n width: '0px',\n opacity: '0',\n });\n\n el.id = 'hume-embedded-voice';\n\n el.src = `${rendererUrl}`;\n\n el.setAttribute('frameborder', '0');\n el.setAttribute('allowtransparency', 'true');\n el.setAttribute('scrolling', 'no');\n el.setAttribute('allow', 'microphone');\n\n if (el.contentWindow) {\n el.contentWindow.document.documentElement.style.backgroundColor =\n 'transparent';\n el.contentWindow.document.body.style.backgroundColor = 'transparent';\n }\n\n return el;\n }\n\n private messageHandler(event: MessageEvent<unknown>) {\n if (!this.iframe) {\n return;\n }\n\n if (event.origin !== new URL(this.iframe.src).origin) {\n return;\n }\n\n const action = FrameToClientActionSchema.safeParse(event.data);\n\n if (!action.success) {\n return;\n }\n\n switch (action.data.type) {\n case WIDGET_IFRAME_IS_READY_ACTION.type: {\n this.showIframe();\n this.sendConfigObject();\n this.sendWindowSize();\n break;\n }\n case 'resize_frame': {\n this.resizeIframe(action.data.payload);\n break;\n }\n case 'transcript_message': {\n this.onMessage(action.data.payload);\n break;\n }\n case 'collapse_widget': {\n this.onClose();\n break;\n }\n }\n }\n\n openEmbed() {\n const action = EXPAND_FROM_CLIENT_ACTION({\n width: window.document.body.clientWidth,\n height: window.document.body.clientHeight,\n });\n this.sendMessageToFrame(action);\n }\n\n private sendConfigObject() {\n const action = UPDATE_CONFIG_ACTION(this.config);\n this.sendMessageToFrame(action);\n }\n\n private sendWindowSize() {\n const action = SEND_WINDOW_SIZE_ACTION({\n width: window.document.body.clientWidth,\n height: window.document.body.clientHeight,\n });\n this.sendMessageToFrame(action);\n }\n\n private sendMessageToFrame(action: ClientToFrameAction) {\n const frame = this.iframe;\n\n if (!frame.contentWindow) {\n return;\n }\n\n frame.contentWindow.postMessage(action, new URL(frame.src).origin);\n }\n\n private showIframe() {\n this.iframe.style.opacity = '1';\n if (this.managedContainer) {\n this.managedContainer.style.pointerEvents = 'all';\n }\n }\n\n private hideIframe() {\n this.iframe.style.opacity = '0';\n if (this.managedContainer) {\n this.managedContainer.style.pointerEvents = 'none';\n }\n }\n\n private resizeIframe({ width, height }: { width: number; height: number }) {\n this.iframe.style.width = `${width}px`;\n this.iframe.style.height = `${height}px`;\n }\n}\n","/** \n \n client frame \n \n ┌───────────────────────────┐ \n │ mount iframe │ ───────────▶ \n └───────────────────────────┘ \n ┌───────────────────────────┐\n ◀─────────── │ iframe is ready │\n └───────────────────────────┘\n ┌───────────────────────────┐ \n │ send config │ ───────────▶ \n └───────────────────────────┘ \n ┌───────────────────────────┐\n ◀─────────── │ widget is open │\n └───────────────────────────┘\n ┌───────────────────────────┐\n ◀─────────── │ widget is collapsed │\n └───────────────────────────┘\n ┌───────────────────────────┐\n ◀─────────── │ widget is minimized │\n └───────────────────────────┘\n ┌───────────────────────────┐\n ◀─────────── │ transcript message │\n └───────────────────────────┘\n ┌───────────────────────────┐\n ◀─────────── │ resize window │\n └───────────────────────────┘\n ┌───────────────────────────┐ \n │ unmount iframe │ ───────────▶ \n └───────────────────────────┘ \n */\nimport type {\n AgentTranscriptMessage,\n Config,\n UserTranscriptMessage,\n} from '@humeai/voice';\nimport {\n AgentTranscriptMessageSchema,\n ConfigSchema,\n UserTranscriptMessageSchema,\n} from '@humeai/voice';\nimport { z } from 'zod';\n\nconst WindowDimensionsSchema = z.object({\n width: z.number(),\n height: z.number(),\n});\n\nexport type WindowDimensions = z.infer<typeof WindowDimensionsSchema>;\n\n// ---------------------------------------------------------------------------\n// Client to frame actions\n// ---------------------------------------------------------------------------\nexport const ClientToFrameActionSchema = z.union([\n z.object({\n type: z.literal('update_config'),\n payload: ConfigSchema,\n }),\n z.object({\n type: z.literal('cancel'),\n }),\n z.object({\n type: z.literal('expand_widget_from_client'),\n payload: WindowDimensionsSchema,\n }),\n z.object({\n type: z.literal('send_window_size'),\n payload: WindowDimensionsSchema,\n }),\n]);\n\nexport type ClientToFrameAction = z.infer<typeof ClientToFrameActionSchema>;\n\nexport const UPDATE_CONFIG_ACTION = (config: Config) =>\n ({\n type: 'update_config',\n payload: config,\n }) satisfies ClientToFrameAction;\n\nexport const EXPAND_FROM_CLIENT_ACTION = (dimensions: WindowDimensions) =>\n ({\n type: 'expand_widget_from_client',\n payload: dimensions,\n }) satisfies ClientToFrameAction;\n\nexport const SEND_WINDOW_SIZE_ACTION = (dimensions: WindowDimensions) =>\n ({\n type: 'send_window_size',\n payload: dimensions,\n }) satisfies ClientToFrameAction;\n\nexport const parseClientToFrameAction = (\n data: unknown,\n): Promise<ClientToFrameAction> => {\n return new Promise((resolve, reject) => {\n try {\n const value = ClientToFrameActionSchema.parse(data);\n resolve(value);\n } catch (error) {\n reject(error);\n }\n });\n};\n\n// ---------------------------------------------------------------------------\n// Frame to client actions\n// ---------------------------------------------------------------------------\nexport const FrameToClientActionSchema = z.union([\n z.object({\n type: z.literal('expand_widget'),\n }),\n z.object({\n type: z.literal('collapse_widget'),\n }),\n z.object({\n type: z.literal('minimize_widget'),\n }),\n z.object({\n type: z.literal('widget_iframe_is_ready'),\n }),\n z.object({\n type: z.literal('transcript_message'),\n payload: z.union([\n UserTranscriptMessageSchema,\n AgentTranscriptMessageSchema,\n ]),\n }),\n z.object({\n type: z.literal('resize_frame'),\n payload: z.object({\n width: z.number(),\n height: z.number(),\n }),\n }),\n]);\n\nexport type FrameToClientAction = z.infer<typeof FrameToClientActionSchema>;\n\nexport const EXPAND_WIDGET_ACTION = {\n type: 'expand_widget',\n} satisfies FrameToClientAction;\n\nexport const COLLAPSE_WIDGET_ACTION = {\n type: 'collapse_widget' as const,\n} satisfies FrameToClientAction;\n\nexport const MINIMIZE_WIDGET_ACTION = {\n type: 'minimize_widget',\n} satisfies FrameToClientAction;\n\nexport const WIDGET_IFRAME_IS_READY_ACTION = {\n type: 'widget_iframe_is_ready',\n} satisfies FrameToClientAction;\n\nexport const TRANSCRIPT_MESSAGE_ACTION = (\n message: UserTranscriptMessage | AgentTranscriptMessage,\n) => {\n return {\n type: 'transcript_message',\n payload: message,\n } satisfies FrameToClientAction;\n};\n\nexport const RESIZE_FRAME_ACTION = (dimensions: {\n width: number;\n height: number;\n}) => {\n return {\n type: 'resize_frame',\n payload: {\n width: dimensions.width,\n height: dimensions.height,\n },\n } satisfies FrameToClientAction;\n};\n"],"mappings":"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","names":["import_voice","import_voice"]}
package/dist/index.mjs ADDED
@@ -0,0 +1,303 @@
1
+ // src/lib/embed.ts
2
+ import { createConfig } from "@humeai/voice";
3
+
4
+ // src/lib/embed-messages.ts
5
+ import {
6
+ AgentTranscriptMessageSchema,
7
+ ConfigSchema,
8
+ UserTranscriptMessageSchema
9
+ } from "@humeai/voice";
10
+ import { z } from "zod";
11
+ var WindowDimensionsSchema = z.object({
12
+ width: z.number(),
13
+ height: z.number()
14
+ });
15
+ var ClientToFrameActionSchema = z.union([
16
+ z.object({
17
+ type: z.literal("update_config"),
18
+ payload: ConfigSchema
19
+ }),
20
+ z.object({
21
+ type: z.literal("cancel")
22
+ }),
23
+ z.object({
24
+ type: z.literal("expand_widget_from_client"),
25
+ payload: WindowDimensionsSchema
26
+ }),
27
+ z.object({
28
+ type: z.literal("send_window_size"),
29
+ payload: WindowDimensionsSchema
30
+ })
31
+ ]);
32
+ var UPDATE_CONFIG_ACTION = (config) => ({
33
+ type: "update_config",
34
+ payload: config
35
+ });
36
+ var EXPAND_FROM_CLIENT_ACTION = (dimensions) => ({
37
+ type: "expand_widget_from_client",
38
+ payload: dimensions
39
+ });
40
+ var SEND_WINDOW_SIZE_ACTION = (dimensions) => ({
41
+ type: "send_window_size",
42
+ payload: dimensions
43
+ });
44
+ var parseClientToFrameAction = (data) => {
45
+ return new Promise((resolve, reject) => {
46
+ try {
47
+ const value = ClientToFrameActionSchema.parse(data);
48
+ resolve(value);
49
+ } catch (error) {
50
+ reject(error);
51
+ }
52
+ });
53
+ };
54
+ var FrameToClientActionSchema = z.union([
55
+ z.object({
56
+ type: z.literal("expand_widget")
57
+ }),
58
+ z.object({
59
+ type: z.literal("collapse_widget")
60
+ }),
61
+ z.object({
62
+ type: z.literal("minimize_widget")
63
+ }),
64
+ z.object({
65
+ type: z.literal("widget_iframe_is_ready")
66
+ }),
67
+ z.object({
68
+ type: z.literal("transcript_message"),
69
+ payload: z.union([
70
+ UserTranscriptMessageSchema,
71
+ AgentTranscriptMessageSchema
72
+ ])
73
+ }),
74
+ z.object({
75
+ type: z.literal("resize_frame"),
76
+ payload: z.object({
77
+ width: z.number(),
78
+ height: z.number()
79
+ })
80
+ })
81
+ ]);
82
+ var EXPAND_WIDGET_ACTION = {
83
+ type: "expand_widget"
84
+ };
85
+ var COLLAPSE_WIDGET_ACTION = {
86
+ type: "collapse_widget"
87
+ };
88
+ var MINIMIZE_WIDGET_ACTION = {
89
+ type: "minimize_widget"
90
+ };
91
+ var WIDGET_IFRAME_IS_READY_ACTION = {
92
+ type: "widget_iframe_is_ready"
93
+ };
94
+ var TRANSCRIPT_MESSAGE_ACTION = (message) => {
95
+ return {
96
+ type: "transcript_message",
97
+ payload: message
98
+ };
99
+ };
100
+ var RESIZE_FRAME_ACTION = (dimensions) => {
101
+ return {
102
+ type: "resize_frame",
103
+ payload: {
104
+ width: dimensions.width,
105
+ height: dimensions.height
106
+ }
107
+ };
108
+ };
109
+
110
+ // src/lib/embed.ts
111
+ var EmbeddedVoice = class _EmbeddedVoice {
112
+ iframe;
113
+ isMounted = false;
114
+ managedContainer = null;
115
+ config;
116
+ onMessage;
117
+ onClose;
118
+ constructor({
119
+ onMessage = () => {
120
+ },
121
+ onClose = () => {
122
+ },
123
+ ...config
124
+ }) {
125
+ this.config = config;
126
+ this.iframe = this.createIframe(config);
127
+ this.onMessage = onMessage;
128
+ this.onClose = onClose;
129
+ this.messageHandler = this.messageHandler.bind(this);
130
+ }
131
+ static create({
132
+ rendererUrl,
133
+ onMessage,
134
+ onClose,
135
+ ...config
136
+ }) {
137
+ const parsedConfig = createConfig(config);
138
+ return new _EmbeddedVoice({
139
+ rendererUrl: rendererUrl ?? "https://voice-widget.hume.ai",
140
+ onMessage,
141
+ onClose,
142
+ ...parsedConfig
143
+ });
144
+ }
145
+ mount(container) {
146
+ const messageHandler = (event) => {
147
+ this.messageHandler(event);
148
+ };
149
+ const resizeHandler = () => {
150
+ this.sendWindowSize();
151
+ };
152
+ const el = container ?? this.createContainer();
153
+ this.managedContainer = el;
154
+ try {
155
+ window.addEventListener("message", messageHandler);
156
+ window.addEventListener("resize", resizeHandler);
157
+ el.appendChild(this.iframe);
158
+ this.isMounted = true;
159
+ } catch (e) {
160
+ this.isMounted = false;
161
+ }
162
+ const unmount = () => {
163
+ try {
164
+ window.removeEventListener("message", messageHandler);
165
+ window.removeEventListener("resize", resizeHandler);
166
+ this.iframe.remove();
167
+ this.isMounted = false;
168
+ } catch (e) {
169
+ this.isMounted = true;
170
+ }
171
+ if (!container) {
172
+ el.remove();
173
+ }
174
+ };
175
+ return unmount;
176
+ }
177
+ createContainer() {
178
+ const div = document.createElement("div");
179
+ Object.assign(div.style, {
180
+ background: "transparent",
181
+ position: "fixed",
182
+ bottom: "0",
183
+ right: "0",
184
+ padding: "24px",
185
+ zIndex: "999999",
186
+ fontSize: "0px",
187
+ pointerEvents: "none"
188
+ });
189
+ div.id = "hume-embedded-voice-container";
190
+ document.body.appendChild(div);
191
+ return div;
192
+ }
193
+ createIframe({ rendererUrl }) {
194
+ const el = document.createElement("iframe");
195
+ Object.assign(el.style, {
196
+ backgroundColor: "transparent",
197
+ backgroundImage: "none",
198
+ border: "none",
199
+ height: "0px",
200
+ width: "0px",
201
+ opacity: "0"
202
+ });
203
+ el.id = "hume-embedded-voice";
204
+ el.src = `${rendererUrl}`;
205
+ el.setAttribute("frameborder", "0");
206
+ el.setAttribute("allowtransparency", "true");
207
+ el.setAttribute("scrolling", "no");
208
+ el.setAttribute("allow", "microphone");
209
+ if (el.contentWindow) {
210
+ el.contentWindow.document.documentElement.style.backgroundColor = "transparent";
211
+ el.contentWindow.document.body.style.backgroundColor = "transparent";
212
+ }
213
+ return el;
214
+ }
215
+ messageHandler(event) {
216
+ if (!this.iframe) {
217
+ return;
218
+ }
219
+ if (event.origin !== new URL(this.iframe.src).origin) {
220
+ return;
221
+ }
222
+ const action = FrameToClientActionSchema.safeParse(event.data);
223
+ if (!action.success) {
224
+ return;
225
+ }
226
+ switch (action.data.type) {
227
+ case WIDGET_IFRAME_IS_READY_ACTION.type: {
228
+ this.showIframe();
229
+ this.sendConfigObject();
230
+ this.sendWindowSize();
231
+ break;
232
+ }
233
+ case "resize_frame": {
234
+ this.resizeIframe(action.data.payload);
235
+ break;
236
+ }
237
+ case "transcript_message": {
238
+ this.onMessage(action.data.payload);
239
+ break;
240
+ }
241
+ case "collapse_widget": {
242
+ this.onClose();
243
+ break;
244
+ }
245
+ }
246
+ }
247
+ openEmbed() {
248
+ const action = EXPAND_FROM_CLIENT_ACTION({
249
+ width: window.document.body.clientWidth,
250
+ height: window.document.body.clientHeight
251
+ });
252
+ this.sendMessageToFrame(action);
253
+ }
254
+ sendConfigObject() {
255
+ const action = UPDATE_CONFIG_ACTION(this.config);
256
+ this.sendMessageToFrame(action);
257
+ }
258
+ sendWindowSize() {
259
+ const action = SEND_WINDOW_SIZE_ACTION({
260
+ width: window.document.body.clientWidth,
261
+ height: window.document.body.clientHeight
262
+ });
263
+ this.sendMessageToFrame(action);
264
+ }
265
+ sendMessageToFrame(action) {
266
+ const frame = this.iframe;
267
+ if (!frame.contentWindow) {
268
+ return;
269
+ }
270
+ frame.contentWindow.postMessage(action, new URL(frame.src).origin);
271
+ }
272
+ showIframe() {
273
+ this.iframe.style.opacity = "1";
274
+ if (this.managedContainer) {
275
+ this.managedContainer.style.pointerEvents = "all";
276
+ }
277
+ }
278
+ hideIframe() {
279
+ this.iframe.style.opacity = "0";
280
+ if (this.managedContainer) {
281
+ this.managedContainer.style.pointerEvents = "none";
282
+ }
283
+ }
284
+ resizeIframe({ width, height }) {
285
+ this.iframe.style.width = `${width}px`;
286
+ this.iframe.style.height = `${height}px`;
287
+ }
288
+ };
289
+
290
+ // src/index.ts
291
+ import { LanguageModelOption } from "@humeai/voice";
292
+ export {
293
+ COLLAPSE_WIDGET_ACTION,
294
+ EXPAND_WIDGET_ACTION,
295
+ EmbeddedVoice,
296
+ LanguageModelOption,
297
+ MINIMIZE_WIDGET_ACTION,
298
+ RESIZE_FRAME_ACTION,
299
+ TRANSCRIPT_MESSAGE_ACTION,
300
+ WIDGET_IFRAME_IS_READY_ACTION,
301
+ parseClientToFrameAction
302
+ };
303
+ //# sourceMappingURL=index.mjs.map