I needed to overwrite files on update (not create new ones) but also a validation which would prevent to upload 2 files with the same name.
The CustomCheckFiled triggers a validation passing the filename and model instance. If the validation returns false, the validation error_message will be displayed in admin.
The OverwriteStorage is needed because the default storage alters the name if such name already exists. Enjoy.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 | # extra py - The Custom FileFiled
from django.db.models import FileField
from django.forms import forms
class CustomCheckFileField(FileField):
def __init__(self, custom_check=None, error_message=None, **kwargs):
self.error_message=error_message
if callable(custom_check):
self.custom_check = custom_check
super(CustomCheckFileField, self).__init__(**kwargs)
def clean(self, *args, **kwargs):
data = super(CustomCheckFileField, self).clean(*args, **kwargs)
file = data.file
#args[1] is the model instance
if not self.custom_check(args[1], self.generate_filename(args[1], file.name)):
raise forms.ValidationError(self.error_message)
return data
def custom_check(self, filename):
return True
#custom FileSystemStorage which return same name for existing file (also deletes existing files on save
#some_other.py
from django.core.files.storage import FileSystemStorage
class OverwriteStorage(FileSystemStorage):
def _save(self, name, content):
if self.exists(name):
self.delete(name)
return super(OverwriteStorage, self)._save(name, content)
def get_available_name(self, name):
return name
#usage
#models.py
def _custom_media_file_unique(instance, filename):
existing = CustomMedia.objects.filter(file=filename)
if existing and existing.count() > 1:
return False
else:
if existing:
return existing[0].id == instance.id
return True
class CustomMedia(models.Model):
file = CustomCheckFileField(upload_to=_get_media_upload_to, custom_check=_custom_media_file_unique,error_message="File Already Exists",storage=OverwriteStorage())
|
More like this
- Template tag - list punctuation for a list of items by shapiromatron 10 months, 1 week ago
- JSONRequestMiddleware adds a .json() method to your HttpRequests by cdcarter 10 months, 2 weeks ago
- Serializer factory with Django Rest Framework by julio 1 year, 5 months ago
- Image compression before saving the new model / work with JPG, PNG by Schleidens 1 year, 6 months ago
- Help text hyperlinks by sa2812 1 year, 6 months ago
Comments
Please login first before commenting.