HeyPuter/puter · warning · HttpError

bad_request

bad_request

Error message

`prompt` must be a non-empty string

What it means

The xAI (Grok Imagine) image provider rejects calls where the prompt parameter is not a non-empty string. This validation (line 74) runs after the test_mode short-circuit and before any upstream API call, ensuring the xAI API receives valid text input.

Source

Thrown at src/backend/drivers/ai-image/providers/xai/XAIImageProvider.ts:75

    }

    getDefaultModel(): string {
        return DEFAULT_MODEL;
    }

    async generate(params: IGenerateParams): Promise<string> {
        const { prompt, test_mode, model, ratio, quality } = params;
        let { input_images } = params;
        const { input_image, input_image_mime_type } = params;

        const selectedModel = this.#getModel(model);

        if (test_mode) {
            return 'https://puter-sample-data.puter.site/image_example.png';
        }

        if (typeof prompt !== 'string' || prompt.trim().length === 0) {
            throw new HttpError(400, '`prompt` must be a non-empty string', {
                legacyCode: 'bad_request',
            });
        }

        // Backwards compat: fold singular `input_image` into `input_images`.
        if (input_image && (!input_images || input_images.length === 0)) {
            input_images = [input_image];
        }
        // xAI caps edits at 3 source images.
        if (input_images && input_images.length > MAX_INPUT_IMAGES) {
            input_images = input_images.slice(0, MAX_INPUT_IMAGES);
        }
        const inputImageCount = input_images?.length ?? 0;
        const hasInputImages = inputImageCount > 0;

        // xAI uses a `resolution` tier ('1k'/'2k') rather than a pixel size.
        const resolution = this.#normalizeResolution(quality);
        const aspectRatio = this.#aspectRatio(ratio);

View on GitHub (pinned to 908ec23eda)

Solutions

  1. Ensure prompt is a trimmed non-empty string before calling generate().
  2. Validate input on the client side and disable the submit button when the prompt is empty.
  3. Set a sensible default or reject the request early.

Example fix

// before
const url = await provider.generate({ prompt: formData.prompt });

// after
const prompt = (formData.prompt ?? '').trim();
if (!prompt) throw new Error('Prompt cannot be empty');
const url = await provider.generate({ prompt });
Defensive patterns

Strategy: validation

Validate before calling

function validatePrompt(prompt: unknown): string {
  if (typeof prompt !== 'string' || prompt.trim().length === 0) {
    throw new Error('prompt must be a non-empty string');
  }
  return prompt.trim();
}
// Use before calling generate:
const cleanPrompt = validatePrompt(params.prompt);

Type guard

function isValidPrompt(value: unknown): value is string {
  return typeof value === 'string' && value.trim().length > 0;
}

Prevention

When it happens

Trigger: Calling generate() with prompt set to undefined, null, an empty string, a whitespace-only string, or a non-string type. This check mirrors the same validation in the Together and Replicate providers.

Common situations: Empty prompt from a UI text field that was not validated; undefined prompt variable due to a missing property in the params object; prompt set to a falsy value by conditional logic upstream.

Related errors


AI-assisted analysis of HeyPuter/puter@908ec23eda (2026-08-12). Data as JSON: /api/errors/f45625e6f0b7d6c2. Report an issue: GitHub.