I'm using PIL to compress uploaded images(FileField
). However I'm getting an error which I believe is a problem of double saving? (saving my image, and then saving the whole form which includes the image). I wanted to perform commit=False
when I'm saving the image but it doesn't appear it's possible. Here's my code:
...
if form_post.is_valid():
instance = form_post.save(commit=False)
instance.user = request.user
if instance.image:
filename = instance.image
instance.image = Image.open(instance.image)
instance.image.thumbnail((220, 130), Image.ANTIALIAS)
instance.image.save(filename, quality=60)
instance.save()
returns 'JpegImageFile' object has no attribute '_committed'
error on the last line (instance.save()
)
Can someone identify the problem? - and any idea how I can fix it?
Full Traceback:
File "/Users/zorgan/Desktop/app/lib/python3.5/site-packages/django/core/handlers/exception.py" in inner
41. response = get_response(request)
File "/Users/zorgan/Desktop/app/lib/python3.5/site-packages/django/core/handlers/base.py" in _get_response
187. response = self.process_exception_by_middleware(e, request)
File "/Users/zorgan/Desktop/app/lib/python3.5/site-packages/django/core/handlers/base.py" in _get_response
185. response = wrapped_callback(request, *callback_args, **callback_kwargs)
File "/Users/zorgan/Desktop/app/lib/python3.5/site-packages/django/contrib/auth/decorators.py" in _wrapped_view
23. return view_func(request, *args, **kwargs)
File "/Users/zorgan/Desktop/project/site/post/views.py" in post
68. if uploaded_file_type(instance) is True:
File "/Users/zorgan/Desktop/project/site/functions/helper_functions.py" in uploaded_file_type
12. f = file.image.read(1024)
Exception Type: AttributeError at /post/
Exception Value: 'JpegImageFile' object has no attribute 'read'
Full models:
class Post(models.Model):
user = models.ForeignKey(User, blank=True, null=True)
title = models.TextField(max_length=95)
image = models.FileField(null=True, blank=True)
and the accompanying PostForm
:
class PostForm(forms.ModelForm):
title = forms.TextInput(attrs={'placeholder': 'title'})
class Meta:
model = Post
fields = [
'user',
'title',
'image',
]
views.py
def post(request):
if request.user.is_authenticated():
form_post = PostForm(request.POST or None, request.FILES or None)
if form_post.is_valid():
instance = form_post.save(commit=False)
if instance.image:
filename = instance.image
instance.image = Image.open(instance.image)
instance.image.thumbnail((220, 130), Image.ANTIALIAS)
instance.image.save(filename, quality=60)
instance.save()
return HttpResponseRedirect('/home/')
else:
form_post = PostForm()
context = {
'form_post': form_post,
}
return render(request, 'post/post.html', context)
else:
return HttpResponseRedirect("/accounts/signup/")
This following code:
if instance.image:
im = Image.open(instance.image)
print("Filename:", im.filename) #doesn't print anything
thumb = im.thumbnail((220, 130), Image.ANTIALIAS)
thumb.save(im.filename, quality=60)
returns an AttributeError
: 'NoneType' object has no attribute 'save'
. I believe this is because im.filename
doesn't print anything. Any idea why?
The other method:
if instance.image:
im = Image.open(instance.image)
thumb = im.thumbnail((220, 130), Image.ANTIALIAS)
thumb_io = BytesIO()
thumb.save(thumb_io, im.format, quality=60)
instance.image.save(im.filename, ContentFile(thumb_io.get_value()), save=False)
also returns AttributeError
: 'NoneType' object has no attribute 'save'
, on this line: thumb.save(thumb_io, im.format, quality=60)
. Not sure why though?