tts: cap chunks at 120 chars to prevent F5 internal-chunking ref_audio bleed

This commit is contained in:
russell@unturf.com 2026-05-24 10:56:22 -04:00
parent 7a5f545c00
commit ad3568ff3c
No known key found for this signature in database

View file

@ -67,11 +67,13 @@ const AUDIO_FORMAT = detectAudioFormat();
const ttsCache = new Map(); const ttsCache = new Map();
// Split long text into chunks at sentence boundaries. // Split long text into chunks at sentence boundaries.
// F5-TTS has no input cap, but smaller chunks shorten time-to-first-audio: // IMPORTANT: F5-TTS internally chunks any input above ~135 chars (its default
// chunk 1 is intentionally small (~500 chars ~ 5s wall) so playback starts ASAP, // max_chars) and prepends the reference audio to each sub-chunk's output,
// later chunks fetch in pipeline while chunk 1 plays. // causing audible "phantom" phrases (e.g. ref text "IT IS NEVER OPENED" bleeds
const TTS_CHUNK_MAX = 2500; // upper bound per chunk (server-side comfortable) // in). Capping at 120 chars per request keeps F5 in single-chunk mode = clean
const TTS_FIRST_CHUNK_MAX = 500; // smaller first chunk for low time-to-first-audio // audio. With PlaylistAudio pipelining, more+smaller chunks also lower TTFA.
const TTS_CHUNK_MAX = 120; // upper bound per chunk (under F5's internal 135 threshold)
const TTS_FIRST_CHUNK_MAX = 120; // first chunk same — there's no win in making it smaller
// Strip patterns F5 would pronounce character-by-character (URLs, paths, emails). // Strip patterns F5 would pronounce character-by-character (URLs, paths, emails).
// F5 has no spell-vs-speak heuristic — feeding it https://foo.bar produces audible // F5 has no spell-vs-speak heuristic — feeding it https://foo.bar produces audible