Attach an image into a Django Model - python

Making a basic Q&A site and want to associate each question with an image (admin uploaded) and if there is no respective image, puts it with a default "No Image" placeholder.
I have two models, Question and Answer (see below). Each question needs to have an image associated with it, so I thought the best way was to attach attribute ImageField with the Question model.
#models.py
class Question(models.Model):
title = models.CharField(max_length = 500)
picture = models.ImageField(height_field = '250',
width_field = '200',
upload_to = 'images')
def __unicode__(self):
return self.title
When I runserver though, tells me to download Python Imaging Library, and when I do get an error (different problem).
Taking a step back, what is the best way to add an image to a model in Django?

Forget PIL...
Use a location URL DB entry. Instead of having an ImageField(), use
picturepath = models.CharField(255)
that contains a URL to the static location of the image.
so if STATIC_URL = "http://127.0.0.1/static/"
and picturepath = "images/poots.png"
Then, pass that information along in the view, and use this in the template:
<img src="{{ STATIC_URL }}{{ question.picturepath }}">
will provide
<img src="http://127.0.0.1/static/images/poots.png">

Related

DJANGO - how to retrieve picture from database(sqlite) to show it on html

I have loaded the pictures to database(sqlite) and now, how to get that photo in html, can you guys tell me the steps to get there, thanks in advance
I want to grab the picture from database and show it in the html.
To show uploaded images in template:
In html file:
<img src="/media/{{image}}" /> #image is a model field name.
This is the way you can view uploaded image in template.
Your images are stored in your static files folder and not directly in the database. I assume you are using an ImageField to store the image in your model. Something like this:
image = models.ImageField(upload_to="static/images/", null=True, blank=True)
If that's the case, in order to display it in one of your templates what you have to do is refer to the image url:
<img src="{{ mymodel.url }}" />

Return the first image from the model using the tag '{{value | first}}'

I have a list of photos from which I would like to always be the first to add as a profile photo. I found the following '|first' tag in the django documentation, but I have problems to add it in my situation, every time I try to do it in this way, '{{ image_list|first.photo.url }}' i receives nothing.
Any help will be appreciated.
My models.py
class Image(models.Model):
photo = models.ImageField()
added_at = models.DateTimeField(auto_now_add=True)
masseurs = models.ForeignKey(Masseurs, on_delete=models.CASCADE)
views.py
masseur = get_object_or_404(Masseurs, pk=masseurs_id)
image_list = Image.objects.filter(masseurs_id = masseurs_id)
return render(request, 'masseur/masseur_detail.html', {'image_list':image_list})
Since image_list is a QuerySet and not a list, |first won't work. You can however use:
{{ image_list.first.photo.url }}
For reference, see : Accessing Method Calls
Most method calls attached to objects are also available from within templates. This means that templates have access to much more than just class attributes (like field names) and variables passed in from views.
Why don't you do it in the view?
image = Image.objects.filter(masseurs_id=masseurs_id).first()
But if you need to do it in the template:
{{ image_list.first.photo.url }}
This is because image_list is a queryset, so you can get the first item of the queryset with the .first() syntax

django aws s3 image resize on upload and access to various resized image

I would like to be able resize my uploaded image to various size categories:
original
medium (500kb)
small (200kb)
And save it to AWS S3. And later be able to access it.
One strategy is to save it in filename_small.jpg, filename_medium.jpg, have a helper function to be able to append the _small, _medium to access those files. Im not sure how to save all the different files (resized) and then access it with the helper.
https://gitlab.com/firdausmah/railercom/blob/master/railercomapp/storage_backends.py
class MediaStorage(S3Boto3Storage):
location = 'media'
file_overwrite = False
https://gitlab.com/firdausmah/railercom/blob/master/railercomapp/models.py
class Employee(models.Model):
...
face_image = models.FileField(upload_to=upload_to('employee/face_image/'), blank=True, storage=MediaStorage())
https://gitlab.com/firdausmah/railercom/blob/master/railercomapp/api.py
#api_view(['POST'])
def update_employee_image(request):
...
employee = Employee.objects.get(id = employee_id)
employee.face_image = face_image_obj
employee.save()
I am using django-storages and S3Boto3Storage. My full working project is in the git links.
Depending on what your use case is I would suggesting using sorl-thumbnail which works with django-storages and will handle the resizing for you, and means you don't have to do the work of managing different sizes yourself.
Instead of defining specific file sizes to store the image for, you would define thumbnail sizes in the places you want to use them, e.g.,
{% thumbnail item.image "300" crop="center" as im %}
<img src="{{ im.url }}" width="{{ im.width }}" height="{{ im.height }}">
{% endthumbnail %}
This would produce a thumbnail of maximum width 300px, which would get generated the first time and saved on s3.
The app has a low level API that you can use if you need to generate and fetch thumbnails outside of a template context:
from sorl.thumbnail import get_thumbnail
im = get_thumbnail(my_file, '100x100', crop='center', quality=99)

