Loading django/forms/fields.py +6 −1 Original line number Diff line number Diff line Loading @@ -659,8 +659,13 @@ class ImageField(FileField): try: # load() could spot a truncated JPEG, but it loads the entire # image in memory, which is a DoS vector. See #3848 and #18520. image = Image.open(file) # verify() must be called immediately after the constructor. Image.open(file).verify() image.verify() # Annotating so subclasses can reuse it for their own validation f.image = image f.content_type = Image.MIME[image.format] except Exception: # Pillow doesn't recognize it as an image. six.reraise(ValidationError, ValidationError( Loading docs/ref/forms/fields.txt +9 −0 Original line number Diff line number Diff line Loading @@ -649,7 +649,16 @@ For each field, we describe the default widget used if you don't specify When you use an ``ImageField`` on a form, you must also remember to :ref:`bind the file data to the form <binding-uploaded-files>`. .. versionchanged:: 1.8 After the field has been cleaned and validated, the ``UploadedFile`` object will have an additional ``image`` attribute containing the Pillow `Image`_ instance used to check if the file was a valid image. ``UploadedFile.content_type`` is also updated with the image's content type as determined by Pillow. .. _Pillow: http://pillow.readthedocs.org/en/latest/ .. _Image: https://pillow.readthedocs.org/en/latest/reference/Image.html ``IntegerField`` ~~~~~~~~~~~~~~~~ Loading docs/releases/1.8.txt +6 −0 Original line number Diff line number Diff line Loading @@ -160,6 +160,12 @@ Forms :attr:`~django.forms.extras.widgets.SelectDateWidget.empty_label` argument, which will override the top list choice label when :class:`~django.forms.DateField` is not required. * After an :class:`~django.forms.ImageField` has been cleaned and validated, the ``UploadedFile`` object will have an additional ``image`` attribute containing the Pillow ``Image`` instance used to check if the file was a valid image. It will also update ``UploadedFile.content_type`` with the image's content type as determined by Pillow. Internationalization ^^^^^^^^^^^^^^^^^^^^ Loading tests/forms_tests/tests/filepath_test_files/1x1.png 0 → 100644 +150 B Loading image diff... tests/forms_tests/tests/test_fields.py +26 −1 Original line number Diff line number Diff line Loading @@ -31,12 +31,18 @@ import pickle import re import os from decimal import Decimal from unittest import skipIf try: from PIL import Image except ImportError: Image = None from django.core.files.uploadedfile import SimpleUploadedFile from django.forms import ( BooleanField, CharField, ChoiceField, ComboField, DateField, DateTimeField, DecimalField, EmailField, Field, FileField, FilePathField, FloatField, Form, forms, HiddenInput, IntegerField, MultipleChoiceField, Form, forms, HiddenInput, ImageField, IntegerField, MultipleChoiceField, NullBooleanField, NumberInput, PasswordInput, RadioSelect, RegexField, SplitDateTimeField, TextInput, Textarea, TimeField, TypedChoiceField, TypedMultipleChoiceField, URLField, ValidationError, Widget, Loading Loading @@ -741,6 +747,24 @@ class FieldsTests(SimpleTestCase): # with here) self.assertTrue(f._has_changed('resume.txt', {'filename': 'resume.txt', 'content': 'My resume'})) # ImageField ################################################################## @skipIf(Image is None, "Pillow is required to test ImageField") def test_imagefield_annotate_with_image_after_clean(self): f = ImageField() img_path = os.path.dirname(upath(__file__)) + '/filepath_test_files/1x1.png' with open(img_path, 'rb') as img_file: img_data = img_file.read() img_file = SimpleUploadedFile('1x1.png', img_data) img_file.content_type = 'text/plain' uploaded_file = f.clean(img_file) self.assertEqual('PNG', uploaded_file.image.format) self.assertEqual('image/png', uploaded_file.content_type) # URLField ################################################################## def test_urlfield_1(self): Loading Loading @@ -1262,6 +1286,7 @@ class FieldsTests(SimpleTestCase): f.choices.sort() expected = [ ('/tests/forms_tests/tests/filepath_test_files/.dot-file', '.dot-file'), ('/tests/forms_tests/tests/filepath_test_files/1x1.png', '1x1.png'), ('/tests/forms_tests/tests/filepath_test_files/directory', 'directory'), ('/tests/forms_tests/tests/filepath_test_files/fake-image.jpg', 'fake-image.jpg'), ('/tests/forms_tests/tests/filepath_test_files/real-text-file.txt', 'real-text-file.txt'), Loading Loading
django/forms/fields.py +6 −1 Original line number Diff line number Diff line Loading @@ -659,8 +659,13 @@ class ImageField(FileField): try: # load() could spot a truncated JPEG, but it loads the entire # image in memory, which is a DoS vector. See #3848 and #18520. image = Image.open(file) # verify() must be called immediately after the constructor. Image.open(file).verify() image.verify() # Annotating so subclasses can reuse it for their own validation f.image = image f.content_type = Image.MIME[image.format] except Exception: # Pillow doesn't recognize it as an image. six.reraise(ValidationError, ValidationError( Loading
docs/ref/forms/fields.txt +9 −0 Original line number Diff line number Diff line Loading @@ -649,7 +649,16 @@ For each field, we describe the default widget used if you don't specify When you use an ``ImageField`` on a form, you must also remember to :ref:`bind the file data to the form <binding-uploaded-files>`. .. versionchanged:: 1.8 After the field has been cleaned and validated, the ``UploadedFile`` object will have an additional ``image`` attribute containing the Pillow `Image`_ instance used to check if the file was a valid image. ``UploadedFile.content_type`` is also updated with the image's content type as determined by Pillow. .. _Pillow: http://pillow.readthedocs.org/en/latest/ .. _Image: https://pillow.readthedocs.org/en/latest/reference/Image.html ``IntegerField`` ~~~~~~~~~~~~~~~~ Loading
docs/releases/1.8.txt +6 −0 Original line number Diff line number Diff line Loading @@ -160,6 +160,12 @@ Forms :attr:`~django.forms.extras.widgets.SelectDateWidget.empty_label` argument, which will override the top list choice label when :class:`~django.forms.DateField` is not required. * After an :class:`~django.forms.ImageField` has been cleaned and validated, the ``UploadedFile`` object will have an additional ``image`` attribute containing the Pillow ``Image`` instance used to check if the file was a valid image. It will also update ``UploadedFile.content_type`` with the image's content type as determined by Pillow. Internationalization ^^^^^^^^^^^^^^^^^^^^ Loading
tests/forms_tests/tests/test_fields.py +26 −1 Original line number Diff line number Diff line Loading @@ -31,12 +31,18 @@ import pickle import re import os from decimal import Decimal from unittest import skipIf try: from PIL import Image except ImportError: Image = None from django.core.files.uploadedfile import SimpleUploadedFile from django.forms import ( BooleanField, CharField, ChoiceField, ComboField, DateField, DateTimeField, DecimalField, EmailField, Field, FileField, FilePathField, FloatField, Form, forms, HiddenInput, IntegerField, MultipleChoiceField, Form, forms, HiddenInput, ImageField, IntegerField, MultipleChoiceField, NullBooleanField, NumberInput, PasswordInput, RadioSelect, RegexField, SplitDateTimeField, TextInput, Textarea, TimeField, TypedChoiceField, TypedMultipleChoiceField, URLField, ValidationError, Widget, Loading Loading @@ -741,6 +747,24 @@ class FieldsTests(SimpleTestCase): # with here) self.assertTrue(f._has_changed('resume.txt', {'filename': 'resume.txt', 'content': 'My resume'})) # ImageField ################################################################## @skipIf(Image is None, "Pillow is required to test ImageField") def test_imagefield_annotate_with_image_after_clean(self): f = ImageField() img_path = os.path.dirname(upath(__file__)) + '/filepath_test_files/1x1.png' with open(img_path, 'rb') as img_file: img_data = img_file.read() img_file = SimpleUploadedFile('1x1.png', img_data) img_file.content_type = 'text/plain' uploaded_file = f.clean(img_file) self.assertEqual('PNG', uploaded_file.image.format) self.assertEqual('image/png', uploaded_file.content_type) # URLField ################################################################## def test_urlfield_1(self): Loading Loading @@ -1262,6 +1286,7 @@ class FieldsTests(SimpleTestCase): f.choices.sort() expected = [ ('/tests/forms_tests/tests/filepath_test_files/.dot-file', '.dot-file'), ('/tests/forms_tests/tests/filepath_test_files/1x1.png', '1x1.png'), ('/tests/forms_tests/tests/filepath_test_files/directory', 'directory'), ('/tests/forms_tests/tests/filepath_test_files/fake-image.jpg', 'fake-image.jpg'), ('/tests/forms_tests/tests/filepath_test_files/real-text-file.txt', 'real-text-file.txt'), Loading