nopSolutions/nopCommerce · error · NopException

Cannot decode picture binary (file name: {fileName})

Error message

Cannot decode picture binary (file name: {fileName})

What it means

Thrown by PictureService.ValidatePictureAsync, which wraps the entire image decode+resize in try/catch. It decodes the binary via SkiaSharp (SKCodec/SKBitmap.Decode) and resizes if it exceeds MaximumImageSize. Any exception from decode/resizing is rethrown as NopException with the file name. The root cause is inside the inner exception — typically an unsupported/corrupt image format.

Source

Thrown at src/Libraries/Nop.Services/Media/PictureService.cs:1030

                using var input = new MemoryStream(pictureBinary);
                using var codec = SKCodec.Create(input);
                image = AutoOrient(SKBitmap.Decode(codec), codec.EncodedOrigin);
            }
            else
                image = SKBitmap.Decode(pictureBinary);

            //resize the image in accordance with the maximum size
            if (Math.Max(image.Height, image.Width) <= _mediaSettings.MaximumImageSize)
                return Task.FromResult(pictureBinary);

            var format = GetImageFormatByMimeType(mimeType);
            pictureBinary = ImageResize(image, format, _mediaSettings.MaximumImageSize);

            return Task.FromResult(pictureBinary);
        }
        catch (Exception exc)
        {
            throw new NopException($"Cannot decode picture binary (file name: {fileName})", exc);
        }
    }

    /// <summary>
    /// Get product picture (for shopping cart and order details pages)
    /// </summary>
    /// <param name="product">Product</param>
    /// <param name="attributesXml">Attributes (in XML format)</param>
    /// <returns>
    /// A task that represents the asynchronous operation
    /// The task result contains the picture
    /// </returns>
    public virtual async Task<Picture> GetProductPictureAsync(Product product, string attributesXml)
    {
        ArgumentNullException.ThrowIfNull(product);

        //first, try to get product attribute combination picture
        var combination = await _productAttributeParser.FindProductAttributeCombinationAsync(product, attributesXml);

View on GitHub (pinned to 64bdf2ff08)

Solutions

  1. Inspect the inner exception (exc) for the exact SkiaSharp error and the true cause.
  2. Validate the file is a real image of a supported type (JPEG/PNG/GIF/BMP/WebP) before uploading.
  3. Re-save/convert the source image to a supported format and retry.
  4. Ensure the deployed SkiaSharp native binaries match the runtime platform so codecs load.
  5. Reject zero-length or undersized uploads at the client/API boundary.

Example fix

// before
public virtual Task<byte[]> ValidatePictureAsync(byte[] pictureBinary, string mimeType, string fileName)
{
    try { /* decode + resize */ }
    catch (Exception exc)
    {
        throw new NopException($"Cannot decode picture binary (file name: {fileName})", exc);
    }
}

// after - pre-validate before decoding
if (pictureBinary is null || pictureBinary.Length == 0)
    throw new NopException($"Empty picture binary (file name: {fileName})");
using var probe = new MemoryStream(pictureBinary);
using var codec = SKCodec.Create(probe);
if (codec is null)
    throw new NopException($"Unsupported image format (file name: {fileName})");
Defensive patterns

Strategy: validation

Validate before calling

// Validate the binary is a decodable image of a supported type before ValidatePictureAsync
if (pictureBinary is null || pictureBinary.Length == 0)
    return Error($"Empty picture binary (file name: {fileName})");
using var probe = new MemoryStream(pictureBinary);
using var codec = SKCodec.Create(probe);
if (codec is null || !_supportedMimes.Contains(codec.EncodedFormat.ToString().ToLower()))
    return Error($"Unsupported or corrupt image (file name: {fileName})");

Type guard

static bool IsDecodableImage(byte[] bytes)
{
    if (bytes is null || bytes.Length == 0) return false;
    try { using var ms = new MemoryStream(bytes); return SKCodec.Create(ms) is not null; }
    catch { return false; }
}

Try / catch

try { var validated = await _pictureService.ValidatePictureAsync(binary, mime, fileName); }
catch (NopException ex) when (ex.Message.StartsWith("Cannot decode picture binary"))
{ /* inspect ex.InnerException for the SkiaSharp cause; reject the upload with a user-facing message */ }

Prevention

When it happens

Trigger: Uploading a file whose bytes are not a decodable image (wrong MIME type, corrupt file, unsupported codec such as certain TIFF/HEIF, or a zero-length file) so SKBitmap.Decode/SKCodec.Create throws.

Common situations: User uploads a renamed non-image (e.g. .jpg that is actually a PDF); truncated/corrupt upload; SkiaSharp build lacking the codec for the format; very large image causing decode failure; empty stream.

Related errors


AI-assisted analysis of nopSolutions/nopCommerce@64bdf2ff08 (2026-08-13). Data as JSON: /api/errors/9ce2e07c76c70a77. Report an issue: GitHub.