Pillow corrupt image for serializer

40 views
Skip to first unread message

cyril moreau

unread,
Dec 7, 2020, 7:36:25 AM12/7/20
to Django REST framework
Hi Everybody,

I try to use the serializer to save an image in my model as following:

def save_file(file,owner):
    data ={}
    pic = None
    myfile = file
    is_image(myfile)
   data['image'] = file
    data['owner'] = owner
    s = ImageSerializer(data=data)
    if s.is_valid():
        logger.error("image {filename} saved".format(filename = file.name))
        pic = s.save()
    else :
        logger.error("image {filename} ERROR {errors}".format(filename = file.name, errors = s.errors))
    return pic

Model :
class Image(models.Model):
    image = models.ImageField(upload_to=path_and_rename, max_length=500)
    owner = models.CharField(max_length=100)

Serializer :
class ImageSerializer(serializers.ModelSerializer):
    class Meta:
        model = Image
        fields = '__all__'

The save function does not work because of the call of the function is_image(file) :
from PIL import Image
def is_image(myfile):
     try:
         im = Image.open(myfile)
         im.verify()
    except Exception:
            raise Execption('Invalid image')

When I call this function the serializer fails as following :
"POST /image HTTP/1.1" 200 22897
image single_file.jpg ERROR {'image': [ErrorDetail(string='Upload a valid image. The file you uploaded was either not an image or a corrupted image.', code='invalid_image')]}

If I comment the call, the serializer save the file correctly.

According to im.verify(), the file is a valid image. but then it seems like Pillow corrupt the file somehow and the serializer can not save it.

I have tried im.load(), im.close(), im.fp.close()
Nothing works.

Can someone help me? Where is my mistake?

Thank you

cyril moreau

unread,
Dec 7, 2020, 8:49:45 AM12/7/20
to Django REST framework
I have found the solution (even if i dont understand why)
it is not an issue due to pillow but the file itself.
if my function is like 
is_image(myfile):
   myfile.read()

I will have the same issue.
The file pointer/cursor needs to be reseted to the first position with myfile.seek(0)

it seems like when i open the file with PIL, the file pointer does not come back to the position 0 by itself.

So I have to change my save_file function to :

def save_file(file,owner):
    data ={}
    pic = None
    is_image(file)
    file.seek(0)
   data['image'] = file
    data['owner'] = owner
    s = ImageSerializer(data=data)
    if s.is_valid():
        logger.error("image {filename} saved".format(filename = file.name))
        pic = s.save()
    else :
        logger.error("image {filename} ERROR {errors}".format(filename = file.name, errors = s.errors))
    return pic

Cyril

Diyorbek Azimqulov

unread,
Dec 7, 2020, 10:29:33 AM12/7/20
to django-res...@googlegroups.com
Hello sir. I started learning django. I want to be a backend web developer. It is good to see you

--
You received this message because you are subscribed to the Google Groups "Django REST framework" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-rest-fram...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-rest-framework/8f2c3774-d111-4195-aa54-44ee8d6060c9n%40googlegroups.com.
Reply all
Reply to author
Forward
0 new messages