""" Part of the bsie module. A copy of the license is provided with the project. Author: Matthias Baumgartner, 2022 """ # standard imports from functools import partial import typing # external imports import PIL.Image import rawpy # bsie imports from bsie.utils import errors, filematcher # inner-module imports from . import utils from .. import base # constants MATCH_RULE = 'mime={image/x-nikon-nef} | extension={nef}' # exports __all__: typing.Sequence[str] = ( 'RawpyPreviewReader', ) ## code ## class RawpyPreviewReader(base.Reader): """Produce previews for raw image files using the rawpy library.""" # file matcher _match: filematcher.Matcher # additional kwargs to rawpy's postprocess _rawpy_kwargs: typing.Dict[str, typing.Any] def __init__(self, **rawpy_kwargs): match_rule = rawpy_kwargs.pop('file_match_rule', MATCH_RULE) self._match = filematcher.parse(match_rule) self._rawpy_kwargs = rawpy_kwargs def __call__(self, path: str) -> typing.Callable[[int], PIL.Image.Image]: # perform quick checks first if not self._match(path): raise errors.UnsupportedFileFormatError(path) try: # open file with rawpy ary = rawpy.imread(path).postprocess(**self._rawpy_kwargs) # convert to PIL.Image img = PIL.Image.fromarray(ary) # return callback return partial(utils.resize, img) except (rawpy.LibRawFatalError, # pylint: disable=no-member # pylint doesn't find the errors rawpy.NotSupportedError, # pylint: disable=no-member rawpy.LibRawNonFatalError, # pylint: disable=no-member ) as err: raise errors.ReaderError(path) from err ## EOF ##