Odif Yltsaeb
Odif Yltsaeb

Reputation: 5656

Django: overriding single model field validation

I am using django.db.models.fields.DecimalField in one case, but its validation error is quite BAD.

like, when user enters 3,4 instead of 3.4 it says - 'Enter a number'. Well 3,4 is as much as number in some countries as 3.4 is. At least to those who perhaps are not well versed in computer stuff.

So for that reason i am trying to override this fields validation so i could validate it myself.

My problem is - before modelforms clean_my_field() is called, models own validation works and it already raises an error.

So i looked up https://docs.djangoproject.com/en/dev/ref/models/instances/#validating-objects

After reading this i understood that i could do

def full_clean(self):
    super(MyModel, self).full_clean(exclude = 'my_field')

and my_field would be excluded from validation and i could validate it myself in

def clean(self)
    pass
    #how do i access cleaned data here anyway?
    #self.cleaned_data does not exist
    #is self.my_field the only way?

But alas - it does not work. self.my_field value is old value in clean() method and cleaned_data is nowhere to be found.

All this makes me think my approach is wrong. I could write my own field which extends django's DecimalField i guess. I thought this approach would work... Can someone clear this up for me as - WHY it does not work. why is that exclude there if it does not work? Django version 1.4.2 by the way.

Alan

Edit: I dug deeper. It seems that even if i override all models cleaning methods and dont use super in them at all - the fields are STILL cleaned at some point and the error is already raised by then.

I guess i will be doing some extending to django.db.models.fields.DecimalField in this case.

An answer about why the exclude is there in the full_clean method would still be nice. Why is it there if it does not work?

Upvotes: 1

Views: 1313

Answers (2)

paramburu
paramburu

Reputation: 11

I know it's an old question but for the ones that didn't find an answer, what I did was to add localize=True in the ModelAdmin for the Admin Site:

formfield_overrides = {
    models.DecimalField: {'localize': True},
}

That will make the FormField locale aware, accepting comma as decimal separator (depending of the current locale, of course). It will also display it localized.

https://docs.djangoproject.com/en/dev/topics/i18n/formatting/#locale-aware-input-in-forms

If you are targeting a single DecimalField or you are writing a custom Form or ModelForm just follow the instructions on the URL.

Upvotes: 1

catherine
catherine

Reputation: 22808

def views_name(request):
    ......
    field = dec_num(form.cleaned-data['....'])
    .........

    return render(request, 'page.html', {.....})


def dec_num(value):
    return value.replace(",",".")

Upvotes: 0

Related Questions