idacosta commited on
Commit
78f5cc2
·
1 Parent(s): 6390e63

Fix OpenAI TTS by chunking text to respect 4096 char limit

Browse files
Files changed (1) hide show
  1. services/podcast_service.py +18 -9
services/podcast_service.py CHANGED
@@ -104,7 +104,7 @@ def _tts_request(text: str, token: str) -> bytes | None:
104
 
105
 
106
  def _synthesize_audio(lines: list[tuple[str, str]], output_path: Path) -> bool:
107
- """Synthesize audio via OpenAI TTS. Returns True on success."""
108
  try:
109
  from openai import OpenAI
110
 
@@ -116,16 +116,25 @@ def _synthesize_audio(lines: list[tuple[str, str]], output_path: Path) -> bool:
116
 
117
  logger.info("TTS: Generating audio for %d lines (%d chars)", len(lines), len(full_text))
118
 
119
- # Call OpenAI TTS API
120
- response = client.audio.speech.create(
121
- model="tts-1",
122
- voice="alloy", # neutral voice (alternatives: echo, fable, onyx, nova, shimmer)
123
- input=full_text,
124
- )
 
 
 
 
 
 
 
 
 
125
 
126
- # Write response to file
127
  with open(str(output_path), "wb") as f:
128
- f.write(response.content)
129
 
130
  file_size = os.path.getsize(str(output_path))
131
  logger.info("Podcast audio saved to %s (%d bytes)", output_path, file_size)
 
104
 
105
 
106
  def _synthesize_audio(lines: list[tuple[str, str]], output_path: Path) -> bool:
107
+ """Synthesize audio via OpenAI TTS. Handles 4096 char limit by chunking."""
108
  try:
109
  from openai import OpenAI
110
 
 
116
 
117
  logger.info("TTS: Generating audio for %d lines (%d chars)", len(lines), len(full_text))
118
 
119
+ # OpenAI TTS has 4096 character limit, so chunk the text
120
+ MAX_CHARS = 4000 # Leave buffer for safety
121
+ chunks = _chunk_text(full_text, MAX_CHARS)
122
+ logger.info("Split into %d chunks for TTS", len(chunks))
123
+
124
+ # Generate audio for each chunk and collect them
125
+ audio_data = b""
126
+ for i, chunk in enumerate(chunks):
127
+ logger.info("TTS chunk %d/%d (%d chars)", i + 1, len(chunks), len(chunk))
128
+ response = client.audio.speech.create(
129
+ model="tts-1",
130
+ voice="alloy", # neutral voice
131
+ input=chunk,
132
+ )
133
+ audio_data += response.content
134
 
135
+ # Write combined audio to file
136
  with open(str(output_path), "wb") as f:
137
+ f.write(audio_data)
138
 
139
  file_size = os.path.getsize(str(output_path))
140
  logger.info("Podcast audio saved to %s (%d bytes)", output_path, file_size)