Error when using django-admin-multiupload and django-imagekit together

At the moment I'm on my way using the django-imagekit to show thumbnails in an image-heavy view of a gallery app. For this purpose I'm using the 'model-method', means I'm creating the thumbnails within the model.
Now with the comfort of the admin in mind (upload multiple picture at once) I also want to implement a multi-upload form in the admin-view. To ease things a little bit I tried to use an app I found on GitHub, django-admin-multiupload (I'm not able to link to it because of my low reputations but that's the exact name for it on GitHub).
When I only use django-imagekit, everything works fine and I get nice thumbnails, just like expected. When I only use django-admin-multiupload, everything works fine and I'm able to upload multiple images just like expected.
The problem starts when I'm using both apps at the same time. The multiupload works still fine but when I'm opening the view, and actually implementing the thumbnail (only using both and not implementing the thumbnail works fine), where the thumbnails should be shown I will get the following error:
OSError at /gallery/ - decoder jpeg not available
You can see the full error here: http://pastebin.com/gtVYEeG7
My confusion starts when starting only the single app and it works. So as far as my knowledge goes, all PIL issues could not be present.
To provide some more information: I'm using a virtualENV with the following list of packages:
pip
django
PIL
pilkit
django-imagekit
django-amdin-multiupload
To also provide some of my implementet code, here it is:
File: models.py
class Image(models.Model):
"""the model for the images"""
# the foreign key from the event
event = models.ForeignKey('Event', related_name='images',
blank=True, null=True)
# the image itself
# file = models.FileField('File', upload_to='gallery/images/')
file = models.ImageField('File', upload_to='gallery/images/')
image_thumbnail = ImageSpecField(source='file',
processors=[
ResizeToFill(300, 250)
],
format='JPEG',
options={'quality': 40})
# image title to represent it in the admin interface
image_name = models.CharField(max_length=35, default='img')
# publication date of the image
pub_date = models.DateTimeField('date published',
auto_now_add=True)
# for a better representation of the image
def __str__(self):
return self.image_name
File: admin.py
(this one is mostly as suggested in the example from the django-admin-multiupload repo, can be viewed here: https://github.com/gkuhn1/django-admin-multiupload/blob/master/example/gallery/admin.py)
from django.contrib import admin
from django.shortcuts import get_object_or_404
from gallery.models import Event, Image
from multiupload.admin import MultiUploadAdmin
# Register your models here.
# allows inline add of single images
class ImageInlineAdmin(admin.TabularInline):
model = Image
# used to define the process_uploaded_file function
# so it will not be duplicated in the Admin-Classes
class GalleryMultiuploadMixing(object):
def process_uploaded_file(self, uploaded, event, request):
image = event.images.create(file=uploaded)
return {
'url': image.file.url,
'thumbnail': image.file.url,
'id': image.id,
'name': image.image_name
}
# admin class for event model
class EventAdmin(GalleryMultiuploadMixing, MultiUploadAdmin):
inlines = [ImageInlineAdmin,]
multiupload_form = True
multiupload_list = False
def delete_file(self, pk, request):
obj = get_object_or_404(Image, pk=pk)
return obj.delete()
admin.site.register(Event, EventAdmin)
# admin class for image model
class ImageAdmin(GalleryMultiuploadMixing, MultiUploadAdmin):
multiupload_form = False
multiupload_list = True
admin.site.register(Image, ImageAdmin)
File: index.html
<td><img class="img-responsive" src="{{ image.image_thumbnail.url }}" /></td>
If there is any need for additional information please don't hesitate to ask.
Thank you in advance and I appreciate any help.
Edit: Today I tried another way and recognized that the error is only appearing to images that were uploaded with the django-admin-multiupload and not if only images are shown that were uploaded with the normal method. Maybe this could help to find a solution.
This error was mainly caused by a broken database that could be fixed by going back to an older version and reimplementing the new code. So there is no problem in django-admin-multiupload or django-imagekit.

400 error on django filefield model save

I'm using django 1.6.5 on python 2.7, and am trying to upload images with a form. My MEDIA_URL is '/uploads', MEDIA_ROOT='...../projectroot/uploads'.
My model:
class Picture(models.Model):
person = models.ForeignKey(User)
image = models.ImageField(upload_to='/images')
My Form field:
images = forms.ImageField(widget=forms.FileInput(), required=False)
My form saving:
image = self.cleaned_data['images']
picture = Picture(park=model, image=image)
picture.save()
I have tried setting the uploads folder permissions to 777 recursively, so django definitely has write access, but that didn't work. Somebody said the enctype on the form mattered, so I've set that to "multipart/form-data".
If it helps, only the actual saving creates the error (although that may have something to do with django just using lazy functions)

Categories