linshenkx/prompt-optimizer · error · Error
Failed to decode image data URL payload
Error message
Failed to decode image data URL payload
What it means
After FileReader.readAsDataURL produces a data URL, parseDataUrlPayload extracts the base64 and MIME parts. If parsing yields no b64 component the function throws, meaning the data URL was malformed (empty result, missing comma, unparsable header) and the payload could not be recovered.
Source
Thrown at packages/ui/src/utils/image-asset-storage.ts:122
return { b64, mimeType: finalMimeType }
}
if (typeof FileReader === 'undefined') {
throw new Error('FileReader is not available to decode image payload')
}
const blob = new Blob([ab], { type: finalMimeType })
const dataUrl = await new Promise<string>((resolve, reject) => {
const reader = new FileReader()
reader.onerror = () => reject(new Error('Failed to read image blob'))
reader.onload = () => resolve(String(reader.result || ''))
reader.readAsDataURL(blob)
})
const parsed = parseDataUrlPayload(dataUrl)
if (!parsed?.b64) {
throw new Error('Failed to decode image data URL payload')
}
return {
b64: parsed.b64,
mimeType: parsed.mimeType || finalMimeType,
}
}
export const normalizeImageSourceToPayload = async (
source: string,
): Promise<ImagePayload | null> => {
const raw = String(source || '').trim()
if (!raw) return null
const dataUrlPayload = parseDataUrlPayload(raw)
if (dataUrlPayload) return dataUrlPayload
if (/^https?:\/\//u.test(raw)) {View on GitHub (pinned to 3e677b1d9f)
Solutions
- Inspect the fetched response: log content-type and byte length; a 200 with empty body commonly causes this
- Validate bytes.length > 0 before requesting payload conversion
- If using a FileReader polyfill, ensure it emits standard 'data:<mime>;base64,<data>' output
- Fall back to Buffer/btoa-based encoding when the data URL path fails
Example fix
// before
const payload = await normalizeImageSourceToPayload(url) // empty 200 body -> throws
// after
const resp = await fetch(url)
if (!resp.ok || (await resp.clone().arrayBuffer()).byteLength === 0) {
throw new Error('Empty image response')
}
const payload = await normalizeImageSourceToPayload(url) Defensive patterns
Strategy: validation
Validate before calling
const resp = await fetch(url)
const ab = await resp.arrayBuffer()
if (ab.byteLength === 0) throw new Error('Empty image response')
// only then hand off to payload normalization Type guard
const isWellFormedDataUrl = (s: string): boolean =>
/^data:[\w./+-]+;base64,[A-Za-z0-9+/]+={0,2}$/.test(s) Try / catch
try { await fetchImagePayloadFromUrl(url) } catch (e) { if (e.message === 'Failed to decode image data URL payload') { /* check empty body / polyfill, retry with btoa path */ } else throw e } Prevention
- Treat 200-with-empty-body as an error before decoding
- Validate data URL shape after readAsDataURL
- Ensure FileReader polyfills emit standard base64 data URLs
When it happens
Trigger: FileReader resolves with an empty or non-standard result string (e.g. '' from a zero-byte blob), a data URL without the 'data:...;base64,' structure, or readAsDataURL returning a plain-URL result for unusual MIME types; parseDataUrlPayload then returns null/empty and the guard fires.
Common situations: Zero-byte responses from a failing server with 200 status; exotic MIME types where the browser emits a non-standard data URL; reader.result being unexpectedly coerced (String(reader.result || '') masking undefined); custom FileReader polyfills emitting wrong formats.
Understand the failure class
- Parsing and encoding errors: unexpected token, malformed input — why parsers reject input and how to find the real culprit.
Related errors
- FileReader is not available to decode image payload
- Failed to parse evaluation result: no valid score JSON or re
- Evaluation result is not a valid object.
- Evaluation result is missing the "score" field.
- Evaluation result is missing score for "${fieldName}".
AI-assisted analysis of linshenkx/prompt-optimizer@3e677b1d9f (2026-08-27).
Data as JSON: /api/errors/3a233217f63b5fc5.
Report an issue: GitHub.