Django: проверка поля файла в модели с использованием Python-magic

У меня есть модель, содержащая поле файла. Я хочу ограничить это PDF-файлами. Я написал чистый метод в модели, потому что я хочу также проверить создание модели на уровне администратора и оболочки. Но это не работает в модели чистого метода. Однако метод очистки формы работает.

class mymodel(models.Model):
    myfile = models.FileField()

    def clean():
        mime = magic.from_buffer(self.myfile.read(), mime=True)
        print mime
        if not mime == 'application/pdf':
            raise ValidationError('File must be a PDF document')

class myform(forms.ModelForm):
    class Meta:
        model = mymodel
        fields = '__all__'

    def clean_myfile(self):
        file = self.cleaned_data.get('myfile')
        mime = magic.from_buffer(file.read(), mime=True)
        print mime
        if not mime == 'application/pdf':
            raise forms.ValidationError('File must be a PDF document')
        else:
            return file

Если я загружаю pdf, метод mime in form clean корректно проверяется (вывод "application/pdf"). Но метод очистки модели не валиден. Он печатает MIME как "application/x-empty". Где я делаю не так?

Также еще одна проблема заключается в том, что если метод очистки модели вызывает ошибку проверки, он не отображается как ошибка поля в форме, а отображается как ошибки, не связанные с полем. Почему так?

2 ответа

Решение

Поскольку вы используете проверку формы, вам не нужно беспокоиться о методе очистки модели

Вы уже делаете правильную вещь в форме

def clean_file(self):
        yourfile = self.cleaned_data.get("your_filename_on_template", False)
        filetype = magic.from_buffer(yourfile.read())
        if not "application/pdf" in filetype:
            raise ValidationError("File is not PDF.")
        return yourfile

Если вы хотите использовать модель clean, вы можете сделать свой собственный валидатор

/questions/44085761/django-proverit-tip-zagruzhaemogo-fajla/44085765#44085765

Вы используете проверку Python-django на стороне сервера, но javascript также является хорошим способом проверки клиентской части файла. Для проверки регулярных выражений javascript вы можете посмотреть этот ответ

/questions/22393976/proverka-tipa-fajla-s-pomoschyu-javascript/22393982#22393982

или если вы можете использовать плагины, вы можете использовать плагин проверки jquery

https://jqueryvalidation.org/

fields = '__all__'

Предложение от Two Scoops of Django: лучшие практики для Django 1.8

26.14 Не используйте ModelForms.Meta.fields = "__ all __" - сюда входят все поля модели в форме модели. Это быстрый и опасный путь. Это очень похоже на то, что мы описываем в разделе 26.13 ("Не использовать ModelForms.Meta.exclude"), и даже с настраиваемым кодом проверки открывает проекты для уязвимостей, связанных с массовым назначением на основе форм. Мы рекомендуем избегать этой техники, насколько это возможно, так как считаем, что просто невозможно уловить все варианты входных данных.

Другие вопросы по тегам