Skip to content

More fine-grained error management than ImageFile.LOAD_TRUNCATED_IMAGES = True #9354

@NHOrus

Description

@NHOrus

What did you do?

I am working with existing large archive of images, and need to open them to make hashes.
Some images are malformed from the source, some are truncated due to download errors. Whole processing pipeline should be read-only in respect to the archive.

What did you expect to happen?

Being able to selectively tell Pillow what Color profile 'iCCP' and image metadata 'eXIf' chunks in PNG images are not exception-worthy and can be safely replaced with None, while all other problems should have exception raised, so the script crashes and alerts me.

What actually happened?

https://gitlab.com/NHOrus/phash_indexer/-/blob/8c8925413463fe4f892456d72de3fe34cdf2bdae/utils.py#L43-L58
I can only disable verification globally, which induces possibility of silently skipping over unwanted errors.

What are your OS, Python and Pillow versions?

  • OS: openSUSE Tumbleweed 20251225
  • Python: Python 3.13.9
  • Pillow: 12.0.0
python3 -m PIL.report                                                                
--------------------------------------------------------------------
Pillow 12.0.0
Python 3.13.9 (main, Nov 23 2025, 01:32:31) [GCC]
--------------------------------------------------------------------
Python executable is /usr/bin/python3
System Python files loaded from /usr
--------------------------------------------------------------------
Python Pillow modules loaded from /home/nho/.local/lib/python3.13/site-packages/PIL
Binary Pillow modules loaded from /home/nho/.local/lib/python3.13/site-packages/PIL
--------------------------------------------------------------------
--- PIL CORE support ok, compiled for 12.0.0
--- TKINTER support ok, loaded 8.6
--- FREETYPE2 support ok, loaded 2.14.1
--- LITTLECMS2 support ok, loaded 2.17
--- WEBP support ok, loaded 1.6.0
--- AVIF support ok, loaded 1.3.0
--- JPEG support ok, compiled for libjpeg-turbo 3.1.2
--- OPENJPEG (JPEG2000) support ok, loaded 2.5.4
--- ZLIB (PNG/ZIP) support ok, loaded 1.3.1, compiled for zlib-ng 2.2.5
--- LIBTIFF support ok, loaded 4.7.1
--- RAQM (Bidirectional Text) support ok, loaded 0.10.3, fribidi 1.0.15, harfbuzz 12.1.0
*** LIBIMAGEQUANT (Quantization method) support not installed
--- XCB (X protocol) support ok
--------------------------------------------------------------------

def hash_image(image: io.BufferedReader) -> int:
    img: Image.Image
    try:
        img = Image.open(image)
    except UnidentifiedImageError:
        image.seek(0)
        if PngImagePlugin._accept(image.read(8)):
            image.seek(0)
            try:
                img = PngImagePlugin.PngImageFile(image)
            except SyntaxError as ex:
                permissible_msgs = ["bad header checksum in b'iCCP'", "CRC error in chunk eXIf", "bad header checksum in b'eXIf'"]
                if any(msg in str(ex) for msg in permissible_msgs):
                    store = ImageFile.LOAD_TRUNCATED_IMAGES
                    ImageFile.LOAD_TRUNCATED_IMAGES = True
                    image.seek(0)
                    img = PngImagePlugin.PngImageFile(image)
                    ImageFile.LOAD_TRUNCATED_IMAGES = store
                else:
                    raise
        else:
            raise
    imgHash = str(imagehash.dhash(img))
    return twos_complement(imgHash, 64) #convert from hexadecimal to 64 bit signed integer

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions