@coze/uniapp-api
Version:
Official Coze UniApp SDK for seamless AI integration into your applications | 扣子官方 UniApp SDK,助您轻松集成 AI 能力到应用中
166 lines (165 loc) • 5.78 kB
JavaScript
;
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.WsTranscriptionClient = void 0;
const api_1 = require("@coze/api");
const base_1 = __importDefault(require("./base"));
const pcm_recorder_1 = require("../pcm-recorder");
/**
* WebSocket transcription client for UniApp/WeChat Mini Program
* Handles speech-to-text conversion through WebSockets
*/
class WsTranscriptionClient extends base_1.default {
constructor() {
super(...arguments);
/**
* Flag to track if recording is in progress
*/
Object.defineProperty(this, "isRecording", {
enumerable: true,
configurable: true,
writable: true,
value: false
});
}
/**
* Generate a UUID for message identification
* @private
* @returns {string} - UUID string
*/
static uuid() {
return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, c => {
const r = (Math.random() * 16) | 0;
const v = c === 'x' ? r : (r & 0x3) | 0x8;
return v.toString(16);
});
}
/**
* Establish WebSocket connection and configure audio format
* @private
*/
connect() {
return __awaiter(this, void 0, void 0, function* () {
var _a;
yield this.init();
yield this.recorder.start();
const sampleRate = this.recorder.getSampleRate();
(_a = this.ws) === null || _a === void 0 ? void 0 : _a.send({
id: WsTranscriptionClient.uuid(),
event_type: api_1.WebsocketsEventType.TRANSCRIPTIONS_UPDATE,
data: {
input_audio: {
format: 'pcm',
codec: 'pcm',
sample_rate: sampleRate,
channel: 1,
bit_depth: 16,
},
},
});
});
}
/**
* Clean up resources and close connections
*/
destroy() {
this.recorder.destroy();
this.listeners.clear();
this.closeWs();
}
/**
* Get current recording status
* @returns {string} - Current status: 'recording', 'paused', or 'ended'
*/
getStatus() {
if (this.isRecording) {
if (this.recorder.getStatus() === pcm_recorder_1.RecordingStatus.PAUSED) {
return 'paused';
}
return 'recording';
}
return 'ended';
}
/**
* Start recording and transcription
*/
start() {
return __awaiter(this, void 0, void 0, function* () {
if (this.getStatus() === 'recording') {
throw new Error('Recording is already started');
}
yield this.connect();
yield this.recorder.record({
pcmAudioCallback: data => {
var _a;
const { raw } = data;
// Convert ArrayBuffer to base64 string for UniApp
const base64String = this.arrayBufferToBase64(raw);
// Send audio to WebSocket
(_a = this.ws) === null || _a === void 0 ? void 0 : _a.send({
id: WsTranscriptionClient.uuid(),
event_type: api_1.WebsocketsEventType.INPUT_AUDIO_BUFFER_APPEND,
data: {
delta: base64String,
},
});
},
});
this.isRecording = true;
});
}
/**
* Convert ArrayBuffer to base64 string (WeChat Mini Program compatible)
* @param {ArrayBuffer} buffer - The ArrayBuffer to convert
* @returns {string} - Base64 string
* @private
*/
arrayBufferToBase64(buffer) {
// Use UniApp's method to convert ArrayBuffer to base64
return uni.arrayBufferToBase64(buffer);
}
/**
* Stop recording and complete transcription
*/
stop() {
var _a;
(_a = this.ws) === null || _a === void 0 ? void 0 : _a.send({
id: WsTranscriptionClient.uuid(),
event_type: api_1.WebsocketsEventType.INPUT_AUDIO_BUFFER_COMPLETE,
});
this.recorder.destroy();
this.closeWs();
this.isRecording = false;
}
/**
* Pause recording (retain context)
*/
pause() {
if (this.getStatus() !== 'recording') {
throw new Error('Recording is not started');
}
return this.recorder.pause();
}
/**
* Resume recording after pause
*/
resume() {
if (this.getStatus() !== 'paused') {
throw new Error('Recording is not paused');
}
return this.recorder.resume();
}
}
exports.WsTranscriptionClient = WsTranscriptionClient;
exports.default = WsTranscriptionClient;