* Note that transcription is limited to 60 seconds audio.
* Use a GCS file for audio longer than 1 minute.
*/
-let audio;
async function transcribeSpeech (audio) {
const request = {
});
ia.setEncoding('base64');
ia.start();
-ia.on('error', (e) => {
- console.log('error recording audio', + e);
-});
ia.on('data', (chunk) => {
-
const buf = Buffer.from(chunk, 'base64');
audioInput.push(buf);
});
+const ao = new portAudio.AudioIO({
+ outOptions: {
+ sampleFormat: 16,
+ channelCount: 1,
+ sampleRate: 16000,
+ deviceId: -1,
+ closeOnError: false,
+ }
+});
+ao.start();
+
async function processAudio() {
const buf = Buffer.concat(audioInput);
+ play(audioInput);
- audioInput = [];
+ while(audioInput.length) { audioInput.pop() };
transcribeSpeech({
content: buf
});
}
+
+ function play(input) {
+ let i = 0;
+ // format buffers into half their size to account for writable highwaterMark.
+ const audio = bufSplit(input);
+ // call this fuction after last audio chunk has been written.
+ const callback = () => {
+ // TODO: clear portAudio writable buffer on write end.
+ }
+ write();
+ // iterate through audio array and write buffers to portAudio writable.
+ function write() {
+ let chunk;
+ let ok = true;
+ do {
+ chunk = audio[i];
+ if (i === audio.length - 1) {
+ // write last chunk.
+ ao.write(chunk, null, callback);
+ } else {
+ // check for backpreassure.
+ ok = ao.write(chunk, null);
+ }
+ i++;
+ } while (i < audio.length && ok);
+
+ if (i < audio.length) {
+ // Had to stop early!
+ // Write some more once it drains.
+ ao.once('drain', write);
+ }
+ }
+}
+
+// utility function used by play func
+function bufSplit(input){
+ let result = [];
+ input.forEach((b) => {
+ // split buffer into two.
+ result.push(b.slice(0, b.length / 2), b.slice(b.length / 2, b.length));
+ });
+ return result;
+}
+
setTimeout(async () => {
ia.pause();
processAudio();
- // ia.resume();
}, 3000);
setTimeout(() => {
setTimeout(async () => {
ia.pause();
processAudio();
- // ia.resume();
}, 8000);
setTimeout(() => {