Intervention/image · error · ImageDecoderException
Failed to decode image from stream, could be unsupported ima
Error message
Failed to decode image from stream, could be unsupported image format
What it means
The stream was read fully into memory, but no decoder in the GD chain could interpret the bytes, so the generic DecoderException is rethrown as ImageDecoderException with the 'could be unsupported image format' hint. The problem is the content, not the stream handling.
Source
Thrown at src/Drivers/Gd/Decoders/StreamImageDecoder.php:65
$result = rewind($input);
if ($result === false) {
throw new StreamException('Failed to rewind position of stream');
}
while (!feof($input)) {
$chunk = fread($input, 1024);
if ($chunk === false) {
throw new StreamException('Failed to read image from stream');
}
$contents .= $chunk;
}
try {
return parent::decode($contents);
} catch (DecoderException) {
throw new ImageDecoderException(
'Failed to decode image from stream, could be unsupported image format',
);
}
}
}
View on GitHub (pinned to 5598b9e397)
Solutions
- Sniff the buffered content with (new finfo())->buffer($contents) before decoding
- Check gd_info() for the required format support in that environment
- Switch to the Imagick driver for broader format coverage
- Catch ImageDecoderException and reject the source with a clear upstream error
Example fix
// before
$image = $manager->decodeStream($socketStream);
// after
$contents = stream_get_contents($socketStream);
$mime = (new finfo())->buffer($contents);
if (!str_starts_with($mime, 'image/')) {
throw new RuntimeException('Stream did not contain an image: ' . $mime);
}
$image = $manager->read($contents); Defensive patterns
Strategy: try-catch
Validate before calling
$contents = stream_get_contents($fp);
if (!str_starts_with((new finfo())->buffer($contents), 'image/')) {
throw new RuntimeException('Stream content is not an image');
}
$manager->read($contents); Try / catch
try {
$image = $manager->decodeStream($fp);
} catch (ImageDecoderException $e) {
// sniff buffered content, then reject or fall back to Imagick driver
} Prevention
- Sniff bytes at trust boundaries (queues, sockets) before decoding
- Know your GD build's supported formats via gd_info()
- Keep an Imagick fallback for broader format coverage
When it happens
Trigger: Streaming WebP or AVIF bytes into a GD build without that format support; binary garbage (archives, encrypted payloads) fed as an image stream; a truncated file that still finished reading.
Common situations: Microservices receiving image bytes over queues or sockets without MIME validation, GD builds missing webp on older distros, processing files by naming convention instead of sniffing content.
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
- Unsupported media type (MIME) ${mediaType}.
- SplFileInfo contains unsupported image type
- Image source must be a resource of type 'file' or 'stream'
- Failed to rewind position of stream
- Failed to read image from stream
AI-assisted analysis of Intervention/image@5598b9e397 (2026-08-23).
Data as JSON: /api/errors/1e3be54c66a50d49.
Report an issue: GitHub.