Skip to content

Commit 68e72f3

Browse files
authored
Improve error handling
2 parents b428dc3 + 125cdd1 commit 68e72f3

File tree

3 files changed

+37
-35
lines changed

3 files changed

+37
-35
lines changed

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@picovoice/web-voice-processor",
3-
"version": "4.0.4",
3+
"version": "4.0.5",
44
"description": "Real-time audio processing for voice, in web browsers",
55
"entry": "src/index.ts",
66
"module": "dist/esm/index.js",

src/polyfill/audioworklet_polyfill.ts

Lines changed: 32 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -19,38 +19,40 @@ type ProcessorPolyfill = {
1919
window.AudioContext = window.AudioContext || window.webkitAudioContext;
2020

2121
if (typeof AudioWorkletNode !== 'function' || !('audioWorklet' in AudioContext.prototype)) {
22-
// @ts-ignore
23-
AudioContext.prototype.audioWorklet = {
24-
addModule: async function(moduleURL: string | URL, options?: WorkletOptions): Promise<void> {
25-
return;
26-
},
27-
};
28-
29-
// @ts-ignore
30-
// eslint-disable-next-line no-native-reassign
31-
window.AudioWorkletNode = function(context: AudioContext, processorName: string, options: any): ScriptProcessorNode {
32-
const { numberOfChannels = 1, frameLength = 512 } = options && options.processorOptions;
33-
const scriptProcessor: ScriptProcessorNode & ProcessorPolyfill = context.createScriptProcessor(frameLength, numberOfChannels, numberOfChannels);
34-
35-
if (!scriptProcessor.port) {
36-
scriptProcessor.port = {};
37-
}
38-
39-
scriptProcessor.onaudioprocess = (event: AudioProcessingEvent): void => {
40-
if (scriptProcessor.port && scriptProcessor.port.onmessage) {
41-
const buffer = [];
42-
for (let i = 0; i < event.inputBuffer.numberOfChannels; i++) {
43-
buffer.push(event.inputBuffer.getChannelData(i));
44-
}
45-
scriptProcessor.port.onmessage({ data: { buffer } } as MessageEvent);
46-
}
22+
if (AudioContext) {
23+
// @ts-ignore
24+
AudioContext.prototype.audioWorklet = {
25+
addModule: async function(moduleURL: string | URL, options?: WorkletOptions): Promise<void> {
26+
return;
27+
},
4728
};
4829

4930
// @ts-ignore
50-
scriptProcessor.port.close = (): void => {
51-
return;
52-
};
31+
// eslint-disable-next-line no-native-reassign
32+
window.AudioWorkletNode = function(context: AudioContext, processorName: string, options: any): ScriptProcessorNode {
33+
const { numberOfChannels = 1, frameLength = 512 } = options && options.processorOptions;
34+
const scriptProcessor: ScriptProcessorNode & ProcessorPolyfill = context.createScriptProcessor(frameLength, numberOfChannels, numberOfChannels);
35+
36+
if (!scriptProcessor.port) {
37+
scriptProcessor.port = {};
38+
}
5339

54-
return scriptProcessor;
55-
};
40+
scriptProcessor.onaudioprocess = (event: AudioProcessingEvent): void => {
41+
if (scriptProcessor.port && scriptProcessor.port.onmessage) {
42+
const buffer = [];
43+
for (let i = 0; i < event.inputBuffer.numberOfChannels; i++) {
44+
buffer.push(event.inputBuffer.getChannelData(i));
45+
}
46+
scriptProcessor.port.onmessage({ data: { buffer } } as MessageEvent);
47+
}
48+
};
49+
50+
// @ts-ignore
51+
scriptProcessor.port.close = (): void => {
52+
return;
53+
};
54+
55+
return scriptProcessor;
56+
};
57+
}
5658
}

src/web_voice_processor.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -97,15 +97,15 @@ export class WebVoiceProcessor {
9797
if (engine.worker.postMessage && typeof engine.worker.postMessage === 'function') {
9898
this.instance()._engines.add(engine);
9999
} else {
100-
throw new Error("Engine must have a 'onmessage' handler.");
100+
throw new WvpError("InvalidEngine", "Engine must have a 'onmessage' handler.");
101101
}
102102
} else {
103103
if (engine.postMessage && typeof engine.postMessage === 'function') {
104104
this.instance()._engines.add(engine);
105105
} else if (engine.onmessage && typeof engine.onmessage === 'function') {
106106
this.instance()._engines.add(engine);
107107
} else {
108-
throw new Error("Engine must have a 'onmessage' handler.");
108+
throw new WvpError("InvalidEngine", "Engine must have a 'onmessage' handler.");
109109
}
110110
}
111111
}
@@ -200,7 +200,7 @@ export class WebVoiceProcessor {
200200
'PermissionError',
201201
'Failed to record audio: microphone permissions denied.'
202202
);
203-
} else if (error.name === 'NotFoundError') {
203+
} else if (error.name === 'NotFoundError' || error.name === 'OverconstrainedError') {
204204
throw new WvpError(
205205
'DeviceMissingError',
206206
'Failed to record audio: audio recording device was not found.'
@@ -303,7 +303,7 @@ export class WebVoiceProcessor {
303303
options: WebVoiceProcessorOptions,
304304
) {
305305
if (navigator.mediaDevices === undefined) {
306-
throw new Error("Audio recording is not allowed or disabled.");
306+
throw new WvpError("DeviceDisabledError", "Audio recording is not allowed or disabled.");
307307
}
308308

309309
const {

0 commit comments

Comments
 (0)