I have a category and for each category I want to add multiple images but whatever I do, I have just one upload file but I want to have multiple. In my Django project I have this class:
in my model file:
class SalonSampleImages(models.Model):
service = models.ForeignKey(Salon, on_delete=models.CASCADE)
Category = models.ForeignKey(
ServiceCategory,
on_delete=models.SET_NULL,
null=True,
blank=True,
verbose_name="the main service",
default=1
)
image = models.ImageField(upload_to='salon_images/', verbose_name="images")
def __str__(self):
return f"images"
class Meta:
verbose_name = "picture"
verbose_name_plural = "pictures"
in my admin file:
class SalonSampleImagesInLineFormSet(forms.BaseInlineFormSet):
def clean(self):
super().clean()
total_images = len([form for form in self.forms if form.cleaned_data and not form.cleaned_data.get('DELETE', False)])
if total_images < 3:
raise ValidationError("you must all at least 3 images")
if total_images > 10:
raise ValidationError("you cannot add more than 10 images")
class SalonSampleImagesInLine(admin.TabularInline):
model = SalonSampleImages
formset = SalonSampleImagesInLineFormSet
extra = 1
and I registered all
then I created a model file:
class MultiFileInput(forms.ClearableFileInput):
allow_multiple_selected = True
def __init__(self, attrs=None):
if attrs is None:
attrs = {}
attrs.setdefault('multiple', 'multiple')
super().__init__(attrs=attrs)
def value_from_datadict(self, data, files, name):
return files.getlist(name)
class MultiImageUploadForm(forms.Form):
category = forms.ModelChoiceField(
queryset=ServiceCategory.objects.all(),
label="choose category"
)
images = forms.FileField(
widget=MultiFileInput(),
label="upload pictures"
)
then I created a html file:
{% extends "admin/base_site.html" %}
{% block content %}
<h1>{{ title }}</h1>
<form method="post" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<input type="submit" value="save the image" class="default">
</form>
{% endblock %}
and my settings.py:
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates'],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]
I have a category and for each category I want to add multiple images but whatever I do, I have just one upload file but I want to have multiple. In my Django project I have this class:
in my model file:
class SalonSampleImages(models.Model):
service = models.ForeignKey(Salon, on_delete=models.CASCADE)
Category = models.ForeignKey(
ServiceCategory,
on_delete=models.SET_NULL,
null=True,
blank=True,
verbose_name="the main service",
default=1
)
image = models.ImageField(upload_to='salon_images/', verbose_name="images")
def __str__(self):
return f"images"
class Meta:
verbose_name = "picture"
verbose_name_plural = "pictures"
in my admin file:
class SalonSampleImagesInLineFormSet(forms.BaseInlineFormSet):
def clean(self):
super().clean()
total_images = len([form for form in self.forms if form.cleaned_data and not form.cleaned_data.get('DELETE', False)])
if total_images < 3:
raise ValidationError("you must all at least 3 images")
if total_images > 10:
raise ValidationError("you cannot add more than 10 images")
class SalonSampleImagesInLine(admin.TabularInline):
model = SalonSampleImages
formset = SalonSampleImagesInLineFormSet
extra = 1
and I registered all
then I created a model file:
class MultiFileInput(forms.ClearableFileInput):
allow_multiple_selected = True
def __init__(self, attrs=None):
if attrs is None:
attrs = {}
attrs.setdefault('multiple', 'multiple')
super().__init__(attrs=attrs)
def value_from_datadict(self, data, files, name):
return files.getlist(name)
class MultiImageUploadForm(forms.Form):
category = forms.ModelChoiceField(
queryset=ServiceCategory.objects.all(),
label="choose category"
)
images = forms.FileField(
widget=MultiFileInput(),
label="upload pictures"
)
then I created a html file:
{% extends "admin/base_site.html" %}
{% block content %}
<h1>{{ title }}</h1>
<form method="post" enctype="multipart/form-data">
{% csrf_token %}
{{ form.as_p }}
<input type="submit" value="save the image" class="default">
</form>
{% endblock %}
and my settings.py:
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
'DIRS': [BASE_DIR / 'templates'],
'APP_DIRS': True,
'OPTIONS': {
'context_processors': [
'django.template.context_processors.debug',
'django.template.context_processors.request',
'django.contrib.auth.context_processors.auth',
'django.contrib.messages.context_processors.messages',
],
},
},
]
Share
Improve this question
edited Mar 29 at 22:32
jonrsharpe
122k30 gold badges268 silver badges475 bronze badges
asked Mar 29 at 22:28
meisam ojaghimeisam ojaghi
111 bronze badge
1 Answer
Reset to default 1From my knowledge, Django admin interface doesn't support multiple files uploads out of the box, however, you can overcome this limitation by installing a third-party library for you to sort it
out - django-admin-multiupload
via using pip to install it.
Update your admin.py file to use this code instead.
```py
from django.contrib import admin
from admin_multiupload.admin import MultiUploadAdmin
from <myapp>.models import SalonSampleImages
class SalonSampleImagesAdmin(MultiUploadAdmin):
list_display = [
'service',
'category',
'image'
]
list_filter = [
'service',
'category'
]
def process_upload_file(self, uploaded, instance, request):
'Process the salon uploaded file'
pass
admin.site.register(SalonSampleImages, SalonSampleImagesAdmin)
# For your forms code, you need to modify it to enable user upload
multiple files at a time with the usage of widget and FileField class
from django import forms
class MultiImageUploadForm(forms.Form):
category = forms.ModelChoiceField(
queryset=ServiceCategory.objects.all(),
label='choose category you want'
)
images = forms.FileField(
widget=forms.ClearableFileInput(attrs={'multiple': True}),
label='upload pictures'
)
NB: if you wanna apply the multiimageform class we created then you need to create a view function for that and you should use getList queryDict of request.FILES part of django. If you need any help from there, still let us know, for now let's focus on your admin interface question, which I had answered above.