Где должна выполняться проверка полей модели в django?
Я мог бы назвать как минимум два возможных варианта: в перегруженном методе .save() модели или в методе .to_python() для моделей. Подкласс подкласса (очевидно, для этого нужно писать пользовательские поля).
Возможные варианты использования:
- когда совершенно необходимо гарантировать, что пустая строка не будет записана в базу данных (пустой = аргумент ключевого слова False здесь не работает, это только для проверки формы)
- когда необходимо гарантировать, что аргумент ключевого слова "choice" получает уважение на уровне db, а не только в интерфейсе администратора (тип эмуляции типа данных enum)
В моделях также есть атрибут класса empty_strings_allowed
. Определение базового класса Field и производные классы с радостью переопределяют его, однако он, похоже, не влияет на уровень базы данных, то есть я все же могу построить модель с полями с пустой строкой и сохраните ее в базе данных. Который я хочу избежать (да, это необходимо).
Возможные реализации
на уровне поля:
class CustomField(models.CharField):
__metaclass__ = models.SubfieldBase
def to_python(self, value):
if not value:
raise IntegrityError(_('Empty string not allowed'))
return models.CharField.to_python(self, value)
на уровне модели:
class MyModel(models.Model)
FIELD1_CHOICES = ['foo', 'bar', 'baz']
field1 = models.CharField(max_length=255,
choices=[(item,item) for item in FIELD1_CHOICES])
def save(self, force_insert=False, force_update=False):
if self.field1 not in MyModel.FIELD1_CHOICES:
raise IntegrityError(_('Invalid value of field1'))
# this can, of course, be made more generic
models.Model.save(self, force_insert, force_update)
Возможно, я что-то упустил, и это можно сделать проще (и чище)?