views:

404

answers:

3

I have done a ModelForm adding some extra fields that are not in the model. I use these fields for some calcualtions when saving the form. The extra fields appear on the form and they are sent in the POST request when uploading the form. The problem is they are not added to the cleaned_data dictionary when I validate the form. ¿How can I access them?

Thanks!

+1  A: 

Ok I have resolved it. It seems that accessing the extra fields with cleaned_data['field_name'] raises a KeyError but using cleaned_data.get('field_name') works. That's weird because normal fields for the model can be accessed via cleaned_data['field_name'].

Update: No, it doesn't work. With get() it doesn't raise a KeyError but it sets a value of None because the extra fields are not in the cleaned_data dictionary.

Here is the code. In the templates there is an autocomplete, so in the form there is an "artist" field rendered as a CharField and an hidden IntegerField that will be autopopulated with the given artist id. In the clean_artist method I want to select the artist object and store it in the artist field of the form.

models.py

class Music(models.Model):
    artist = models.ForeignKey(Artist, related_name='music', blank=True, null=True)
    # other fields...

forms.py

class MusicForm(forms.ModelForm):
    artist_id = forms.IntegerField(label="", widget=forms.HiddenInput(), required=False)
    artist = forms.CharField(required=False)
    # other fields ...

    class Meta:
        model = Music

    def clean_artist(self):
        if self.cleaned_data.get('artist') == '':
            artist = None
        else:
            artist_id = self.cleaned_data.get('artist_id') # this returns always None because artist_id is not in cleaned_fields (this seemed to work with previous django versions but not with current SVN version)
            if artist_id != None:
                artist = Artist.objects.get(id=artist_id)
            else:
                artist = None

    return artist
Antonio Melé
This is strange, because get is no different from []. Post your code and it will be easier to find underlying problem.
gruszczy
return artist needs an extra indent. it's not in the clean_artist method.
Brandon H
A: 

If the code you've posted in your follow-up answer is an exact copy-and-paste, then there is an indentation problem with the last line - it should be one level in.

Daniel Roseman
+1  A: 

First, you shouldn't have artist_id and artist fields. They are build from the model. If you need some artist name, add artist_name field, that is CharField.

Furthermore, you are trying to retrieve something from cleaned_data inside clean value. There might not be data you need - you should use values from self.data, where is data directly from POST.

gruszczy