[英]How to rotate image before save in Django?
Now I'm creating a web app which allows user to upload images using Django Rest Framework. 现在我正在创建一个Web应用程序,允许用户使用Django Rest Framework上传图像。 I'd like to rotate those images according to EXIF tag and save. 我想根据EXIF标签旋转这些图像并保存。
At first, I found this way , and it works in local environment. 起初,我发现了这种方式 ,它适用于当地环境。 But, now I use Amazon S3 for deployment, then this way doesn't work. 但是,现在我使用Amazon S3进行部署,然后这种方式不起作用。
So, I'm trying to rotate image before save and struggling... Recent code is below, raising TypeError at /api/work/ 'str' object is not callable
when I post new Work object. 因此,我正在尝试在保存和挣扎之前旋转图像...最近的代码如下, TypeError at /api/work/ 'str' object is not callable
提出TypeError at /api/work/ 'str' object is not callable
当我发布新的Work对象时, TypeError at /api/work/ 'str' object is not callable
。
How to fix it? 怎么解决?
Or is there other nice way? 还是有其他好方法吗?
[models.py] [models.py]
from django.db import models
from django.conf import settings
from PIL import Image as Img
from PIL import ExifTags
from io import BytesIO
from django.core.files import File
import datetime
class Work(models.Model):
owner = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, null=True, blank=True)
title = models.CharField(max_length=120)
made_date = models.DateField(default=datetime.date.today, null=True, blank=True)
note = models.TextField(max_length=2000, null=True, blank=True)
image = models.ImageField(upload_to='work_pic', default='default_image.png')
def __str__(self):
return self.title
def save(self, *args, **kwargs):
if self.image:
pilImage = Img.open(BytesIO(self.image.read()))
for orientation in ExifTags.TAGS.keys():
if ExifTags.TAGS[orientation] == 'Orientation':
break
exif = dict(pilImage._getexif().items())
if exif[orientation] == 3:
pilImage = pilImage.rotate(180, expand=True)
elif exif[orientation] == 6:
pilImage = pilImage.rotate(270, expand=True)
elif exif[orientation] == 8:
pilImage = pilImage.rotate(90, expand=True)
output = BytesIO()
pilImage.save(output, format='JPEG', quality=75)
output.seek(0)
self.image = File(output, self.image.name())
return super(Work, self).save(*args, **kwargs)
[serializers.py] [serializers.py]
from rest_framework import serializers
from .models import Work
class WorkSerializer(serializers.ModelSerializer):
owner = serializers.HiddenField(default=serializers.CurrentUserDefault())
class Meta:
model = Work
fields = '__all__'
def create(self, validated_data):
return Work.objects.create(**validated_data)
In your save()
method, you are calling the self.image.name
attribute as a function. 在save()
方法中,您将self.image.name
属性作为函数调用。 the Image.name
is a string
attribute, so you don't have to call it as a function. Image.name
是一个string
属性,因此您不必将其称为函数。
So change the line self.image = File(output, self.image.name())
to 所以将行self.image = File(output, self.image.name())
更改为
self.image = File(output, self.image.name)
will solve the error 将解决错误
Complete Model definition 完整的模型定义
class Work(models.Model):
owner = models.ForeignKey(settings.AUTH_USER_MODEL, on_delete=models.CASCADE, null=True, blank=True)
title = models.CharField(max_length=120)
made_date = models.DateField(default=datetime.date.today, null=True, blank=True)
note = models.TextField(max_length=2000, null=True, blank=True)
image = models.ImageField(upload_to='work_pic', default='default_image.png')
def __str__(self):
return self.title
def save(self, *args, **kwargs):
if self.image:
pilImage = Img.open(BytesIO(self.image.read()))
for orientation in ExifTags.TAGS.keys():
if ExifTags.TAGS[orientation] == 'Orientation':
break
exif = dict(pilImage._getexif().items())
if exif[orientation] == 3:
pilImage = pilImage.rotate(180, expand=True)
elif exif[orientation] == 6:
pilImage = pilImage.rotate(270, expand=True)
elif exif[orientation] == 8:
pilImage = pilImage.rotate(90, expand=True)
output = BytesIO()
pilImage.save(output, format='JPEG', quality=75)
output.seek(0)
self.image = File(output, self.image.name)
return super(Work, self).save(*args, **kwargs)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.