feat: add minimax tts support (#1043)
This commit is contained in:
@@ -1,6 +1,7 @@
|
||||
// Generic config-driven TTS handlers — dispatched by ttsConfig.format.
|
||||
// Each handler accepts { baseUrl, apiKey, text, modelId, voiceId } and returns { base64, format }.
|
||||
import { responseToBase64, throwUpstreamError } from "./_base.js";
|
||||
import minimaxTts from "./minimax.js";
|
||||
|
||||
// Hyperbolic: POST { text } → { audio: base64 }
|
||||
async function hyperbolic({ baseUrl, apiKey, text }) {
|
||||
@@ -164,4 +165,5 @@ export const FORMAT_HANDLERS = {
|
||||
coqui,
|
||||
tortoise,
|
||||
openai: openaiCompat,
|
||||
"minimax-tts": minimaxTts,
|
||||
};
|
||||
|
||||
59
open-sse/handlers/ttsProviders/minimax.js
Normal file
59
open-sse/handlers/ttsProviders/minimax.js
Normal file
@@ -0,0 +1,59 @@
|
||||
import { Buffer } from "node:buffer";
|
||||
|
||||
function hexToBase64(audioHex) {
|
||||
const clean = typeof audioHex === "string" ? audioHex.trim() : "";
|
||||
if (!clean) throw new Error("MiniMax TTS returned no audio");
|
||||
if (clean.length % 2 !== 0 || !/^[0-9a-f]+$/i.test(clean)) {
|
||||
throw new Error("MiniMax TTS returned invalid audio");
|
||||
}
|
||||
return Buffer.from(clean, "hex").toString("base64");
|
||||
}
|
||||
|
||||
// MiniMax T2A HTTP: returns hex-encoded audio in non-streaming mode.
|
||||
export default async function minimaxTts({ baseUrl, apiKey, text, modelId, voiceId }) {
|
||||
const res = await fetch(baseUrl, {
|
||||
method: "POST",
|
||||
headers: { "Content-Type": "application/json", "Authorization": `Bearer ${apiKey}` },
|
||||
body: JSON.stringify({
|
||||
model: modelId || "speech-2.8-hd",
|
||||
text,
|
||||
stream: false,
|
||||
language_boost: "auto",
|
||||
output_format: "hex",
|
||||
voice_setting: {
|
||||
voice_id: voiceId || "English_expressive_narrator",
|
||||
speed: 1,
|
||||
vol: 1,
|
||||
pitch: 0,
|
||||
},
|
||||
audio_setting: {
|
||||
sample_rate: 32000,
|
||||
bitrate: 128000,
|
||||
format: "mp3",
|
||||
channel: 1,
|
||||
},
|
||||
}),
|
||||
});
|
||||
|
||||
const rawText = await res.text();
|
||||
let data = {};
|
||||
if (rawText) {
|
||||
try { data = JSON.parse(rawText); } catch { data = {}; }
|
||||
}
|
||||
|
||||
const baseResp = data.base_resp || data.baseResp || {};
|
||||
const statusCode = Number(baseResp.status_code ?? baseResp.statusCode ?? 0);
|
||||
const statusMessage = baseResp.status_msg || baseResp.statusMsg || data.message || "";
|
||||
|
||||
if (!res.ok) {
|
||||
throw new Error(statusMessage || rawText || `MiniMax TTS error (${res.status})`);
|
||||
}
|
||||
if (statusCode !== 0) {
|
||||
throw new Error(statusMessage || "MiniMax TTS upstream error");
|
||||
}
|
||||
|
||||
return {
|
||||
base64: hexToBase64(data.data?.audio),
|
||||
format: data.extra_info?.audio_format || data.extraInfo?.audioFormat || "mp3",
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user