From 40487d9634264e90c71d1cc128e0a398ca09464b Mon Sep 17 00:00:00 2001 From: neru Date: Tue, 13 Jan 2026 17:48:33 -0300 Subject: [PATCH] feat: add TTS module --- src/modules/tts.ts | 74 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 src/modules/tts.ts diff --git a/src/modules/tts.ts b/src/modules/tts.ts new file mode 100644 index 0000000..9668b43 --- /dev/null +++ b/src/modules/tts.ts @@ -0,0 +1,74 @@ +import path from 'path'; +import fs from 'fs'; + +import { Logger } from '../utils/log'; +import { isModule } from '../utils/misc'; + +export interface TTSResponse { + error?: string; + data?: Buffer; +} + +export interface TTSModule { + name: string; + getVoices: () => Promise | undefined>; + generate: (voice: string, text: string) => Promise; +} + +export class TTSManager { + private readonly modules: Array = []; + private readonly log: Logger; + + private constructor() { + this.log = new Logger('TTS Manager'); + const modesFolder = path.resolve(__dirname, './tts-modes'); + + fs.readdirSync(modesFolder).map( + async (file) => await this.loadModule(path.join(modesFolder, file)) + ); + } + + /* + public + */ + public getModule(name: string): TTSModule | undefined { + return this.modules.find((mod) => mod.name == name); + } + + public getModules(): TTSModule[] { + return this.modules; + } + + /* + internal + */ + private async loadModule(filePath: string): Promise { + try { + if (!isModule(filePath)) return; + + const modRaw = await import(`file://${filePath}`); + + if (!modRaw || !modRaw.default) { + this.log.warning('Invalid module format in %s', filePath); + return; + } + + const mod = modRaw.default as TTSModule; + + this.log.verbose(`Loaded TTS mode: ${mod.name}`); + this.modules.push(mod); + } catch (err) { + this.log.error('Failed to load TTS Module at %s (%s)', filePath, err); + } + } + + /* + singleton logic + */ + static #instance: TTSManager | null = null; + + public static get get(): TTSManager { + if (!TTSManager.#instance) TTSManager.#instance = new TTSManager(); + return TTSManager.#instance; + } +}