spring-projects/spring-ai · warning
No speech response returned for request: + requestContext.re
Error message
No speech response returned for request: + requestContext.request
What it means
Warning logged by ElevenLabsTextToSpeechModel.call() inside the retry-wrapped request when the textToSpeech HTTP response has a null body. The method returns an empty byte[0] audio payload in the TextToSpeechResponse rather than throwing, so callers may silently write/play zero-length audio.
Source
Thrown at models/spring-ai-elevenlabs/src/main/java/org/springframework/ai/elevenlabs/ElevenLabsTextToSpeechModel.java:82
this.elevenLabsApi = elevenLabsApi;
this.options = options;
this.retryTemplate = retryTemplate;
}
public static Builder builder() {
return new Builder();
}
@Override
public TextToSpeechResponse call(TextToSpeechPrompt prompt) {
RequestContext requestContext = prepareRequest(prompt);
byte[] audioData = RetryUtils.execute(this.retryTemplate, () -> {
var response = this.elevenLabsApi.textToSpeech(requestContext.request, requestContext.voiceId,
requestContext.queryParameters);
if (response.getBody() == null) {
if (logger.isWarnEnabled()) {
logger.warn("No speech response returned for request: " + requestContext.request);
}
return new byte[0];
}
return response.getBody();
});
return new TextToSpeechResponse(List.of(new Speech(audioData)));
}
@Override
public Flux<TextToSpeechResponse> stream(TextToSpeechPrompt prompt) {
RequestContext requestContext = prepareRequest(prompt);
return RetryUtils.execute(this.retryTemplate, () -> this.elevenLabsApi
.textToSpeechStream(requestContext.request, requestContext.voiceId, requestContext.queryParameters)
.map(entity -> new TextToSpeechResponse(List.of(new Speech(Objects.requireNonNull(entity.getBody()))))));
}
View on GitHub (pinned to 98a7beda4f)
Solutions
- Verify the ElevenLabs API key and remaining character quota in your account dashboard.
- Confirm the voiceId passed in the request context still exists in your ElevenLabs account.
- Check the raw HTTP response with an interceptor; a 4xx body may be swallowed as null by generic error handling.
- Treat byte[0] speech output as failure in application code and retry or surface an error.
Example fix
// before
byte[] audio = ttsModel.call(new TextToSpeechRequest(text, voiceId, null)).getAudio();
FileOutputStream out = new FileOutputStream(f); // writes empty file silently
// after
if (audio == null || audio.length == 0) throw new IllegalStateException("TTS returned no audio"); Defensive patterns
Strategy: try-catch
Validate before calling
// pre-flight: verify voiceId exists and quota remains assert voiceId != null && !voiceId.isBlank();
Type guard
static boolean hasAudio(TextToSpeechResponse r) {
return r != null && r.getSpeech() != null && r.getSpeech().stream().anyMatch(s -> s.getAudio() != null && s.getAudio().length > 0);
} Try / catch
TextToSpeechResponse r = ttsModel.call(req);
if (!hasAudio(r)) throw new IllegalStateException("ElevenLabs returned no audio; check quota/key/voiceId"); Prevention
- Monitor ElevenLabs character quota programmatically
- Cache voice IDs and validate them against the voices endpoint
- Never write audio bytes to disk without a length check
When it happens
Trigger: elevenLabsApi.textToSpeech(requestContext.request, voiceId, queryParameters) returns a ResponseEntity whose getBody() is null — empty response body from ElevenLabs, or deserialization yielding null after retries.
Common situations: Exhausted ElevenLabs quota (Free tier limits) returning unusual empty responses; invalid or deleted voiceId; API outage or gateway stripping the body; expired/invalid API key returning an unexpected empty 2xx.
Related errors
- No speech response returned for prompt: + prompt
- Failed to read audio speech response
- Failed to read resource:
- Unsupported audio data type:
- Image generation failed: no image returned
AI-assisted analysis of spring-projects/spring-ai@98a7beda4f (2026-09-11).
Data as JSON: /api/errors/489e0f90978e2e6c.
Report an issue: GitHub.