MinValueValidator not working on DecimalField in D

2019-08-26 02:39发布

问题:

I have an API developed with Django and Django Rest Framework. I've got a model with a DecimalField which should store values of at least one. Therefore, I've defined the field in the following way:

goal = models.DecimalField(decimal_places=2, max_digits=16, validators=[MinValueValidator(1)])

When I create objects calling the API (using DRF's ModelViewSet), I can create objects with negative "goal", so the validator doesn't seem to work (I've got it included in the model serializer).

Any idea?

回答1:

from django.db import models
from django.core.exceptions import ValidationError
from django.utils.translation import ugettext_lazy as _


class MyModel(models.Model):
    goal = models.DecimalField(decimal_places=2, max_digits=16, 
              validators=[MinValueValidator(1)])

    def clean(self):
        if self.goal < 1:
            raise ValidationError(_('Only numbers equal to 1 or greater are accepted.'))


回答2:

The validators only run automatically when Django’s ModelForm is used. Otherwise, you need to trigger validation yourself, usually by calling the model object’s full_clean() method.

See https://docs.djangoproject.com/en/1.9/ref/validators/#how-validators-are-run



回答3:

This is a known bug with Django REST framework 3.3.x. You can temporarily "fix" the issue by downgrading to 3.2.5, or by waiting for 3.3.3 to be released (which should include the fix).

DRF is currently filtering out that validator in Django < 1.9, which is why it is not actually being run.