spring-projects/spring-ai · error · java.lang.IllegalArgumentException
ImagePrompt must contain at least one non-empty message
Error message
ImagePrompt must contain at least one non-empty message
What it means
GoogleGenAiImageModel.call() converts each message in the ImagePrompt into Gemini Content objects with parts, filtering out messages that produce no parts (e.g. no text and no media). If no message yields any parts, there is no usable prompt to send to generateContent, so it throws this IllegalArgumentException.
Source
Thrown at models/spring-ai-google-genai-image/src/main/java/org/springframework/ai/google/genai/image/GoogleGenAiImageModel.java:145
final GoogleGenAiImageOptions options = (GoogleGenAiImageOptions) imagePrompt.getOptions();
Assert.notNull(options, "Options must not be null");
final String model = options.getModel();
Assert.notNull(model, "Model must not be null");
final String modelName = this.connectionDetails.getModelEndpointName(model);
final GenerateContentConfig config = getGenerateContentConfig(options);
final List<Content> contents = imagePrompt.getInstructions()
.stream()
.map(GoogleGenAiImageModel::messageToParts)
.filter(Predicate.not(List::isEmpty))
.map(parts -> Content.builder().role(MessageType.USER.getValue()).parts(parts).build())
.toList();
if (contents.isEmpty()) {
throw new IllegalArgumentException("ImagePrompt must contain at least one non-empty message");
}
final GenerateContentResponse imagesResponse = RetryUtils.execute(this.retryTemplate,
() -> this.genAiClient.models.generateContent(modelName, contents, config));
final List<Candidate> candidates = Optional.ofNullable(imagesResponse)
.map(GenerateContentResponse::candidates)
.flatMap(Function.identity())
.orElse(List.of());
final List<ImageGeneration> generationList = candidates.stream()
.flatMap(GoogleGenAiImageModel::candidateToImageGenerations)
.toList();
final List<String> candidateTexts = candidates.stream()
.flatMap(candidate -> candidate.content().flatMap(Content::parts).orElse(List.of()).stream())
.filter(part -> part.inlineData().isEmpty())
.map(Part::text)View on GitHub (pinned to 98a7beda4f)
Solutions
- Validate the prompt before calling: ensure the ImagePrompt contains at least one message with non-blank text or media.
- Fix template/user-input handling so blank prompts are rejected or filled earlier.
- Wrap the call in a guard that throws a more descriptive application-level error for empty prompts.
Example fix
// before
ImageResponse res = imageModel.call(new ImagePrompt(userInput));
// after
if (!StringUtils.hasText(userInput)) {
throw new IllegalArgumentException("Image prompt text must not be blank");
}
ImageResponse res = imageModel.call(new ImagePrompt(userInput)); Defensive patterns
Strategy: validation
Validate before calling
boolean hasPrompt = prompt.getInstructions().stream()
.anyMatch(m -> StringUtils.hasText(m.getText()) || (m.getMedia() != null && !m.getMedia().isEmpty()));
if (!hasPrompt) { throw new IllegalArgumentException("ImagePrompt is empty"); } Prevention
- Validate user/template-derived prompt text for blankness before image generation.
- Check template variable rendering so prompts never resolve to empty strings.
- Add tests for empty and whitespace-only prompts.
When it happens
Trigger: Calling call(new ImagePrompt("")) or an ImagePrompt whose messages contain only empty strings / blank instructions — every message maps to an empty parts list and 'contents' ends up empty.
Common situations: Template-rendered prompts that resolved to an empty string (missing template variables); user input passed through unvalidated and blank; a refactor passing instructions as empty lists; whitespace-only prompts from form submissions.
Understand the failure class
Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.
Related errors
- No embedding input is provided - all texts are null or empty
- Image prompt instructions cannot be empty
- No embedding input is provided - instructions list is empty
- Unsupported media data type:
- think level must be one of
AI-assisted analysis of spring-projects/spring-ai@98a7beda4f (2026-09-11).
Data as JSON: /api/errors/8537b2d05e741b3f.
Report an issue: GitHub.