@coze/realtime-api 1.3.0 → 1.3.2-alpha.f7fe14
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 +3 -0
- package/README.zh-CN.md +3 -0
- package/dist/cjs/event-names/index.js +220 -210
- package/dist/cjs/index.js +762 -624
- package/dist/cjs/live/index.js +289 -0
- package/dist/esm/event-names/index.js +216 -169
- package/dist/esm/index.js +757 -591
- package/dist/esm/live/index.js +287 -0
- package/dist/tsconfig.build.tsbuildinfo +1 -1
- package/dist/types/event-names/event-names.d.ts +8 -2
- package/dist/types/index.d.ts +330 -9
- package/dist/types/live/live/index.d.ts +91 -0
- package/package.json +26 -6
- package/dist/types/client.d.ts +0 -49
- package/dist/types/error.d.ts +0 -25
- package/dist/types/event-handler.d.ts +0 -12
- package/dist/types/event-names/client.d.ts +0 -49
- package/dist/types/event-names/error.d.ts +0 -25
- package/dist/types/event-names/event-handler.d.ts +0 -12
- package/dist/types/event-names/index.d.ts +0 -163
- package/dist/types/event-names/utils.d.ts +0 -49
- package/dist/types/event-names.d.ts +0 -208
- package/dist/types/utils.d.ts +0 -49
- package/dist/umd/index.js +0 -987
package/dist/cjs/index.js
CHANGED
|
@@ -1,95 +1,31 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
var
|
|
4
|
-
|
|
5
|
-
(
|
|
6
|
-
|
|
7
|
-
__webpack_require__.n = function(module) {
|
|
8
|
-
var getter = module && module.__esModule ? function() {
|
|
9
|
-
return module['default'];
|
|
10
|
-
} : function() {
|
|
11
|
-
return module;
|
|
12
|
-
};
|
|
13
|
-
__webpack_require__.d(getter, {
|
|
14
|
-
a: getter
|
|
15
|
-
});
|
|
16
|
-
return getter;
|
|
17
|
-
};
|
|
18
|
-
})();
|
|
19
|
-
// webpack/runtime/define_property_getters
|
|
20
|
-
(()=>{
|
|
21
|
-
__webpack_require__.d = function(exports1, definition) {
|
|
22
|
-
for(var key in definition)if (__webpack_require__.o(definition, key) && !__webpack_require__.o(exports1, key)) Object.defineProperty(exports1, key, {
|
|
23
|
-
enumerable: true,
|
|
24
|
-
get: definition[key]
|
|
25
|
-
});
|
|
26
|
-
};
|
|
27
|
-
})();
|
|
28
|
-
// webpack/runtime/has_own_property
|
|
29
|
-
(()=>{
|
|
30
|
-
__webpack_require__.o = function(obj, prop) {
|
|
31
|
-
return Object.prototype.hasOwnProperty.call(obj, prop);
|
|
32
|
-
};
|
|
33
|
-
})();
|
|
34
|
-
// webpack/runtime/make_namespace_object
|
|
35
|
-
(()=>{
|
|
36
|
-
// define __esModule on exports
|
|
37
|
-
__webpack_require__.r = function(exports1) {
|
|
38
|
-
if ('undefined' != typeof Symbol && Symbol.toStringTag) Object.defineProperty(exports1, Symbol.toStringTag, {
|
|
39
|
-
value: 'Module'
|
|
40
|
-
});
|
|
41
|
-
Object.defineProperty(exports1, '__esModule', {
|
|
42
|
-
value: true
|
|
43
|
-
});
|
|
44
|
-
};
|
|
45
|
-
})();
|
|
46
|
-
/************************************************************************/ var __webpack_exports__ = {};
|
|
47
|
-
// ESM COMPAT FLAG
|
|
48
|
-
__webpack_require__.r(__webpack_exports__);
|
|
49
|
-
// EXPORTS
|
|
50
|
-
__webpack_require__.d(__webpack_exports__, {
|
|
51
|
-
RealtimeAPIError: ()=>/* reexport */ RealtimeAPIError,
|
|
52
|
-
RealtimeUtils: ()=>/* reexport */ utils_namespaceObject,
|
|
53
|
-
RealtimeError: ()=>/* reexport */ error_RealtimeError,
|
|
54
|
-
EventNames: ()=>/* reexport */ event_names,
|
|
55
|
-
RealtimeClient: ()=>/* binding */ RealtimeClient
|
|
56
|
-
});
|
|
57
|
-
// NAMESPACE OBJECT: ./src/utils.ts
|
|
58
|
-
var utils_namespaceObject = {};
|
|
59
|
-
__webpack_require__.r(utils_namespaceObject);
|
|
60
|
-
__webpack_require__.d(utils_namespaceObject, {
|
|
61
|
-
checkDevicePermission: ()=>checkDevicePermission,
|
|
62
|
-
checkPermission: ()=>checkPermission,
|
|
63
|
-
getAudioDevices: ()=>getAudioDevices,
|
|
64
|
-
isMobileVideoDevice: ()=>isMobileVideoDevice,
|
|
65
|
-
isScreenShareDevice: ()=>isScreenShareDevice,
|
|
66
|
-
isScreenShareSupported: ()=>isScreenShareSupported,
|
|
67
|
-
sleep: ()=>sleep
|
|
68
|
-
});
|
|
69
|
-
const api_namespaceObject = require("@coze/api");
|
|
70
|
-
const rtc_namespaceObject = require("@volcengine/rtc");
|
|
71
|
-
var rtc_default = /*#__PURE__*/ __webpack_require__.n(rtc_namespaceObject);
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var api = require('@coze/api');
|
|
4
|
+
var VERTC = require('@volcengine/rtc');
|
|
5
|
+
var RTCAIAnsExtension = require('@volcengine/rtc/extension-ainr');
|
|
6
|
+
|
|
72
7
|
/**
|
|
73
8
|
+ * Delays execution for the specified duration
|
|
74
9
|
+ * @param milliseconds The time to sleep in milliseconds
|
|
75
10
|
+ * @throws {Error} If milliseconds is negative
|
|
76
11
|
+ * @returns Promise that resolves after the specified duration
|
|
77
|
-
+ */
|
|
78
|
-
|
|
79
|
-
|
|
12
|
+
+ */
|
|
13
|
+
const sleep = (milliseconds) => {
|
|
14
|
+
if (milliseconds < 0) {
|
|
15
|
+
throw new Error('Sleep duration must be non-negative');
|
|
16
|
+
}
|
|
17
|
+
return new Promise(resolve => setTimeout(resolve, milliseconds));
|
|
80
18
|
};
|
|
81
19
|
/**
|
|
82
20
|
* @deprecated use checkDevicePermission instead
|
|
83
21
|
* Check microphone permission,return boolean
|
|
84
|
-
*/
|
|
85
|
-
|
|
22
|
+
*/
|
|
23
|
+
const checkPermission = async ({ audio = true, video = false, } = {}) => {
|
|
86
24
|
try {
|
|
87
|
-
const result = await
|
|
88
|
-
audio,
|
|
89
|
-
video
|
|
90
|
-
});
|
|
25
|
+
const result = await VERTC.enableDevices({ audio, video });
|
|
91
26
|
return result.audio;
|
|
92
|
-
}
|
|
27
|
+
}
|
|
28
|
+
catch (error) {
|
|
93
29
|
console.error('Failed to check device permissions:', error);
|
|
94
30
|
return false;
|
|
95
31
|
}
|
|
@@ -98,225 +34,289 @@ var rtc_default = /*#__PURE__*/ __webpack_require__.n(rtc_namespaceObject);
|
|
|
98
34
|
* Checks device permissions for audio and video
|
|
99
35
|
* @param checkVideo Whether to check video permissions (default: false)
|
|
100
36
|
* @returns Promise that resolves with the device permission status
|
|
101
|
-
*/
|
|
102
|
-
|
|
103
|
-
return await rtc_default().enableDevices({
|
|
104
|
-
audio: true,
|
|
105
|
-
video: checkVideo
|
|
106
|
-
});
|
|
107
|
-
};
|
|
37
|
+
*/
|
|
38
|
+
const checkDevicePermission = async (checkVideo = false) => await VERTC.enableDevices({ audio: true, video: checkVideo });
|
|
108
39
|
/**
|
|
109
40
|
* Get audio devices
|
|
110
41
|
* @returns Promise<AudioDevices> Object containing arrays of audio input and output devices
|
|
111
|
-
*/
|
|
112
|
-
|
|
42
|
+
*/
|
|
43
|
+
const getAudioDevices = async ({ video = false, } = {}) => {
|
|
113
44
|
let devices = [];
|
|
114
45
|
if (video) {
|
|
115
|
-
devices = await
|
|
116
|
-
if (isScreenShareSupported())
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
}
|
|
46
|
+
devices = await VERTC.enumerateDevices();
|
|
47
|
+
if (isScreenShareSupported()) {
|
|
48
|
+
// @ts-expect-error - add screenShare device to devices
|
|
49
|
+
devices.push({
|
|
50
|
+
deviceId: 'screenShare',
|
|
51
|
+
kind: 'videoinput',
|
|
52
|
+
label: 'Screen Share',
|
|
53
|
+
groupId: 'screenShare',
|
|
54
|
+
});
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
else {
|
|
58
|
+
devices = await [
|
|
59
|
+
...(await VERTC.enumerateAudioCaptureDevices()),
|
|
60
|
+
...(await VERTC.enumerateAudioPlaybackDevices()),
|
|
61
|
+
];
|
|
62
|
+
}
|
|
63
|
+
if (!(devices === null || devices === void 0 ? void 0 : devices.length)) {
|
|
64
|
+
return {
|
|
65
|
+
audioInputs: [],
|
|
66
|
+
audioOutputs: [],
|
|
67
|
+
videoInputs: [],
|
|
68
|
+
};
|
|
69
|
+
}
|
|
132
70
|
return {
|
|
133
|
-
audioInputs: devices.filter(
|
|
134
|
-
audioOutputs: devices.filter(
|
|
135
|
-
videoInputs: devices.filter(
|
|
71
|
+
audioInputs: devices.filter(i => i.deviceId && i.kind === 'audioinput'),
|
|
72
|
+
audioOutputs: devices.filter(i => i.deviceId && i.kind === 'audiooutput'),
|
|
73
|
+
videoInputs: devices.filter(i => i.deviceId && i.kind === 'videoinput'),
|
|
136
74
|
};
|
|
137
75
|
};
|
|
138
|
-
const isScreenShareDevice = (deviceId)=>'screenShare'
|
|
76
|
+
const isScreenShareDevice = (deviceId) => deviceId === 'screenShare';
|
|
139
77
|
/**
|
|
140
78
|
* 判断是否前后置摄像头
|
|
141
79
|
* @param deviceId
|
|
142
80
|
* @returns
|
|
143
|
-
*/
|
|
81
|
+
*/
|
|
82
|
+
const isMobileVideoDevice = (deviceId) => deviceId === 'user' || deviceId === 'environment';
|
|
144
83
|
/**
|
|
145
84
|
* Check if browser supports screen sharing
|
|
146
85
|
* 检查浏览器是否支持屏幕共享
|
|
147
|
-
*/
|
|
148
|
-
|
|
149
|
-
|
|
86
|
+
*/
|
|
87
|
+
function isScreenShareSupported() {
|
|
88
|
+
var _a;
|
|
89
|
+
return !!((_a = navigator === null || navigator === void 0 ? void 0 : navigator.mediaDevices) === null || _a === void 0 ? void 0 : _a.getDisplayMedia);
|
|
150
90
|
}
|
|
151
|
-
|
|
91
|
+
|
|
92
|
+
var utils = /*#__PURE__*/Object.freeze({
|
|
93
|
+
__proto__: null,
|
|
94
|
+
checkDevicePermission: checkDevicePermission,
|
|
95
|
+
checkPermission: checkPermission,
|
|
96
|
+
getAudioDevices: getAudioDevices,
|
|
97
|
+
isMobileVideoDevice: isMobileVideoDevice,
|
|
98
|
+
isScreenShareDevice: isScreenShareDevice,
|
|
99
|
+
isScreenShareSupported: isScreenShareSupported,
|
|
100
|
+
sleep: sleep
|
|
101
|
+
});
|
|
102
|
+
|
|
103
|
+
var EventNames;
|
|
104
|
+
(function (EventNames) {
|
|
105
|
+
/**
|
|
106
|
+
* en: All events
|
|
107
|
+
* zh: 所有事件
|
|
108
|
+
*/
|
|
109
|
+
EventNames["ALL"] = "realtime.event";
|
|
110
|
+
/**
|
|
111
|
+
* en: All client events
|
|
112
|
+
* zh: 所有客户端事件
|
|
113
|
+
*/
|
|
114
|
+
EventNames["ALL_CLIENT"] = "client.*";
|
|
115
|
+
/**
|
|
116
|
+
* en: All server events
|
|
117
|
+
* zh: 所有服务端事件
|
|
118
|
+
*/
|
|
119
|
+
EventNames["ALL_SERVER"] = "server.*";
|
|
120
|
+
/**
|
|
121
|
+
* en: Room info
|
|
122
|
+
* zh: 房间信息
|
|
123
|
+
*/
|
|
124
|
+
EventNames["ROOM_INFO"] = "client.room.info";
|
|
125
|
+
/**
|
|
126
|
+
* en: Client connected
|
|
127
|
+
* zh: 客户端连接
|
|
128
|
+
*/
|
|
129
|
+
EventNames["CONNECTED"] = "client.connected";
|
|
130
|
+
/**
|
|
131
|
+
* en: Client connecting
|
|
132
|
+
* zh: 客户端连接中
|
|
133
|
+
*/
|
|
134
|
+
EventNames["CONNECTING"] = "client.connecting";
|
|
135
|
+
/**
|
|
136
|
+
* en: Client interrupted
|
|
137
|
+
* zh: 客户端中断
|
|
138
|
+
*/
|
|
139
|
+
EventNames["INTERRUPTED"] = "client.interrupted";
|
|
140
|
+
/**
|
|
141
|
+
* en: Client disconnected
|
|
142
|
+
* zh: 客户端断开
|
|
143
|
+
*/
|
|
144
|
+
EventNames["DISCONNECTED"] = "client.disconnected";
|
|
145
|
+
/**
|
|
146
|
+
* en: Client audio unmuted
|
|
147
|
+
* zh: 客户端音频未静音
|
|
148
|
+
*/
|
|
149
|
+
EventNames["AUDIO_UNMUTED"] = "client.audio.unmuted";
|
|
150
|
+
/**
|
|
151
|
+
* en: Client audio muted
|
|
152
|
+
* zh: 客户端音频静音
|
|
153
|
+
*/
|
|
154
|
+
EventNames["AUDIO_MUTED"] = "client.audio.muted";
|
|
155
|
+
/**
|
|
156
|
+
* en: Client video on
|
|
157
|
+
* zh: 客户端视频开启
|
|
158
|
+
*/
|
|
159
|
+
EventNames["VIDEO_ON"] = "client.video.on";
|
|
160
|
+
/**
|
|
161
|
+
* en: Client video off
|
|
162
|
+
* zh: 客户端视频关闭
|
|
163
|
+
*/
|
|
164
|
+
EventNames["VIDEO_OFF"] = "client.video.off";
|
|
165
|
+
/**
|
|
166
|
+
* en: Client video error
|
|
167
|
+
* zh: 客户端视频(或屏幕共享)错误
|
|
168
|
+
*/
|
|
169
|
+
EventNames["VIDEO_ERROR"] = "client.video.error";
|
|
170
|
+
/**
|
|
171
|
+
* en: Client video event
|
|
172
|
+
* zh: 客户端视频事件
|
|
173
|
+
*/
|
|
174
|
+
EventNames["PLAYER_EVENT"] = "client.video.event";
|
|
175
|
+
/**
|
|
176
|
+
* en: Client error
|
|
177
|
+
* zh: 客户端错误
|
|
178
|
+
*/
|
|
179
|
+
EventNames["ERROR"] = "client.error";
|
|
180
|
+
/**
|
|
181
|
+
* en: Audio noise reduction enabled
|
|
182
|
+
* zh: 抑制平稳噪声
|
|
183
|
+
*/
|
|
184
|
+
EventNames["SUPPRESS_STATIONARY_NOISE"] = "client.suppress.stationary.noise";
|
|
185
|
+
/**
|
|
186
|
+
* en: Suppress non-stationary noise
|
|
187
|
+
* zh: 抑制非平稳噪声
|
|
188
|
+
*/
|
|
189
|
+
EventNames["SUPPRESS_NON_STATIONARY_NOISE"] = "client.suppress.non.stationary.noise";
|
|
190
|
+
/**
|
|
191
|
+
* en: Audio input device changed
|
|
192
|
+
* zh: 音频输入设备改变
|
|
193
|
+
*/
|
|
194
|
+
EventNames["AUDIO_INPUT_DEVICE_CHANGED"] = "client.input.device.changed";
|
|
195
|
+
/**
|
|
196
|
+
* en: Audio output device changed
|
|
197
|
+
* zh: 音频输出设备改变
|
|
198
|
+
*/
|
|
199
|
+
EventNames["AUDIO_OUTPUT_DEVICE_CHANGED"] = "client.output.device.changed";
|
|
200
|
+
/**
|
|
201
|
+
* en: Video input device changed
|
|
202
|
+
* zh: 视频输入设备改变
|
|
203
|
+
*/
|
|
204
|
+
EventNames["VIDEO_INPUT_DEVICE_CHANGED"] = "client.video.input.device.changed";
|
|
205
|
+
/**
|
|
206
|
+
* en: Network quality changed
|
|
207
|
+
* zh: 网络质量改变
|
|
208
|
+
*/
|
|
209
|
+
EventNames["NETWORK_QUALITY"] = "client.network.quality";
|
|
210
|
+
/**
|
|
211
|
+
* en: Bot joined
|
|
212
|
+
* zh: Bot 加入
|
|
213
|
+
*/
|
|
214
|
+
EventNames["BOT_JOIN"] = "server.bot.join";
|
|
215
|
+
/**
|
|
216
|
+
* en: Bot left
|
|
217
|
+
* zh: Bot 离开
|
|
218
|
+
*/
|
|
219
|
+
EventNames["BOT_LEAVE"] = "server.bot.leave";
|
|
220
|
+
/**
|
|
221
|
+
* en: Audio speech started
|
|
222
|
+
* zh: 开始说话
|
|
223
|
+
*/
|
|
224
|
+
EventNames["AUDIO_AGENT_SPEECH_STARTED"] = "server.audio.agent.speech_started";
|
|
225
|
+
/**
|
|
226
|
+
* en: Audio speech stopped
|
|
227
|
+
* zh: 停止说话
|
|
228
|
+
*/
|
|
229
|
+
EventNames["AUDIO_AGENT_SPEECH_STOPPED"] = "server.audio.agent.speech_stopped";
|
|
152
230
|
/**
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
231
|
+
* en: Server error
|
|
232
|
+
* zh: 服务端错误
|
|
233
|
+
*/
|
|
234
|
+
EventNames["SERVER_ERROR"] = "server.error";
|
|
156
235
|
/**
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
236
|
+
* en: User speech started
|
|
237
|
+
* zh: 用户开始说话
|
|
238
|
+
*/
|
|
239
|
+
EventNames["AUDIO_USER_SPEECH_STARTED"] = "server.audio.user.speech_started";
|
|
160
240
|
/**
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
241
|
+
* en: User speech stopped
|
|
242
|
+
* zh: 用户停止说话
|
|
243
|
+
*/
|
|
244
|
+
EventNames["AUDIO_USER_SPEECH_STOPPED"] = "server.audio.user.speech_stopped";
|
|
164
245
|
/**
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
246
|
+
* en: User successfully enters the room
|
|
247
|
+
* zh: 用户成功进入房间后,会收到该事件
|
|
248
|
+
*/
|
|
249
|
+
EventNames["SESSION_CREATED"] = "server.session.created";
|
|
168
250
|
/**
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
251
|
+
* en: Session updated
|
|
252
|
+
* zh: 会话更新
|
|
253
|
+
*/
|
|
254
|
+
EventNames["SESSION_UPDATED"] = "server.session.updated";
|
|
172
255
|
/**
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
256
|
+
* en: Conversation created
|
|
257
|
+
* zh: 会话创建
|
|
258
|
+
*/
|
|
259
|
+
EventNames["CONVERSATION_CREATED"] = "server.conversation.created";
|
|
176
260
|
/**
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
261
|
+
* en: Conversation chat created
|
|
262
|
+
* zh: 会话对话创建
|
|
263
|
+
*/
|
|
264
|
+
EventNames["CONVERSATION_CHAT_CREATED"] = "server.conversation.chat.created";
|
|
180
265
|
/**
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
266
|
+
* en: Conversation chat in progress
|
|
267
|
+
* zh: 对话正在处理中
|
|
268
|
+
*/
|
|
269
|
+
EventNames["CONVERSATION_CHAT_IN_PROGRESS"] = "server.conversation.chat.in_progress";
|
|
184
270
|
/**
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
271
|
+
* en: Conversation message delta received
|
|
272
|
+
* zh: 文本消息增量返回
|
|
273
|
+
*/
|
|
274
|
+
EventNames["CONVERSATION_MESSAGE_DELTA"] = "server.conversation.message.delta";
|
|
188
275
|
/**
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
276
|
+
* en: Conversation message completed
|
|
277
|
+
* zh: 文本消息完成
|
|
278
|
+
*/
|
|
279
|
+
EventNames["CONVERSATION_MESSAGE_COMPLETED"] = "server.conversation.message.completed";
|
|
192
280
|
/**
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
281
|
+
* en: Conversation chat completed
|
|
282
|
+
* zh: 对话完成
|
|
283
|
+
*/
|
|
284
|
+
EventNames["CONVERSATION_CHAT_COMPLETED"] = "server.conversation.chat.completed";
|
|
196
285
|
/**
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
286
|
+
* en: Conversation chat requires action
|
|
287
|
+
* zh: 对话需要插件
|
|
288
|
+
*/
|
|
289
|
+
EventNames["CONVERSATION_CHAT_REQUIRES_ACTION"] = "server.conversation.chat.requires_action";
|
|
200
290
|
/**
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
291
|
+
* en: Conversation chat failed
|
|
292
|
+
* zh: 对话失败
|
|
293
|
+
*/
|
|
294
|
+
EventNames["CONVERSATION_CHAT_FAILED"] = "server.conversation.chat.failed";
|
|
204
295
|
/**
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
296
|
+
* en: Session pre answer updated
|
|
297
|
+
* zh: 安抚配置更新成功
|
|
298
|
+
*/
|
|
299
|
+
EventNames["SESSION_PRE_ANSWER_UPDATED"] = "server.session.pre_answer.updated";
|
|
208
300
|
/**
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
301
|
+
* en: Conversation audio transcript delta
|
|
302
|
+
* zh: 用户语音识别字幕
|
|
303
|
+
*/
|
|
304
|
+
EventNames["CONVERSATION_AUDIO_TRANSCRIPT_DELTA"] = "server.conversation.audio_transcript.delta";
|
|
212
305
|
/**
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
306
|
+
* en: Mode updated
|
|
307
|
+
* zh: 更新房间模式成功
|
|
308
|
+
*/
|
|
309
|
+
EventNames["MODE_UPDATED"] = "server.mode.updated";
|
|
216
310
|
/**
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
* zh: 音频输出设备改变
|
|
227
|
-
*/ EventNames["AUDIO_OUTPUT_DEVICE_CHANGED"] = "client.output.device.changed";
|
|
228
|
-
/**
|
|
229
|
-
* en: Video input device changed
|
|
230
|
-
* zh: 视频输入设备改变
|
|
231
|
-
*/ EventNames["VIDEO_INPUT_DEVICE_CHANGED"] = "client.video.input.device.changed";
|
|
232
|
-
/**
|
|
233
|
-
* en: Network quality changed
|
|
234
|
-
* zh: 网络质量改变
|
|
235
|
-
*/ EventNames["NETWORK_QUALITY"] = "client.network.quality";
|
|
236
|
-
/**
|
|
237
|
-
* en: Bot joined
|
|
238
|
-
* zh: Bot 加入
|
|
239
|
-
*/ EventNames["BOT_JOIN"] = "server.bot.join";
|
|
240
|
-
/**
|
|
241
|
-
* en: Bot left
|
|
242
|
-
* zh: Bot 离开
|
|
243
|
-
*/ EventNames["BOT_LEAVE"] = "server.bot.leave";
|
|
244
|
-
/**
|
|
245
|
-
* en: Audio speech started
|
|
246
|
-
* zh: 开始说话
|
|
247
|
-
*/ EventNames["AUDIO_AGENT_SPEECH_STARTED"] = "server.audio.agent.speech_started";
|
|
248
|
-
/**
|
|
249
|
-
* en: Audio speech stopped
|
|
250
|
-
* zh: 停止说话
|
|
251
|
-
*/ EventNames["AUDIO_AGENT_SPEECH_STOPPED"] = "server.audio.agent.speech_stopped";
|
|
252
|
-
/**
|
|
253
|
-
* en: Server error
|
|
254
|
-
* zh: 服务端错误
|
|
255
|
-
*/ EventNames["SERVER_ERROR"] = "server.error";
|
|
256
|
-
/**
|
|
257
|
-
* en: User speech started
|
|
258
|
-
* zh: 用户开始说话
|
|
259
|
-
*/ EventNames["AUDIO_USER_SPEECH_STARTED"] = "server.audio.user.speech_started";
|
|
260
|
-
/**
|
|
261
|
-
* en: User speech stopped
|
|
262
|
-
* zh: 用户停止说话
|
|
263
|
-
*/ EventNames["AUDIO_USER_SPEECH_STOPPED"] = "server.audio.user.speech_stopped";
|
|
264
|
-
/**
|
|
265
|
-
* en: User successfully enters the room
|
|
266
|
-
* zh: 用户成功进入房间后,会收到该事件
|
|
267
|
-
*/ EventNames["SESSION_CREATED"] = "server.session.created";
|
|
268
|
-
/**
|
|
269
|
-
* en: Session updated
|
|
270
|
-
* zh: 会话更新
|
|
271
|
-
*/ EventNames["SESSION_UPDATED"] = "server.session.updated";
|
|
272
|
-
/**
|
|
273
|
-
* en: Conversation created
|
|
274
|
-
* zh: 会话创建
|
|
275
|
-
*/ EventNames["CONVERSATION_CREATED"] = "server.conversation.created";
|
|
276
|
-
/**
|
|
277
|
-
* en: Conversation chat created
|
|
278
|
-
* zh: 会话对话创建
|
|
279
|
-
*/ EventNames["CONVERSATION_CHAT_CREATED"] = "server.conversation.chat.created";
|
|
280
|
-
/**
|
|
281
|
-
* en: Conversation chat in progress
|
|
282
|
-
* zh: 对话正在处理中
|
|
283
|
-
*/ EventNames["CONVERSATION_CHAT_IN_PROGRESS"] = "server.conversation.chat.in_progress";
|
|
284
|
-
/**
|
|
285
|
-
* en: Conversation message delta received
|
|
286
|
-
* zh: 文本消息增量返回
|
|
287
|
-
*/ EventNames["CONVERSATION_MESSAGE_DELTA"] = "server.conversation.message.delta";
|
|
288
|
-
/**
|
|
289
|
-
* en: Conversation message completed
|
|
290
|
-
* zh: 文本消息完成
|
|
291
|
-
*/ EventNames["CONVERSATION_MESSAGE_COMPLETED"] = "server.conversation.message.completed";
|
|
292
|
-
/**
|
|
293
|
-
* en: Conversation chat completed
|
|
294
|
-
* zh: 对话完成
|
|
295
|
-
*/ EventNames["CONVERSATION_CHAT_COMPLETED"] = "server.conversation.chat.completed";
|
|
296
|
-
/**
|
|
297
|
-
* en: Conversation chat requires action
|
|
298
|
-
* zh: 对话需要插件
|
|
299
|
-
*/ EventNames["CONVERSATION_CHAT_REQUIRES_ACTION"] = "server.conversation.chat.requires_action";
|
|
300
|
-
/**
|
|
301
|
-
* en: Conversation chat failed
|
|
302
|
-
* zh: 对话失败
|
|
303
|
-
*/ EventNames["CONVERSATION_CHAT_FAILED"] = "server.conversation.chat.failed";
|
|
304
|
-
/**
|
|
305
|
-
* en: Session pre answer updated
|
|
306
|
-
* zh: 安抚配置更新成功
|
|
307
|
-
*/ EventNames["SESSION_PRE_ANSWER_UPDATED"] = "server.session.pre_answer.updated";
|
|
308
|
-
/**
|
|
309
|
-
* en: Conversation audio transcript delta
|
|
310
|
-
* zh: 用户语音识别字幕
|
|
311
|
-
*/ EventNames["CONVERSATION_AUDIO_TRANSCRIPT_DELTA"] = "server.conversation.audio_transcript.delta";
|
|
312
|
-
/**
|
|
313
|
-
* en: Mode updated
|
|
314
|
-
* zh: 更新房间模式成功
|
|
315
|
-
*/ EventNames["MODE_UPDATED"] = "server.mode.updated";
|
|
316
|
-
return EventNames;
|
|
317
|
-
}(event_names_EventNames || {});
|
|
318
|
-
/* ESM default export */ const event_names = event_names_EventNames;
|
|
319
|
-
var error_RealtimeError = /*#__PURE__*/ function(RealtimeError) {
|
|
311
|
+
* en: Live created
|
|
312
|
+
* zh: 直播创建
|
|
313
|
+
*/
|
|
314
|
+
EventNames["LIVE_CREATED"] = "server.live.created";
|
|
315
|
+
})(EventNames || (EventNames = {}));
|
|
316
|
+
var EventNames$1 = EventNames;
|
|
317
|
+
|
|
318
|
+
exports.RealtimeError = void 0;
|
|
319
|
+
(function (RealtimeError) {
|
|
320
320
|
RealtimeError["DEVICE_ACCESS_ERROR"] = "DEVICE_ACCESS_ERROR";
|
|
321
321
|
RealtimeError["STREAM_CREATION_ERROR"] = "STREAM_CREATION_ERROR";
|
|
322
322
|
RealtimeError["CONNECTION_ERROR"] = "CONNECTION_ERROR";
|
|
@@ -329,21 +329,40 @@ var error_RealtimeError = /*#__PURE__*/ function(RealtimeError) {
|
|
|
329
329
|
RealtimeError["CREATE_ROOM_ERROR"] = "CREATE_ROOM_ERROR";
|
|
330
330
|
RealtimeError["PARSE_MESSAGE_ERROR"] = "PARSE_MESSAGE_ERROR";
|
|
331
331
|
RealtimeError["HANDLER_MESSAGE_ERROR"] = "HANDLER_MESSAGE_ERROR";
|
|
332
|
-
|
|
333
|
-
|
|
332
|
+
})(exports.RealtimeError || (exports.RealtimeError = {}));
|
|
333
|
+
({
|
|
334
|
+
[exports.RealtimeError.DEVICE_ACCESS_ERROR]: 'Failed to get devices',
|
|
335
|
+
[exports.RealtimeError.STREAM_CREATION_ERROR]: 'Failed to create local stream',
|
|
336
|
+
[exports.RealtimeError.CONNECTION_ERROR]: 'Failed to connect',
|
|
337
|
+
[exports.RealtimeError.DISCONNECTION_ERROR]: 'Failed to disconnect',
|
|
338
|
+
[exports.RealtimeError.INTERRUPT_ERROR]: 'Failed to interrupt',
|
|
339
|
+
[exports.RealtimeError.EVENT_HANDLER_ERROR]: 'Event handler not found',
|
|
340
|
+
[exports.RealtimeError.PERMISSION_DENIED]: 'Permission denied for requested operation',
|
|
341
|
+
[exports.RealtimeError.NETWORK_ERROR]: 'Network connection error occurred',
|
|
342
|
+
[exports.RealtimeError.INVALID_STATE]: 'Operation invalid in current state',
|
|
343
|
+
[exports.RealtimeError.CREATE_ROOM_ERROR]: 'Failed to create room',
|
|
344
|
+
[exports.RealtimeError.PARSE_MESSAGE_ERROR]: 'Failed to parse message',
|
|
345
|
+
[exports.RealtimeError.HANDLER_MESSAGE_ERROR]: 'Failed to handle message',
|
|
346
|
+
});
|
|
334
347
|
class RealtimeAPIError extends Error {
|
|
335
348
|
/**
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
349
|
+
* @param code - Error code
|
|
350
|
+
* @param message - Error message
|
|
351
|
+
* @param error - Error object
|
|
352
|
+
*/
|
|
353
|
+
constructor(code, message, error) {
|
|
340
354
|
super(`[${code}] ${message}`);
|
|
341
355
|
this.name = 'RealtimeAPIError';
|
|
342
356
|
this.code = code;
|
|
343
357
|
this.error = error;
|
|
344
358
|
}
|
|
345
359
|
}
|
|
360
|
+
|
|
346
361
|
class RealtimeEventHandler {
|
|
362
|
+
constructor(debug = false) {
|
|
363
|
+
this.eventHandlers = {};
|
|
364
|
+
this._debug = debug;
|
|
365
|
+
}
|
|
347
366
|
clearEventHandlers() {
|
|
348
367
|
this.eventHandlers = {};
|
|
349
368
|
}
|
|
@@ -358,185 +377,254 @@ class RealtimeEventHandler {
|
|
|
358
377
|
const handlers = this.eventHandlers[eventName] || [];
|
|
359
378
|
if (callback) {
|
|
360
379
|
const index = handlers.indexOf(callback);
|
|
361
|
-
if (
|
|
380
|
+
if (index === -1) {
|
|
362
381
|
console.warn(`Could not turn off specified event listener for "${eventName}": not found as a listener`);
|
|
363
382
|
return;
|
|
364
383
|
}
|
|
365
384
|
handlers.splice(index, 1);
|
|
366
|
-
}
|
|
385
|
+
}
|
|
386
|
+
else {
|
|
387
|
+
delete this.eventHandlers[eventName];
|
|
388
|
+
}
|
|
367
389
|
}
|
|
368
390
|
// eslint-disable-next-line max-params
|
|
369
391
|
_dispatchToHandlers(eventName, event, handlers, prefix) {
|
|
370
|
-
for (const handler of handlers)
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
392
|
+
for (const handler of handlers) {
|
|
393
|
+
if (!prefix || eventName.startsWith(prefix)) {
|
|
394
|
+
try {
|
|
395
|
+
handler(eventName, event);
|
|
396
|
+
}
|
|
397
|
+
catch (e) {
|
|
398
|
+
throw new RealtimeAPIError(exports.RealtimeError.HANDLER_MESSAGE_ERROR, `Failed to handle message: ${eventName}`);
|
|
399
|
+
}
|
|
400
|
+
}
|
|
374
401
|
}
|
|
375
402
|
}
|
|
376
|
-
dispatch(eventName, event) {
|
|
377
|
-
|
|
378
|
-
|
|
403
|
+
dispatch(eventName, event, consoleLog = true) {
|
|
404
|
+
if (consoleLog) {
|
|
405
|
+
this._log(`dispatch ${eventName} event`, event);
|
|
406
|
+
}
|
|
379
407
|
const handlers = (this.eventHandlers[eventName] || []).slice();
|
|
380
408
|
this._dispatchToHandlers(eventName, event, handlers);
|
|
381
|
-
const allHandlers = (this.eventHandlers[
|
|
409
|
+
const allHandlers = (this.eventHandlers[EventNames$1.ALL] || []).slice();
|
|
382
410
|
this._dispatchToHandlers(eventName, event, allHandlers);
|
|
383
|
-
const allClientHandlers = (this.eventHandlers[
|
|
411
|
+
const allClientHandlers = (this.eventHandlers[EventNames$1.ALL_CLIENT] || []).slice();
|
|
384
412
|
this._dispatchToHandlers(eventName, event, allClientHandlers, 'client.');
|
|
385
|
-
const allServerHandlers = (this.eventHandlers[
|
|
413
|
+
const allServerHandlers = (this.eventHandlers[EventNames$1.ALL_SERVER] || []).slice();
|
|
386
414
|
this._dispatchToHandlers(eventName, event, allServerHandlers, 'server.');
|
|
387
415
|
}
|
|
388
416
|
_log(message, event) {
|
|
389
|
-
if (this._debug)
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
this.eventHandlers = {};
|
|
393
|
-
this._debug = debug;
|
|
417
|
+
if (this._debug) {
|
|
418
|
+
console.log(`[RealtimeClient] ${message}`, event);
|
|
419
|
+
}
|
|
394
420
|
}
|
|
395
421
|
}
|
|
396
|
-
|
|
397
|
-
var extension_ainr_default = /*#__PURE__*/ __webpack_require__.n(extension_ainr_namespaceObject);
|
|
422
|
+
|
|
398
423
|
class EngineClient extends RealtimeEventHandler {
|
|
424
|
+
// eslint-disable-next-line max-params
|
|
425
|
+
constructor(appId, debug = false, isTestEnv = false, isSupportVideo = false, videoConfig) {
|
|
426
|
+
super(debug);
|
|
427
|
+
this.joinUserId = '';
|
|
428
|
+
this._AIAnsExtension = null;
|
|
429
|
+
this._isSupportVideo = false;
|
|
430
|
+
if (isTestEnv) {
|
|
431
|
+
VERTC.setParameter('ICE_CONFIG_REQUEST_URLS', ['rtc-test.bytedance.com']);
|
|
432
|
+
}
|
|
433
|
+
else {
|
|
434
|
+
localStorage.removeItem('RTC_ACCESS_URLS-VolcEngine');
|
|
435
|
+
}
|
|
436
|
+
this.engine = VERTC.createEngine(appId);
|
|
437
|
+
this.handleMessage = this.handleMessage.bind(this);
|
|
438
|
+
this.handleUserJoin = this.handleUserJoin.bind(this);
|
|
439
|
+
this.handleUserLeave = this.handleUserLeave.bind(this);
|
|
440
|
+
this.handleEventError = this.handleEventError.bind(this);
|
|
441
|
+
this.handlePlayerEvent = this.handlePlayerEvent.bind(this);
|
|
442
|
+
this.handleNetworkQuality = this.handleNetworkQuality.bind(this);
|
|
443
|
+
this.handleTrackEnded = this.handleTrackEnded.bind(this);
|
|
444
|
+
// Debug only
|
|
445
|
+
this.handleLocalAudioPropertiesReport =
|
|
446
|
+
this.handleLocalAudioPropertiesReport.bind(this);
|
|
447
|
+
this.handleRemoteAudioPropertiesReport =
|
|
448
|
+
this.handleRemoteAudioPropertiesReport.bind(this);
|
|
449
|
+
this._isSupportVideo = isSupportVideo;
|
|
450
|
+
this._videoConfig = videoConfig;
|
|
451
|
+
}
|
|
399
452
|
bindEngineEvents() {
|
|
400
|
-
this.engine.on(
|
|
401
|
-
this.engine.on(
|
|
402
|
-
this.engine.on(
|
|
403
|
-
this.engine.on(
|
|
404
|
-
this.engine.on(
|
|
405
|
-
this.engine.on(
|
|
406
|
-
if (this._isSupportVideo)
|
|
453
|
+
this.engine.on(VERTC.events.onUserMessageReceived, this.handleMessage);
|
|
454
|
+
this.engine.on(VERTC.events.onUserJoined, this.handleUserJoin);
|
|
455
|
+
this.engine.on(VERTC.events.onUserLeave, this.handleUserLeave);
|
|
456
|
+
this.engine.on(VERTC.events.onError, this.handleEventError);
|
|
457
|
+
this.engine.on(VERTC.events.onNetworkQuality, this.handleNetworkQuality);
|
|
458
|
+
this.engine.on(VERTC.events.onTrackEnded, this.handleTrackEnded);
|
|
459
|
+
if (this._isSupportVideo) {
|
|
460
|
+
this.engine.on(VERTC.events.onPlayerEvent, this.handlePlayerEvent);
|
|
461
|
+
}
|
|
407
462
|
if (this._debug) {
|
|
408
|
-
this.engine.on(
|
|
409
|
-
this.engine.on(
|
|
463
|
+
this.engine.on(VERTC.events.onLocalAudioPropertiesReport, this.handleLocalAudioPropertiesReport);
|
|
464
|
+
this.engine.on(VERTC.events.onRemoteAudioPropertiesReport, this.handleRemoteAudioPropertiesReport);
|
|
410
465
|
}
|
|
411
466
|
}
|
|
412
467
|
removeEventListener() {
|
|
413
|
-
this.engine.off(
|
|
414
|
-
this.engine.off(
|
|
415
|
-
this.engine.off(
|
|
416
|
-
this.engine.off(
|
|
417
|
-
this.engine.off(
|
|
418
|
-
this.engine.off(
|
|
419
|
-
if (this._isSupportVideo)
|
|
468
|
+
this.engine.off(VERTC.events.onUserMessageReceived, this.handleMessage);
|
|
469
|
+
this.engine.off(VERTC.events.onUserJoined, this.handleUserJoin);
|
|
470
|
+
this.engine.off(VERTC.events.onUserLeave, this.handleUserLeave);
|
|
471
|
+
this.engine.off(VERTC.events.onError, this.handleEventError);
|
|
472
|
+
this.engine.off(VERTC.events.onNetworkQuality, this.handleNetworkQuality);
|
|
473
|
+
this.engine.off(VERTC.events.onTrackEnded, this.handleTrackEnded);
|
|
474
|
+
if (this._isSupportVideo) {
|
|
475
|
+
this.engine.off(VERTC.events.onPlayerEvent, this.handlePlayerEvent);
|
|
476
|
+
}
|
|
420
477
|
if (this._debug) {
|
|
421
|
-
this.engine.off(
|
|
422
|
-
this.engine.off(
|
|
478
|
+
this.engine.off(VERTC.events.onLocalAudioPropertiesReport, this.handleLocalAudioPropertiesReport);
|
|
479
|
+
this.engine.off(VERTC.events.onRemoteAudioPropertiesReport, this.handleRemoteAudioPropertiesReport);
|
|
423
480
|
}
|
|
424
481
|
}
|
|
425
482
|
_parseMessage(event) {
|
|
426
483
|
try {
|
|
427
484
|
return JSON.parse(event.message);
|
|
428
|
-
|
|
429
|
-
}
|
|
430
|
-
|
|
485
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
486
|
+
}
|
|
487
|
+
catch (e) {
|
|
488
|
+
throw new RealtimeAPIError(exports.RealtimeError.PARSE_MESSAGE_ERROR, (e === null || e === void 0 ? void 0 : e.message) || 'Unknown error');
|
|
431
489
|
}
|
|
432
490
|
}
|
|
433
491
|
handleMessage(event) {
|
|
434
492
|
try {
|
|
435
493
|
const message = this._parseMessage(event);
|
|
436
494
|
this.dispatch(`server.${message.event_type}`, message);
|
|
437
|
-
}
|
|
495
|
+
}
|
|
496
|
+
catch (e) {
|
|
438
497
|
if (e instanceof RealtimeAPIError) {
|
|
439
|
-
if (e.code ===
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
498
|
+
if (e.code === exports.RealtimeError.PARSE_MESSAGE_ERROR) {
|
|
499
|
+
this.dispatch(EventNames$1.ERROR, {
|
|
500
|
+
message: `Failed to parse message: ${event.message}`,
|
|
501
|
+
error: e,
|
|
502
|
+
});
|
|
503
|
+
}
|
|
504
|
+
else if (e.code === exports.RealtimeError.HANDLER_MESSAGE_ERROR) {
|
|
505
|
+
this.dispatch(EventNames$1.ERROR, {
|
|
506
|
+
message: `Failed to handle message: ${event.message}`,
|
|
507
|
+
error: e,
|
|
508
|
+
});
|
|
509
|
+
}
|
|
510
|
+
}
|
|
511
|
+
else {
|
|
512
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
513
|
+
}
|
|
448
514
|
}
|
|
449
515
|
}
|
|
450
516
|
handleEventError(e) {
|
|
451
|
-
this.dispatch(
|
|
517
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
452
518
|
}
|
|
453
519
|
handleUserJoin(event) {
|
|
454
520
|
this.joinUserId = event.userInfo.userId;
|
|
455
|
-
this.dispatch(
|
|
521
|
+
this.dispatch(EventNames$1.BOT_JOIN, event);
|
|
456
522
|
}
|
|
457
523
|
handleUserLeave(event) {
|
|
458
|
-
this.dispatch(
|
|
524
|
+
this.dispatch(EventNames$1.BOT_LEAVE, event);
|
|
459
525
|
}
|
|
460
526
|
handlePlayerEvent(event) {
|
|
461
|
-
this.dispatch(
|
|
527
|
+
this.dispatch(EventNames$1.PLAYER_EVENT, event);
|
|
462
528
|
}
|
|
463
529
|
handleNetworkQuality(uplinkNetworkQuality, downlinkNetworkQuality) {
|
|
464
|
-
this.dispatch(
|
|
530
|
+
this.dispatch(EventNames$1.NETWORK_QUALITY, {
|
|
465
531
|
uplinkNetworkQuality,
|
|
466
|
-
downlinkNetworkQuality
|
|
532
|
+
downlinkNetworkQuality,
|
|
467
533
|
});
|
|
468
534
|
}
|
|
469
535
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
470
536
|
handleTrackEnded(event) {
|
|
471
|
-
if ((null
|
|
537
|
+
if ((event === null || event === void 0 ? void 0 : event.kind) === 'video') {
|
|
538
|
+
this.dispatch(EventNames$1.VIDEO_OFF, event);
|
|
539
|
+
}
|
|
472
540
|
}
|
|
473
541
|
async joinRoom(options) {
|
|
474
|
-
const { token, roomId, uid, audioMutedDefault, videoOnDefault, isAutoSubscribeAudio } = options;
|
|
542
|
+
const { token, roomId, uid, audioMutedDefault, videoOnDefault, isAutoSubscribeAudio, } = options;
|
|
475
543
|
try {
|
|
476
544
|
await this.engine.joinRoom(token, roomId, {
|
|
477
|
-
userId: uid
|
|
545
|
+
userId: uid,
|
|
478
546
|
}, {
|
|
479
547
|
isAutoPublish: !audioMutedDefault,
|
|
480
548
|
isAutoSubscribeAudio,
|
|
481
|
-
isAutoSubscribeVideo: this._isSupportVideo && videoOnDefault
|
|
549
|
+
isAutoSubscribeVideo: this._isSupportVideo && videoOnDefault,
|
|
482
550
|
});
|
|
483
|
-
}
|
|
484
|
-
|
|
551
|
+
}
|
|
552
|
+
catch (e) {
|
|
553
|
+
if (e instanceof Error) {
|
|
554
|
+
throw new RealtimeAPIError(exports.RealtimeError.CONNECTION_ERROR, e.message);
|
|
555
|
+
}
|
|
485
556
|
}
|
|
486
557
|
}
|
|
487
558
|
async setAudioInputDevice(deviceId) {
|
|
488
559
|
const devices = await getAudioDevices();
|
|
489
|
-
if (
|
|
560
|
+
if (devices.audioInputs.findIndex(i => i.deviceId === deviceId) === -1) {
|
|
561
|
+
throw new RealtimeAPIError(exports.RealtimeError.DEVICE_ACCESS_ERROR, `Audio input device not found: ${deviceId}`);
|
|
562
|
+
}
|
|
490
563
|
this.engine.stopAudioCapture();
|
|
491
564
|
await this.engine.startAudioCapture(deviceId);
|
|
492
565
|
}
|
|
493
566
|
async setAudioOutputDevice(deviceId) {
|
|
494
|
-
const devices = await getAudioDevices({
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
567
|
+
const devices = await getAudioDevices({ video: false });
|
|
568
|
+
if (devices.audioOutputs.findIndex(i => i.deviceId === deviceId) === -1) {
|
|
569
|
+
throw new RealtimeAPIError(exports.RealtimeError.DEVICE_ACCESS_ERROR, `Audio output device not found: ${deviceId}`);
|
|
570
|
+
}
|
|
498
571
|
await this.engine.setAudioPlaybackDevice(deviceId);
|
|
499
572
|
}
|
|
500
|
-
async setVideoInputDevice(deviceId) {
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
this.engine.setLocalVideoPlayer(isScreenShareDevice(deviceId)
|
|
508
|
-
|
|
509
|
-
|
|
573
|
+
async setVideoInputDevice(deviceId, isAutoCapture = true) {
|
|
574
|
+
var _a, _b;
|
|
575
|
+
const devices = await getAudioDevices({ video: true });
|
|
576
|
+
if (!isMobileVideoDevice(deviceId) &&
|
|
577
|
+
devices.videoInputs.findIndex(i => i.deviceId === deviceId) === -1) {
|
|
578
|
+
throw new RealtimeAPIError(exports.RealtimeError.DEVICE_ACCESS_ERROR, `Video input device not found: ${deviceId}`);
|
|
579
|
+
}
|
|
580
|
+
this.engine.setLocalVideoPlayer(isScreenShareDevice(deviceId)
|
|
581
|
+
? VERTC.StreamIndex.STREAM_INDEX_SCREEN
|
|
582
|
+
: VERTC.StreamIndex.STREAM_INDEX_MAIN, {
|
|
583
|
+
renderDom: ((_a = this._videoConfig) === null || _a === void 0 ? void 0 : _a.renderDom) || 'local-player',
|
|
584
|
+
userId: this._roomUserId,
|
|
510
585
|
});
|
|
511
586
|
await this.changeVideoState(false);
|
|
512
587
|
if (isScreenShareDevice(deviceId)) {
|
|
513
|
-
if (this._streamIndex ===
|
|
588
|
+
if (this._streamIndex === VERTC.StreamIndex.STREAM_INDEX_MAIN) {
|
|
589
|
+
this.engine.setLocalVideoPlayer(VERTC.StreamIndex.STREAM_INDEX_MAIN);
|
|
590
|
+
}
|
|
514
591
|
if (isAutoCapture) {
|
|
515
|
-
|
|
516
|
-
this.engine.
|
|
517
|
-
await this.engine.
|
|
518
|
-
await this.engine.publishScreen(rtc_namespaceObject.MediaType.VIDEO);
|
|
592
|
+
this.engine.setVideoSourceType(VERTC.StreamIndex.STREAM_INDEX_SCREEN, VERTC.VideoSourceType.VIDEO_SOURCE_TYPE_INTERNAL);
|
|
593
|
+
await this.engine.startScreenCapture((_b = this._videoConfig) === null || _b === void 0 ? void 0 : _b.screenConfig);
|
|
594
|
+
await this.engine.publishScreen(VERTC.MediaType.VIDEO);
|
|
519
595
|
}
|
|
520
|
-
this._streamIndex =
|
|
521
|
-
}
|
|
522
|
-
|
|
523
|
-
if (
|
|
524
|
-
|
|
596
|
+
this._streamIndex = VERTC.StreamIndex.STREAM_INDEX_SCREEN;
|
|
597
|
+
}
|
|
598
|
+
else {
|
|
599
|
+
if (this._streamIndex === VERTC.StreamIndex.STREAM_INDEX_SCREEN) {
|
|
600
|
+
this.engine.setLocalVideoPlayer(VERTC.StreamIndex.STREAM_INDEX_SCREEN);
|
|
601
|
+
}
|
|
602
|
+
if (isAutoCapture) {
|
|
603
|
+
await this.engine.startVideoCapture(deviceId);
|
|
604
|
+
}
|
|
605
|
+
this._streamIndex = VERTC.StreamIndex.STREAM_INDEX_MAIN;
|
|
525
606
|
}
|
|
526
607
|
}
|
|
527
608
|
async createLocalStream(userId, videoConfig) {
|
|
528
609
|
this._roomUserId = userId;
|
|
529
|
-
const devices = await getAudioDevices({
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
if (this._isSupportVideo && !devices.videoInputs.length)
|
|
610
|
+
const devices = await getAudioDevices({ video: this._isSupportVideo });
|
|
611
|
+
if (!devices.audioInputs.length) {
|
|
612
|
+
throw new RealtimeAPIError(exports.RealtimeError.DEVICE_ACCESS_ERROR, 'Failed to get audio devices');
|
|
613
|
+
}
|
|
614
|
+
if (this._isSupportVideo && !devices.videoInputs.length) {
|
|
615
|
+
throw new RealtimeAPIError(exports.RealtimeError.DEVICE_ACCESS_ERROR, 'Failed to get video devices');
|
|
616
|
+
}
|
|
534
617
|
await this.engine.startAudioCapture(devices.audioInputs[0].deviceId);
|
|
535
|
-
if (this._isSupportVideo)
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
618
|
+
if (this._isSupportVideo) {
|
|
619
|
+
try {
|
|
620
|
+
await this.setVideoInputDevice((videoConfig === null || videoConfig === void 0 ? void 0 : videoConfig.videoInputDeviceId) || devices.videoInputs[0].deviceId, videoConfig === null || videoConfig === void 0 ? void 0 : videoConfig.videoOnDefault);
|
|
621
|
+
this.dispatch((videoConfig === null || videoConfig === void 0 ? void 0 : videoConfig.videoOnDefault)
|
|
622
|
+
? EventNames$1.VIDEO_ON
|
|
623
|
+
: EventNames$1.VIDEO_OFF, {});
|
|
624
|
+
}
|
|
625
|
+
catch (e) {
|
|
626
|
+
this.dispatch(EventNames$1.VIDEO_ERROR, e);
|
|
627
|
+
}
|
|
540
628
|
}
|
|
541
629
|
}
|
|
542
630
|
async disconnect() {
|
|
@@ -544,34 +632,47 @@ class EngineClient extends RealtimeEventHandler {
|
|
|
544
632
|
await this.engine.leaveRoom();
|
|
545
633
|
this.removeEventListener();
|
|
546
634
|
this.clearEventHandlers();
|
|
547
|
-
|
|
548
|
-
}
|
|
549
|
-
|
|
635
|
+
VERTC.destroyEngine(this.engine);
|
|
636
|
+
}
|
|
637
|
+
catch (e) {
|
|
638
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
550
639
|
throw e;
|
|
551
640
|
}
|
|
552
641
|
}
|
|
553
642
|
async changeAudioState(isMicOn) {
|
|
554
643
|
try {
|
|
555
|
-
if (isMicOn)
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
644
|
+
if (isMicOn) {
|
|
645
|
+
await this.engine.publishStream(VERTC.MediaType.AUDIO);
|
|
646
|
+
}
|
|
647
|
+
else {
|
|
648
|
+
await this.engine.unpublishStream(VERTC.MediaType.AUDIO);
|
|
649
|
+
}
|
|
650
|
+
}
|
|
651
|
+
catch (e) {
|
|
652
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
559
653
|
throw e;
|
|
560
654
|
}
|
|
561
655
|
}
|
|
562
656
|
async changeVideoState(isVideoOn) {
|
|
657
|
+
var _a;
|
|
563
658
|
if (isVideoOn) {
|
|
564
|
-
if (this._streamIndex ===
|
|
659
|
+
if (this._streamIndex === VERTC.StreamIndex.STREAM_INDEX_MAIN) {
|
|
660
|
+
await this.engine.startVideoCapture();
|
|
661
|
+
}
|
|
565
662
|
else {
|
|
566
|
-
|
|
567
|
-
this.engine.
|
|
568
|
-
await this.engine.
|
|
569
|
-
await this.engine.publishScreen(rtc_namespaceObject.MediaType.VIDEO);
|
|
663
|
+
this.engine.setVideoSourceType(VERTC.StreamIndex.STREAM_INDEX_SCREEN, VERTC.VideoSourceType.VIDEO_SOURCE_TYPE_INTERNAL);
|
|
664
|
+
await this.engine.startScreenCapture((_a = this._videoConfig) === null || _a === void 0 ? void 0 : _a.screenConfig);
|
|
665
|
+
await this.engine.publishScreen(VERTC.MediaType.VIDEO);
|
|
570
666
|
}
|
|
571
|
-
}
|
|
667
|
+
}
|
|
572
668
|
else {
|
|
573
|
-
|
|
574
|
-
|
|
669
|
+
if (this._streamIndex === VERTC.StreamIndex.STREAM_INDEX_MAIN) {
|
|
670
|
+
await this.engine.stopVideoCapture();
|
|
671
|
+
}
|
|
672
|
+
else {
|
|
673
|
+
await this.engine.stopScreenCapture();
|
|
674
|
+
await this.engine.unpublishScreen(VERTC.MediaType.VIDEO);
|
|
675
|
+
}
|
|
575
676
|
}
|
|
576
677
|
}
|
|
577
678
|
async stop() {
|
|
@@ -579,11 +680,12 @@ class EngineClient extends RealtimeEventHandler {
|
|
|
579
680
|
const result = await this.engine.sendUserMessage(this.joinUserId, JSON.stringify({
|
|
580
681
|
id: 'event_1',
|
|
581
682
|
event_type: 'conversation.chat.cancel',
|
|
582
|
-
data: {}
|
|
683
|
+
data: {},
|
|
583
684
|
}));
|
|
584
685
|
this._log(`interrupt ${this.joinUserId} ${result}`);
|
|
585
|
-
}
|
|
586
|
-
|
|
686
|
+
}
|
|
687
|
+
catch (e) {
|
|
688
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
587
689
|
throw e;
|
|
588
690
|
}
|
|
589
691
|
}
|
|
@@ -591,8 +693,9 @@ class EngineClient extends RealtimeEventHandler {
|
|
|
591
693
|
try {
|
|
592
694
|
const result = await this.engine.sendUserMessage(this.joinUserId, JSON.stringify(message));
|
|
593
695
|
this._log(`sendMessage ${this.joinUserId} ${JSON.stringify(message)} ${result}`);
|
|
594
|
-
}
|
|
595
|
-
|
|
696
|
+
}
|
|
697
|
+
catch (e) {
|
|
698
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
596
699
|
throw e;
|
|
597
700
|
}
|
|
598
701
|
}
|
|
@@ -601,352 +704,387 @@ class EngineClient extends RealtimeEventHandler {
|
|
|
601
704
|
}
|
|
602
705
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
603
706
|
handleLocalAudioPropertiesReport(event) {
|
|
604
|
-
var
|
|
605
|
-
if (this._debug && (
|
|
707
|
+
var _a, _b;
|
|
708
|
+
if (this._debug && ((_b = (_a = event[0]) === null || _a === void 0 ? void 0 : _a.audioPropertiesInfo) === null || _b === void 0 ? void 0 : _b.linearVolume) > 0) {
|
|
709
|
+
console.log('handleLocalAudioPropertiesReport', event);
|
|
710
|
+
}
|
|
606
711
|
}
|
|
607
712
|
handleRemoteAudioPropertiesReport(event) {
|
|
608
|
-
if (this._debug)
|
|
713
|
+
if (this._debug) {
|
|
714
|
+
console.log('handleRemoteAudioPropertiesReport', event);
|
|
715
|
+
}
|
|
609
716
|
}
|
|
610
717
|
async enableAudioNoiseReduction() {
|
|
611
|
-
var
|
|
612
|
-
await (
|
|
718
|
+
var _a;
|
|
719
|
+
await ((_a = this.engine) === null || _a === void 0 ? void 0 : _a.setAudioCaptureConfig({
|
|
613
720
|
noiseSuppression: true,
|
|
614
721
|
echoCancellation: true,
|
|
615
|
-
autoGainControl: true
|
|
722
|
+
autoGainControl: true,
|
|
616
723
|
}));
|
|
617
724
|
}
|
|
618
725
|
async initAIAnsExtension() {
|
|
619
|
-
const AIAnsExtension = new (
|
|
726
|
+
const AIAnsExtension = new RTCAIAnsExtension();
|
|
620
727
|
await this.engine.registerExtension(AIAnsExtension);
|
|
621
728
|
this._AIAnsExtension = AIAnsExtension;
|
|
622
729
|
}
|
|
623
730
|
changeAIAnsExtension(enable) {
|
|
731
|
+
var _a, _b;
|
|
624
732
|
if (enable) {
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
null === (_this__AIAnsExtension1 = this._AIAnsExtension) || void 0 === _this__AIAnsExtension1 || _this__AIAnsExtension1.disable();
|
|
733
|
+
(_a = this._AIAnsExtension) === null || _a === void 0 ? void 0 : _a.enable();
|
|
734
|
+
}
|
|
735
|
+
else {
|
|
736
|
+
(_b = this._AIAnsExtension) === null || _b === void 0 ? void 0 : _b.disable();
|
|
630
737
|
}
|
|
631
738
|
}
|
|
632
739
|
async startAudioPlaybackDeviceTest() {
|
|
633
740
|
try {
|
|
634
741
|
await this.engine.startAudioPlaybackDeviceTest('audio-test.wav', 200);
|
|
635
|
-
}
|
|
636
|
-
|
|
742
|
+
}
|
|
743
|
+
catch (e) {
|
|
744
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
637
745
|
throw e;
|
|
638
746
|
}
|
|
639
747
|
}
|
|
640
748
|
stopAudioPlaybackDeviceTest() {
|
|
641
749
|
try {
|
|
642
750
|
this.engine.stopAudioPlaybackDeviceTest();
|
|
643
|
-
}
|
|
644
|
-
|
|
751
|
+
}
|
|
752
|
+
catch (e) {
|
|
753
|
+
this.dispatch(EventNames$1.ERROR, e);
|
|
645
754
|
throw e;
|
|
646
755
|
}
|
|
647
756
|
}
|
|
648
757
|
getRtcEngine() {
|
|
649
758
|
return this.engine;
|
|
650
759
|
}
|
|
651
|
-
// eslint-disable-next-line max-params
|
|
652
|
-
constructor(appId, debug = false, isTestEnv = false, isSupportVideo = false, videoConfig){
|
|
653
|
-
super(debug), this.joinUserId = '', this._AIAnsExtension = null, this._isSupportVideo = false;
|
|
654
|
-
if (isTestEnv) rtc_default().setParameter('ICE_CONFIG_REQUEST_URLS', [
|
|
655
|
-
'rtc-test.bytedance.com'
|
|
656
|
-
]);
|
|
657
|
-
this.engine = rtc_default().createEngine(appId);
|
|
658
|
-
this.handleMessage = this.handleMessage.bind(this);
|
|
659
|
-
this.handleUserJoin = this.handleUserJoin.bind(this);
|
|
660
|
-
this.handleUserLeave = this.handleUserLeave.bind(this);
|
|
661
|
-
this.handleEventError = this.handleEventError.bind(this);
|
|
662
|
-
this.handlePlayerEvent = this.handlePlayerEvent.bind(this);
|
|
663
|
-
this.handleNetworkQuality = this.handleNetworkQuality.bind(this);
|
|
664
|
-
this.handleTrackEnded = this.handleTrackEnded.bind(this);
|
|
665
|
-
// Debug only
|
|
666
|
-
this.handleLocalAudioPropertiesReport = this.handleLocalAudioPropertiesReport.bind(this);
|
|
667
|
-
this.handleRemoteAudioPropertiesReport = this.handleRemoteAudioPropertiesReport.bind(this);
|
|
668
|
-
this._isSupportVideo = isSupportVideo;
|
|
669
|
-
this._videoConfig = videoConfig;
|
|
670
|
-
}
|
|
671
760
|
}
|
|
761
|
+
|
|
672
762
|
// Only use for test
|
|
673
763
|
const TEST_APP_ID = '6705332c79516e015e3e5f0c';
|
|
674
764
|
class RealtimeClient extends RealtimeEventHandler {
|
|
675
765
|
/**
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
766
|
+
* Constructor for initializing a RealtimeClient instance.
|
|
767
|
+
*
|
|
768
|
+
* 构造函数,初始化RealtimeClient实例。
|
|
769
|
+
*
|
|
770
|
+
* @param config
|
|
771
|
+
* @param config.accessToken - Required, Access Token. |
|
|
772
|
+
* 必填,Access Token。
|
|
773
|
+
* @param config.botId - Required, Bot Id. |
|
|
774
|
+
* 必填,Bot Id。
|
|
775
|
+
* @param config.voiceId - Optional, Voice Id. |
|
|
776
|
+
* 可选,音色Id。
|
|
777
|
+
* @param config.conversationId - Optional, Conversation Id. |
|
|
778
|
+
* 可选,会话Id。
|
|
779
|
+
* @param config.userId - Optional, User Id. |
|
|
780
|
+
* 可选,用户Id。
|
|
781
|
+
* @param config.baseURL - Optional, defaults to "https://api.coze.cn". |
|
|
782
|
+
* 可选,默认值为 "https://api.coze.cn"。
|
|
783
|
+
* @param config.debug - Optional, defaults to false.
|
|
784
|
+
* 可选,默认值为 false。
|
|
785
|
+
* @param config.allowPersonalAccessTokenInBrowser
|
|
786
|
+
* - Optional, whether to allow personal access tokens in browser environment. |
|
|
787
|
+
* 可选,是否允许在浏览器环境中使用个人访问令牌。
|
|
788
|
+
* @param config.audioMutedDefault - Optional, whether audio is muted by default, defaults to false. |
|
|
789
|
+
* 可选,默认是否静音,默认值为 false。
|
|
790
|
+
* @param config.connectorId - Required, Connector Id. |
|
|
791
|
+
* 必填,渠道 Id。
|
|
792
|
+
* @param config.suppressStationaryNoise - Optional, suppress stationary noise, defaults to false. |
|
|
793
|
+
* 可选,默认是否抑制静态噪声,默认值为 false。
|
|
794
|
+
* @param config.suppressNonStationaryNoise - Optional, suppress non-stationary noise, defaults to false. |
|
|
795
|
+
* 可选,默认是否抑制非静态噪声,默认值为 false。
|
|
796
|
+
* @param config.isAutoSubscribeAudio - Optional, whether to automatically subscribe to bot reply audio streams, defaults to true. |
|
|
797
|
+
* @param config.videoConfig - Optional, Video configuration. |
|
|
798
|
+
* 可选,视频配置。
|
|
799
|
+
* @param config.videoConfig.videoOnDefault - Optional, Whether to turn on video by default, defaults to true. |
|
|
800
|
+
* 可选,默认是否开启视频,默认值为 true。
|
|
801
|
+
* @param config.videoConfig.renderDom - Optional, The DOM element to render the video stream to. |
|
|
802
|
+
* 可选,渲染视频流的 DOM 元素。
|
|
803
|
+
* @param config.videoConfig.videoInputDeviceId - Optional, The device ID of the video input device to use. |
|
|
804
|
+
* 可选,视频输入设备的设备 ID。
|
|
805
|
+
* @param config.videoConfig.screenConfig - Optional, Screen share configuration if videoInputDeviceId is 'screenShare' see https://www.volcengine.com/docs/6348/104481#screenconfig for more details. |
|
|
806
|
+
* 可选,屏幕共享配置,如果 videoInputDeviceId 是 'screenShare',请参考 https://www.volcengine.com/docs/6348/104481#screenconfig 了解更多详情。
|
|
807
|
+
* @param config.prologueContent - Optional, Prologue content. | 可选,开场白内容。
|
|
808
|
+
* @param config.roomMode - Optional, Room mode. | 可选,房间模式。
|
|
809
|
+
*/
|
|
810
|
+
constructor(config) {
|
|
811
|
+
var _a;
|
|
812
|
+
super(config.debug);
|
|
813
|
+
this._client = null;
|
|
814
|
+
this.isConnected = false;
|
|
815
|
+
this._isTestEnv = false;
|
|
816
|
+
this._isSupportVideo = false;
|
|
817
|
+
this._config = config;
|
|
818
|
+
const defaultBaseURL = (_a = this._config.baseURL) !== null && _a !== void 0 ? _a : 'https://api.coze.cn';
|
|
819
|
+
this._config.baseURL = defaultBaseURL;
|
|
820
|
+
// init api
|
|
821
|
+
this._api = new api.CozeAPI({
|
|
822
|
+
token: this._config.accessToken,
|
|
823
|
+
baseURL: defaultBaseURL,
|
|
824
|
+
allowPersonalAccessTokenInBrowser: this._config.allowPersonalAccessTokenInBrowser,
|
|
825
|
+
});
|
|
826
|
+
this._isSupportVideo = !!config.videoConfig;
|
|
827
|
+
}
|
|
828
|
+
/**
|
|
829
|
+
* en: Establish a connection to the Coze API and join the room
|
|
830
|
+
*
|
|
831
|
+
* zh: 建立与 Coze API 的连接并加入房间
|
|
832
|
+
*/
|
|
833
|
+
async connect() {
|
|
834
|
+
var _a, _b, _c, _d;
|
|
681
835
|
const { botId, conversationId, voiceId, getRoomInfo } = this._config;
|
|
682
|
-
this.dispatch(
|
|
836
|
+
this.dispatch(EventNames$1.CONNECTING, {});
|
|
683
837
|
let roomInfo;
|
|
684
838
|
try {
|
|
685
839
|
// Step1 get token
|
|
686
|
-
if (getRoomInfo)
|
|
840
|
+
if (getRoomInfo) {
|
|
841
|
+
roomInfo = await getRoomInfo();
|
|
842
|
+
}
|
|
687
843
|
else {
|
|
688
844
|
const config = {};
|
|
689
|
-
if (this._config.prologueContent)
|
|
690
|
-
|
|
845
|
+
if (this._config.prologueContent) {
|
|
846
|
+
config.prologue_content = this._config.prologueContent;
|
|
847
|
+
}
|
|
848
|
+
if (this._config.roomMode !== undefined &&
|
|
849
|
+
this._config.roomMode !== null) {
|
|
850
|
+
config.room_mode = this._config.roomMode || api.RoomMode.Default;
|
|
851
|
+
}
|
|
691
852
|
if (this._config.videoConfig) {
|
|
692
|
-
if (isScreenShareDevice(this._config.videoConfig.videoInputDeviceId))
|
|
693
|
-
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
853
|
+
if (isScreenShareDevice(this._config.videoConfig.videoInputDeviceId)) {
|
|
854
|
+
config.video_config = {
|
|
855
|
+
stream_video_type: 'screen',
|
|
856
|
+
};
|
|
857
|
+
}
|
|
858
|
+
else {
|
|
859
|
+
config.video_config = {
|
|
860
|
+
stream_video_type: 'main',
|
|
861
|
+
};
|
|
862
|
+
}
|
|
863
|
+
}
|
|
864
|
+
if (this._config.translateConfig) {
|
|
865
|
+
config.translate_config = this._config.translateConfig;
|
|
866
|
+
}
|
|
867
|
+
if (this._config.turnDetection) {
|
|
868
|
+
config.turn_detection = this._config.turnDetection;
|
|
698
869
|
}
|
|
699
|
-
|
|
870
|
+
const params = {
|
|
700
871
|
bot_id: botId,
|
|
701
|
-
conversation_id: conversationId ||
|
|
702
|
-
voice_id: voiceId && voiceId.length > 0 ? voiceId :
|
|
872
|
+
conversation_id: conversationId || undefined,
|
|
873
|
+
voice_id: voiceId && voiceId.length > 0 ? voiceId : undefined,
|
|
703
874
|
connector_id: this._config.connectorId,
|
|
704
|
-
uid: this._config.userId ||
|
|
705
|
-
workflow_id: this._config.workflowId ||
|
|
706
|
-
config
|
|
707
|
-
}
|
|
875
|
+
uid: this._config.userId || undefined,
|
|
876
|
+
workflow_id: this._config.workflowId || undefined,
|
|
877
|
+
config,
|
|
878
|
+
};
|
|
879
|
+
roomInfo = await this._api.audio.rooms.create(params);
|
|
708
880
|
}
|
|
709
|
-
} catch (error) {
|
|
710
|
-
this.dispatch(event_names.ERROR, error);
|
|
711
|
-
throw new RealtimeAPIError(error_RealtimeError.CREATE_ROOM_ERROR, error instanceof Error ? error.message : 'Unknown error', error);
|
|
712
881
|
}
|
|
713
|
-
|
|
882
|
+
catch (error) {
|
|
883
|
+
this.dispatch(EventNames$1.ERROR, error);
|
|
884
|
+
throw new RealtimeAPIError(exports.RealtimeError.CREATE_ROOM_ERROR, error instanceof Error ? error.message : 'Unknown error', error);
|
|
885
|
+
}
|
|
886
|
+
this.dispatch(EventNames$1.ROOM_INFO, {
|
|
714
887
|
roomId: roomInfo.room_id,
|
|
715
888
|
uid: roomInfo.uid,
|
|
716
889
|
token: roomInfo.token,
|
|
717
|
-
appId: roomInfo.app_id
|
|
890
|
+
appId: roomInfo.app_id,
|
|
718
891
|
});
|
|
719
892
|
this._isTestEnv = TEST_APP_ID === roomInfo.app_id;
|
|
720
893
|
// Step2 create engine
|
|
721
894
|
this._client = new EngineClient(roomInfo.app_id, this._config.debug, this._isTestEnv, this._isSupportVideo, this._config.videoConfig);
|
|
722
895
|
// Step3 bind engine events
|
|
723
896
|
this._client.bindEngineEvents();
|
|
724
|
-
this._client.on(
|
|
897
|
+
this._client.on(EventNames$1.ALL, (eventName, data) => {
|
|
725
898
|
this.dispatch(eventName, data, false);
|
|
726
899
|
});
|
|
727
900
|
if (this._config.suppressStationaryNoise) {
|
|
728
901
|
await this._client.enableAudioNoiseReduction();
|
|
729
|
-
this.dispatch(
|
|
902
|
+
this.dispatch(EventNames$1.SUPPRESS_STATIONARY_NOISE, {});
|
|
730
903
|
}
|
|
731
|
-
if (this._config.suppressNonStationaryNoise)
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
|
|
904
|
+
if (this._config.suppressNonStationaryNoise) {
|
|
905
|
+
try {
|
|
906
|
+
await this._client.initAIAnsExtension();
|
|
907
|
+
this._client.changeAIAnsExtension(true);
|
|
908
|
+
this.dispatch(EventNames$1.SUPPRESS_NON_STATIONARY_NOISE, {});
|
|
909
|
+
}
|
|
910
|
+
catch (error) {
|
|
911
|
+
console.warn('Config suppressNonStationaryNoise is not supported', error);
|
|
912
|
+
}
|
|
737
913
|
}
|
|
738
|
-
var _this__config_audioMutedDefault, _this__config_videoConfig_videoOnDefault, _this__config_isAutoSubscribeAudio;
|
|
739
914
|
// Step4 join room
|
|
740
915
|
await this._client.joinRoom({
|
|
741
916
|
token: roomInfo.token,
|
|
742
917
|
roomId: roomInfo.room_id,
|
|
743
918
|
uid: roomInfo.uid,
|
|
744
|
-
audioMutedDefault:
|
|
745
|
-
videoOnDefault:
|
|
746
|
-
isAutoSubscribeAudio:
|
|
919
|
+
audioMutedDefault: (_a = this._config.audioMutedDefault) !== null && _a !== void 0 ? _a : false,
|
|
920
|
+
videoOnDefault: (_c = (_b = this._config.videoConfig) === null || _b === void 0 ? void 0 : _b.videoOnDefault) !== null && _c !== void 0 ? _c : true,
|
|
921
|
+
isAutoSubscribeAudio: (_d = this._config.isAutoSubscribeAudio) !== null && _d !== void 0 ? _d : true,
|
|
747
922
|
});
|
|
748
923
|
// Step5 create local stream
|
|
749
924
|
await this._client.createLocalStream(roomInfo.uid, this._config.videoConfig);
|
|
750
925
|
// step6 set connected and dispatch connected event
|
|
751
926
|
this.isConnected = true;
|
|
752
|
-
this.dispatch(
|
|
927
|
+
this.dispatch(EventNames$1.CONNECTED, {
|
|
753
928
|
roomId: roomInfo.room_id,
|
|
754
929
|
uid: roomInfo.uid,
|
|
755
930
|
token: roomInfo.token,
|
|
756
|
-
appId: roomInfo.app_id
|
|
931
|
+
appId: roomInfo.app_id,
|
|
757
932
|
});
|
|
758
933
|
}
|
|
759
934
|
/**
|
|
760
|
-
|
|
761
|
-
|
|
762
|
-
|
|
763
|
-
|
|
764
|
-
|
|
765
|
-
|
|
766
|
-
this.
|
|
935
|
+
* en: Interrupt the current conversation
|
|
936
|
+
*
|
|
937
|
+
* zh: 中断当前对话
|
|
938
|
+
*/
|
|
939
|
+
async interrupt() {
|
|
940
|
+
var _a;
|
|
941
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.stop());
|
|
942
|
+
this.dispatch(EventNames$1.INTERRUPTED, {});
|
|
767
943
|
}
|
|
768
944
|
/**
|
|
769
|
-
|
|
770
|
-
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
|
|
774
|
-
|
|
945
|
+
* en: Disconnect from the current session
|
|
946
|
+
*
|
|
947
|
+
* zh: 断开与当前会话的连接
|
|
948
|
+
*/
|
|
949
|
+
async disconnect() {
|
|
950
|
+
var _a;
|
|
951
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.disconnect());
|
|
775
952
|
this.isConnected = false;
|
|
776
953
|
this._client = null;
|
|
777
|
-
this.dispatch(
|
|
954
|
+
this.dispatch(EventNames$1.DISCONNECTED, {});
|
|
778
955
|
}
|
|
779
956
|
/**
|
|
780
|
-
|
|
781
|
-
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
957
|
+
* en: Send a message to the bot
|
|
958
|
+
*
|
|
959
|
+
* zh: 发送消息给Bot
|
|
960
|
+
*/
|
|
961
|
+
async sendMessage(message) {
|
|
962
|
+
var _a;
|
|
963
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.sendMessage(message));
|
|
964
|
+
const eventType = typeof message.event_type === 'string'
|
|
965
|
+
? message.event_type
|
|
966
|
+
: 'unknown_event';
|
|
787
967
|
this.dispatch(`client.${eventType}`, message);
|
|
788
968
|
}
|
|
789
969
|
/**
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
794
|
-
|
|
795
|
-
|
|
796
|
-
|
|
797
|
-
|
|
970
|
+
* en: Enable or disable audio
|
|
971
|
+
*
|
|
972
|
+
* zh: 启用或禁用音频
|
|
973
|
+
*/
|
|
974
|
+
async setAudioEnable(isEnable) {
|
|
975
|
+
var _a;
|
|
976
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.changeAudioState(isEnable));
|
|
977
|
+
if (isEnable) {
|
|
978
|
+
this.dispatch(EventNames$1.AUDIO_UNMUTED, {});
|
|
979
|
+
}
|
|
980
|
+
else {
|
|
981
|
+
this.dispatch(EventNames$1.AUDIO_MUTED, {});
|
|
982
|
+
}
|
|
798
983
|
}
|
|
799
984
|
async setVideoEnable(isEnable) {
|
|
985
|
+
var _a;
|
|
800
986
|
try {
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
this.dispatch(
|
|
987
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.changeVideoState(isEnable));
|
|
988
|
+
this.dispatch(isEnable ? EventNames$1.VIDEO_ON : EventNames$1.VIDEO_OFF, {});
|
|
989
|
+
}
|
|
990
|
+
catch (e) {
|
|
991
|
+
this.dispatch(EventNames$1.VIDEO_ERROR, e);
|
|
806
992
|
throw e;
|
|
807
993
|
}
|
|
808
994
|
}
|
|
809
995
|
/**
|
|
810
|
-
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
996
|
+
* en: Enable audio properties reporting (debug mode only)
|
|
997
|
+
*
|
|
998
|
+
* zh: 启用音频属性报告(仅限调试模式)
|
|
999
|
+
*/
|
|
1000
|
+
enableAudioPropertiesReport(config) {
|
|
1001
|
+
var _a;
|
|
814
1002
|
if (this._config.debug) {
|
|
815
|
-
|
|
816
|
-
null === (_this__client = this._client) || void 0 === _this__client || _this__client.enableAudioPropertiesReport(config);
|
|
1003
|
+
(_a = this._client) === null || _a === void 0 ? void 0 : _a.enableAudioPropertiesReport(config);
|
|
817
1004
|
return true;
|
|
818
1005
|
}
|
|
819
|
-
|
|
820
|
-
|
|
1006
|
+
else {
|
|
1007
|
+
console.warn('enableAudioPropertiesReport is not supported in non-debug mode');
|
|
1008
|
+
return false;
|
|
1009
|
+
}
|
|
821
1010
|
}
|
|
822
1011
|
/**
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
|
|
1012
|
+
* en: Start audio playback device test (debug mode only)
|
|
1013
|
+
*
|
|
1014
|
+
* zh: 开始音频播放设备测试(仅限调试模式)
|
|
1015
|
+
*/
|
|
1016
|
+
async startAudioPlaybackDeviceTest() {
|
|
1017
|
+
var _a;
|
|
827
1018
|
if (this._config.debug) {
|
|
828
|
-
|
|
829
|
-
|
|
830
|
-
|
|
1019
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.startAudioPlaybackDeviceTest());
|
|
1020
|
+
}
|
|
1021
|
+
else {
|
|
1022
|
+
console.warn('startAudioPlaybackDeviceTest is not supported in non-debug mode');
|
|
1023
|
+
}
|
|
831
1024
|
}
|
|
832
1025
|
/**
|
|
833
|
-
|
|
834
|
-
|
|
835
|
-
|
|
836
|
-
|
|
1026
|
+
* en: Stop audio playback device test (debug mode only)
|
|
1027
|
+
*
|
|
1028
|
+
* zh: 停止音频播放设备测试(仅限调试模式)
|
|
1029
|
+
*/
|
|
1030
|
+
stopAudioPlaybackDeviceTest() {
|
|
1031
|
+
var _a;
|
|
837
1032
|
if (this._config.debug) {
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
|
|
841
|
-
|
|
842
|
-
|
|
843
|
-
* en: Set the audio input device
|
|
844
|
-
*
|
|
845
|
-
* zh: 设置音频输入设备
|
|
846
|
-
*/ async setAudioInputDevice(deviceId) {
|
|
847
|
-
var _this__client;
|
|
848
|
-
await (null === (_this__client = this._client) || void 0 === _this__client ? void 0 : _this__client.setAudioInputDevice(deviceId));
|
|
849
|
-
this.dispatch(event_names.AUDIO_INPUT_DEVICE_CHANGED, {
|
|
850
|
-
deviceId
|
|
851
|
-
});
|
|
1033
|
+
(_a = this._client) === null || _a === void 0 ? void 0 : _a.stopAudioPlaybackDeviceTest();
|
|
1034
|
+
}
|
|
1035
|
+
else {
|
|
1036
|
+
console.warn('stopAudioPlaybackDeviceTest is not supported in non-debug mode');
|
|
1037
|
+
}
|
|
852
1038
|
}
|
|
853
1039
|
/**
|
|
854
|
-
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
|
|
859
|
-
|
|
860
|
-
this.
|
|
861
|
-
|
|
862
|
-
|
|
1040
|
+
* en: Set the audio input device
|
|
1041
|
+
*
|
|
1042
|
+
* zh: 设置音频输入设备
|
|
1043
|
+
*/
|
|
1044
|
+
async setAudioInputDevice(deviceId) {
|
|
1045
|
+
var _a;
|
|
1046
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.setAudioInputDevice(deviceId));
|
|
1047
|
+
this.dispatch(EventNames$1.AUDIO_INPUT_DEVICE_CHANGED, { deviceId });
|
|
1048
|
+
}
|
|
1049
|
+
/**
|
|
1050
|
+
* en: Set the audio output device
|
|
1051
|
+
*
|
|
1052
|
+
* zh: 设置音频输出设备
|
|
1053
|
+
*/
|
|
1054
|
+
async setAudioOutputDevice(deviceId) {
|
|
1055
|
+
var _a;
|
|
1056
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.setAudioOutputDevice(deviceId));
|
|
1057
|
+
this.dispatch(EventNames$1.AUDIO_OUTPUT_DEVICE_CHANGED, { deviceId });
|
|
863
1058
|
}
|
|
864
1059
|
/**
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
1060
|
+
* en: Set the video input device
|
|
1061
|
+
*
|
|
1062
|
+
* zh: 设置视频输入设备
|
|
1063
|
+
*/
|
|
1064
|
+
async setVideoInputDevice(deviceId) {
|
|
1065
|
+
var _a;
|
|
869
1066
|
try {
|
|
870
|
-
|
|
871
|
-
|
|
872
|
-
|
|
873
|
-
|
|
874
|
-
this.dispatch(
|
|
1067
|
+
await ((_a = this._client) === null || _a === void 0 ? void 0 : _a.setVideoInputDevice(deviceId));
|
|
1068
|
+
this.dispatch(EventNames$1.VIDEO_ON, {});
|
|
1069
|
+
}
|
|
1070
|
+
catch (e) {
|
|
1071
|
+
this.dispatch(EventNames$1.VIDEO_ERROR, e);
|
|
875
1072
|
throw e;
|
|
876
1073
|
}
|
|
877
|
-
this.dispatch(
|
|
878
|
-
deviceId
|
|
879
|
-
});
|
|
1074
|
+
this.dispatch(EventNames$1.VIDEO_INPUT_DEVICE_CHANGED, { deviceId });
|
|
880
1075
|
}
|
|
881
1076
|
/**
|
|
882
|
-
|
|
883
|
-
|
|
884
|
-
|
|
885
|
-
|
|
886
|
-
|
|
887
|
-
|
|
888
|
-
|
|
889
|
-
/**
|
|
890
|
-
* Constructor for initializing a RealtimeClient instance.
|
|
891
|
-
*
|
|
892
|
-
* 构造函数,初始化RealtimeClient实例。
|
|
893
|
-
*
|
|
894
|
-
* @param config
|
|
895
|
-
* @param config.accessToken - Required, Access Token. |
|
|
896
|
-
* 必填,Access Token。
|
|
897
|
-
* @param config.botId - Required, Bot Id. |
|
|
898
|
-
* 必填,Bot Id。
|
|
899
|
-
* @param config.voiceId - Optional, Voice Id. |
|
|
900
|
-
* 可选,音色Id。
|
|
901
|
-
* @param config.conversationId - Optional, Conversation Id. |
|
|
902
|
-
* 可选,会话Id。
|
|
903
|
-
* @param config.userId - Optional, User Id. |
|
|
904
|
-
* 可选,用户Id。
|
|
905
|
-
* @param config.baseURL - Optional, defaults to "https://api.coze.cn". |
|
|
906
|
-
* 可选,默认值为 "https://api.coze.cn"。
|
|
907
|
-
* @param config.debug - Optional, defaults to false.
|
|
908
|
-
* 可选,默认值为 false。
|
|
909
|
-
* @param config.allowPersonalAccessTokenInBrowser
|
|
910
|
-
* - Optional, whether to allow personal access tokens in browser environment. |
|
|
911
|
-
* 可选,是否允许在浏览器环境中使用个人访问令牌。
|
|
912
|
-
* @param config.audioMutedDefault - Optional, whether audio is muted by default, defaults to false. |
|
|
913
|
-
* 可选,默认是否静音,默认值为 false。
|
|
914
|
-
* @param config.connectorId - Required, Connector Id. |
|
|
915
|
-
* 必填,渠道 Id。
|
|
916
|
-
* @param config.suppressStationaryNoise - Optional, suppress stationary noise, defaults to false. |
|
|
917
|
-
* 可选,默认是否抑制静态噪声,默认值为 false。
|
|
918
|
-
* @param config.suppressNonStationaryNoise - Optional, suppress non-stationary noise, defaults to false. |
|
|
919
|
-
* 可选,默认是否抑制非静态噪声,默认值为 false。
|
|
920
|
-
* @param config.isAutoSubscribeAudio - Optional, whether to automatically subscribe to bot reply audio streams, defaults to true. |
|
|
921
|
-
* @param config.videoConfig - Optional, Video configuration. |
|
|
922
|
-
* 可选,视频配置。
|
|
923
|
-
* @param config.videoConfig.videoOnDefault - Optional, Whether to turn on video by default, defaults to true. |
|
|
924
|
-
* 可选,默认是否开启视频,默认值为 true。
|
|
925
|
-
* @param config.videoConfig.renderDom - Optional, The DOM element to render the video stream to. |
|
|
926
|
-
* 可选,渲染视频流的 DOM 元素。
|
|
927
|
-
* @param config.videoConfig.videoInputDeviceId - Optional, The device ID of the video input device to use. |
|
|
928
|
-
* 可选,视频输入设备的设备 ID。
|
|
929
|
-
* @param config.videoConfig.screenConfig - Optional, Screen share configuration if videoInputDeviceId is 'screenShare' see https://www.volcengine.com/docs/6348/104481#screenconfig for more details. |
|
|
930
|
-
* 可选,屏幕共享配置,如果 videoInputDeviceId 是 'screenShare',请参考 https://www.volcengine.com/docs/6348/104481#screenconfig 了解更多详情。
|
|
931
|
-
* @param config.prologueContent - Optional, Prologue content. | 可选,开场白内容。
|
|
932
|
-
* @param config.roomMode - Optional, Room mode. | 可选,房间模式。
|
|
933
|
-
*/ constructor(config){
|
|
934
|
-
super(config.debug), this._client = null, this.isConnected = false, this._isTestEnv = false, this._isSupportVideo = false;
|
|
935
|
-
this._config = config;
|
|
936
|
-
var _this__config_baseURL;
|
|
937
|
-
const defaultBaseURL = null !== (_this__config_baseURL = this._config.baseURL) && void 0 !== _this__config_baseURL ? _this__config_baseURL : 'https://api.coze.cn';
|
|
938
|
-
this._config.baseURL = defaultBaseURL;
|
|
939
|
-
// init api
|
|
940
|
-
this._api = new api_namespaceObject.CozeAPI({
|
|
941
|
-
token: this._config.accessToken,
|
|
942
|
-
baseURL: defaultBaseURL,
|
|
943
|
-
allowPersonalAccessTokenInBrowser: this._config.allowPersonalAccessTokenInBrowser
|
|
944
|
-
});
|
|
945
|
-
this._isSupportVideo = !!config.videoConfig;
|
|
1077
|
+
* en: Get the RTC engine instance, for detail visit https://www.volcengine.com/docs/6348/104481
|
|
1078
|
+
*
|
|
1079
|
+
* zh: 获取 RTC 引擎实例,详情请访问 https://www.volcengine.com/docs/6348/104481
|
|
1080
|
+
*/
|
|
1081
|
+
getRtcEngine() {
|
|
1082
|
+
var _a;
|
|
1083
|
+
return (_a = this._client) === null || _a === void 0 ? void 0 : _a.getRtcEngine();
|
|
946
1084
|
}
|
|
947
1085
|
}
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
|
|
952
|
-
|
|
1086
|
+
|
|
1087
|
+
exports.EventNames = EventNames$1;
|
|
1088
|
+
exports.RealtimeAPIError = RealtimeAPIError;
|
|
1089
|
+
exports.RealtimeClient = RealtimeClient;
|
|
1090
|
+
exports.RealtimeUtils = utils;
|