Coverage for /var/srv/projects/api.amasfac.comuna18.com/tmp/venv/lib/python3.9/site-packages/django/core/files/images.py: 15%

50 statements  

« prev     ^ index     » next       coverage.py v6.4.4, created at 2023-07-17 14:22 -0600

1""" 

2Utility functions for handling images. 

3 

4Requires Pillow as you might imagine. 

5""" 

6import struct 

7import zlib 

8 

9from django.core.files import File 

10 

11 

12class ImageFile(File): 

13 """ 

14 A mixin for use alongside django.core.files.base.File, which provides 

15 additional features for dealing with images. 

16 """ 

17 

18 @property 

19 def width(self): 

20 return self._get_image_dimensions()[0] 

21 

22 @property 

23 def height(self): 

24 return self._get_image_dimensions()[1] 

25 

26 def _get_image_dimensions(self): 

27 if not hasattr(self, "_dimensions_cache"): 

28 close = self.closed 

29 self.open() 

30 self._dimensions_cache = get_image_dimensions(self, close=close) 

31 return self._dimensions_cache 

32 

33 

34def get_image_dimensions(file_or_path, close=False): 

35 """ 

36 Return the (width, height) of an image, given an open file or a path. Set 

37 'close' to True to close the file at the end if it is initially in an open 

38 state. 

39 """ 

40 from PIL import ImageFile as PillowImageFile 

41 

42 p = PillowImageFile.Parser() 

43 if hasattr(file_or_path, "read"): 

44 file = file_or_path 

45 file_pos = file.tell() 

46 file.seek(0) 

47 else: 

48 try: 

49 file = open(file_or_path, "rb") 

50 except OSError: 

51 return (None, None) 

52 close = True 

53 try: 

54 # Most of the time Pillow only needs a small chunk to parse the image 

55 # and get the dimensions, but with some TIFF files Pillow needs to 

56 # parse the whole file. 

57 chunk_size = 1024 

58 while 1: 

59 data = file.read(chunk_size) 

60 if not data: 

61 break 

62 try: 

63 p.feed(data) 

64 except zlib.error as e: 

65 # ignore zlib complaining on truncated stream, just feed more 

66 # data to parser (ticket #19457). 

67 if e.args[0].startswith("Error -5"): 

68 pass 

69 else: 

70 raise 

71 except struct.error: 

72 # Ignore PIL failing on a too short buffer when reads return 

73 # less bytes than expected. Skip and feed more data to the 

74 # parser (ticket #24544). 

75 pass 

76 except RuntimeError: 

77 # e.g. "RuntimeError: could not create decoder object" for 

78 # WebP files. A different chunk_size may work. 

79 pass 

80 if p.image: 

81 return p.image.size 

82 chunk_size *= 2 

83 return (None, None) 

84 finally: 

85 if close: 

86 file.close() 

87 else: 

88 file.seek(file_pos)