@jambonz/speech-utils 0.0.14 → 0.0.16
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/lib/synth-audio.js +32 -4
- package/package.json +2 -2
package/lib/synth-audio.js
CHANGED
|
@@ -30,9 +30,27 @@ const {
|
|
|
30
30
|
const {SynthesizeSpeechRequest} = require('../stubs/riva/proto/riva_tts_pb');
|
|
31
31
|
const {AudioEncoding} = require('../stubs/riva/proto/riva_audio_pb');
|
|
32
32
|
const debug = require('debug')('jambonz:realtimedb-helpers');
|
|
33
|
-
const EXPIRES = (process.env.JAMBONES_TTS_CACHE_DURATION_MINS ||
|
|
33
|
+
const EXPIRES = (process.env.JAMBONES_TTS_CACHE_DURATION_MINS || 4 * 60) * 60; // cache tts for 4 hours
|
|
34
34
|
const TMP_FOLDER = '/tmp';
|
|
35
35
|
|
|
36
|
+
|
|
37
|
+
const trimTrailingSilence = (buffer) => {
|
|
38
|
+
assert.ok(buffer instanceof Buffer, 'trimTrailingSilence - argument is not a Buffer');
|
|
39
|
+
|
|
40
|
+
let offset = buffer.length;
|
|
41
|
+
while (offset > 0) {
|
|
42
|
+
// Get 16-bit value from the buffer (read in reverse)
|
|
43
|
+
const value = buffer.readUInt16BE(offset - 2);
|
|
44
|
+
if (value !== 0) {
|
|
45
|
+
break;
|
|
46
|
+
}
|
|
47
|
+
offset -= 2;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// Trim the silence from the end
|
|
51
|
+
return offset === buffer.length ? buffer : buffer.subarray(0, offset);
|
|
52
|
+
};
|
|
53
|
+
|
|
36
54
|
/**
|
|
37
55
|
* Synthesize speech to an mp3 file, and also cache the generated speech
|
|
38
56
|
* in redis (base64 format) for 24 hours so as to avoid unnecessarily paying
|
|
@@ -104,7 +122,12 @@ async function synthAudio(client, logger, stats, { account_sid,
|
|
|
104
122
|
text
|
|
105
123
|
});
|
|
106
124
|
let filePath;
|
|
107
|
-
if (['nuance', 'nvidia'].includes(vendor)
|
|
125
|
+
if (['nuance', 'nvidia'].includes(vendor) ||
|
|
126
|
+
(
|
|
127
|
+
process.env.JAMBONES_TTS_TRIM_SILENCE &&
|
|
128
|
+
['microsoft', 'azure'].includes(vendor)
|
|
129
|
+
)
|
|
130
|
+
) {
|
|
108
131
|
filePath = `${TMP_FOLDER}/${key.replace('tts:', `tts-${salt || ''}`)}.r8`;
|
|
109
132
|
}
|
|
110
133
|
else filePath = `${TMP_FOLDER}/${key.replace('tts:', `tts-${salt || ''}`)}.mp3`;
|
|
@@ -284,6 +307,7 @@ const synthMicrosoft = async(logger, {
|
|
|
284
307
|
}) => {
|
|
285
308
|
try {
|
|
286
309
|
const {api_key: apiKey, region, use_custom_tts, custom_tts_endpoint} = credentials;
|
|
310
|
+
const trimSilence = filePath.endsWith('.r8');
|
|
287
311
|
let content = text;
|
|
288
312
|
const speechConfig = SpeechConfig.fromSubscription(apiKey, region);
|
|
289
313
|
speechConfig.speechSynthesisLanguage = language;
|
|
@@ -297,7 +321,9 @@ const synthMicrosoft = async(logger, {
|
|
|
297
321
|
*/
|
|
298
322
|
if (!content.startsWith('<speak')) content = `<speak>${text}</speak>`;
|
|
299
323
|
}
|
|
300
|
-
speechConfig.speechSynthesisOutputFormat =
|
|
324
|
+
speechConfig.speechSynthesisOutputFormat = trimSilence ?
|
|
325
|
+
SpeechSynthesisOutputFormat.Raw8Khz16BitMonoPcm :
|
|
326
|
+
SpeechSynthesisOutputFormat.Audio16Khz32KBitRateMonoMp3;
|
|
301
327
|
const synthesizer = new SpeechSynthesizer(speechConfig);
|
|
302
328
|
|
|
303
329
|
if (content.startsWith('<speak>')) {
|
|
@@ -323,7 +349,9 @@ const synthMicrosoft = async(logger, {
|
|
|
323
349
|
reject(cancellation.errorDetails);
|
|
324
350
|
break;
|
|
325
351
|
case ResultReason.SynthesizingAudioCompleted:
|
|
326
|
-
|
|
352
|
+
let buffer = Buffer.from(result.audioData);
|
|
353
|
+
if (trimSilence) buffer = trimTrailingSilence(buffer);
|
|
354
|
+
resolve(buffer);
|
|
327
355
|
synthesizer.close();
|
|
328
356
|
stats.increment('tts.count', ['vendor:microsoft', 'accepted:yes']);
|
|
329
357
|
break;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jambonz/speech-utils",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.16",
|
|
4
4
|
"description": "TTS-related speech utilities for jambonz",
|
|
5
5
|
"main": "index.js",
|
|
6
6
|
"author": "Dave Horton",
|
|
@@ -24,7 +24,7 @@
|
|
|
24
24
|
},
|
|
25
25
|
"homepage": "https://github.com/jambonz/speech-utils#readme",
|
|
26
26
|
"dependencies": {
|
|
27
|
-
"@aws-sdk/client-polly": "^3.
|
|
27
|
+
"@aws-sdk/client-polly": "^3.347.1",
|
|
28
28
|
"@google-cloud/text-to-speech": "^4.2.1",
|
|
29
29
|
"@grpc/grpc-js": "^1.8.13",
|
|
30
30
|
"bent": "^7.3.12",
|