Create Custom Error Messages with Model Forms

DjangoDjango Forms

Django Problem Overview


I can see how to add an error message to a field when using forms, but what about model form?

This is my test model:

class Author(models.Model):
    first_name = models.CharField(max_length=125)
    last_name = models.CharField(max_length=125)
    created = models.DateTimeField(auto_now_add=True)
    updated = models.DateTimeField(auto_now=True)

My model form:

class AuthorForm(forms.ModelForm):
    class Meta:
        model = Author

The error message on the fields: first_name and last_name is:

> This field is required

How do I change that in a model form?

Django Solutions


Solution 1 - Django

New in Django 1.6:

> ModelForm accepts several new Meta options. > > - Fields included in the localized_fields list will be localized (by setting localize on the form field). > - The labels, help_texts and error_messages options may be used to customize the default fields, see Overriding the default fields for details.

From that:

class AuthorForm(ModelForm):
    class Meta:
        model = Author
        fields = ('name', 'title', 'birth_date')
        labels = {
            'name': _('Writer'),
        }
        help_texts = {
            'name': _('Some useful help text.'),
        }
        error_messages = {
            'name': {
                'max_length': _("This writer's name is too long."),
            },
        }

Related: https://stackoverflow.com/questions/15348007/djangos-modelform-where-is-the-list-of-meta-options/

Solution 2 - Django

For simple cases, you can specify custom error messages

class AuthorForm(forms.ModelForm):
    first_name = forms.CharField(error_messages={'required': 'Please let us know what to call you!'})
    class Meta:
        model = Author

Solution 3 - Django

Another easy way of doing this is just override it in init.

class AuthorForm(forms.ModelForm):
    class Meta:
        model = Author

    def __init__(self, *args, **kwargs):
        super(AuthorForm, self).__init__(*args, **kwargs)

        # add custom error messages
        self.fields['name'].error_messages.update({
            'required': 'Please let us know what to call you!',
        })

Solution 4 - Django

I have wondered about this many times as well. That's why I finally wrote a small extension to the ModelForm class, which allows me to set arbitrary field attributes - including the error messages - via the Meta class. The code and explanation can be found here: http://blog.brendel.com/2012/01/django-modelforms-setting-any-field.html

You will be able to do things like this:

class AuthorForm(ExtendedMetaModelForm):
    class Meta:
        model = Author
        field_args = {
            "first_name" : {
                "error_messages" : {
                    "required" : "Please let us know what to call you!"
                }
            }
        }

I think that's what you are looking for, right?

Solution 5 - Django

the easyest way is to override the clean method:

class AuthorForm(forms.ModelForm):
   class Meta:
      model = Author
   def clean(self):
	  if self.cleaned_data.get('name')=="":
         raise forms.ValidationError('No name!')
      return self.cleaned_data

Solution 6 - Django

I have a cleaner solution, based on jamesmfriedman's answer. This solution is even more DRY, especially if you have lots of fields.

custom_errors = {
    'required': 'Your custom error message'
}

class AuthorForm(forms.ModelForm):
    class Meta:
        model = Author

    def __init__(self, *args, **kwargs):
        super(AuthorForm, self).__init__(*args, **kwargs)

        for field in self.fields:
            self.fields[field].error_messages = custom_errors

Solution 7 - Django

You can easily check and put custom error message by overriding clean()method and using self.add_error(field, message):

def clean(self):
    super(PromotionForm, self).clean()
    error_message = ''
    field = ''
    # reusable check
    if self.cleaned_data['reusable'] == 0:
        error_message = 'reusable should not be zero'
        field = 'reusable'
        self.add_error(field, error_message)
        raise ValidationError(error_message)

    return self.cleaned_data

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestioniJKView Question on Stackoverflow
Solution 1 - DjangodoctaphredView Answer on Stackoverflow
Solution 2 - DjangochefsmartView Answer on Stackoverflow
Solution 3 - DjangojamesmfriedmanView Answer on Stackoverflow
Solution 4 - DjangojbrendelView Answer on Stackoverflow
Solution 5 - DjangoMermozView Answer on Stackoverflow
Solution 6 - DjangoVingtoftView Answer on Stackoverflow
Solution 7 - DjangoMoe FarView Answer on Stackoverflow