In my model I defined and ImageField()
image = models.ImageField(upload_to='images/%Y/%m/%d/', blank=True, null=True)
I want to validate the uploaded image on:
extensions = (‘gif’, ‘jpg’, ‘jpeg’, ‘png’)
dimensions = (360, 80))
size = (32*1024)
I had a look at
validate_image_file_extension but that only validates the extension. Is there a validator that validates all three.
I saw validators being defined in models.py, is that the best place or should I put the validator in views.py or forms.py.
It kinda depends upon what you want to have happen if the submitted file is not valid. I’d be inclined to validate the image in the form - the earliest possible point, and before it gets saved.
I’d probably write a custom file handler* to allow me to access the data before it gets written to a file and then use
Pillow to examine that image to determine its dimensions. (The file object provides access to verify the size. So I’d probably check the extension and size first, before calling Pillow to identify the dimensions.)
(* Also see Custom upload handlers)
I followed the links you provided, and read through a lot of ImageField() and validators documentation.
I thought the easiest way to validate an image would be making use of the attributes in the class ImageField()
class ImageField(upload_to=None, height_field=None, width_field=None, max_length=100, **options)
In models.py I have:
from PIL import Image
from django.core.validators import FileExtensionValidator
from config.settings import ALLOWED_IMAGE_EXTENSIONS
node = models.OneToOneField(Node, on_delete=models.CASCADE, primary_key=True, related_name='logos', related_query_name='logo')
image = models.ImageField(
When I upload an image I get an AttributeError:
Exception Type: AttributeError
'Logo' object has no attribute '240'
Exception Location: /Users/annet/Documents/project/venv/lib/python3.10/site-packages/django/db/models/fields/files.py, line 475, in update_dimension_fields
Obviously my understanding of the attributes is wrong, what did I miss reading the documentation?
Quoting from the docs for the model ImageField.width_field:
Name of a model field which will be auto-populated with the width of the image each time the model instance is saved.
That attribute identifies a field to be populated by Django when the model is saved.
In other words, in your
image field definition, you would have
width_field = image_width, and then another field in your model:
image_width = IntegerField(). Similarly, you would have a height field defined and reference that field name in the
height_field attribute of the ImageField.
Note that these are populated when the model instance is saved, and so they don’t provide any capability for you to check them before then. (They also don’t define or create any limitation on those values. Any defaults defined in those fields are going to be overwritten by the actual value obtained from the image.)