Robert Townley
Robert Townley

Reputation: 3584

Add object ID to field names in Django form

Within a single HTML form, I'll be rendering different Django modelforms.

These forms may (and probably will) have identical field names (such as "Content"). As such, I need to append the modelform instance's object ID to each field in the form to ensure that they have unique HTML input names). I do this on init like so:

class Edit_Text_Block_Form(ModelForm):
    content = forms.CharField(widget = forms.Textarea(
        attrs = {
            "class": "full_tinymce"
        }),
        label = "",
    )

    class Meta:
        model = TextBlock
        fields = []

    def __init__(self, user, *args, **kwargs):
        self.user = user
        super(Edit_Text_Block_Form, self).__init__(*args, **kwargs)
        old_fields = self.fields
        new_fields = {}
        for field in old_fields:
            new_fields[str(self.instance.id)+"_"+field] = self.fields[field]
        self.fields = {}
        for field in new_fields:
            self.fields[field] = new_fields[field]

This works fine, and html renders with names and IDs like "96_content" which is what I want.

However, upon save, it's looking through my fields to save the "content" field when it only sees "96_content" and gets confused. As such, I need to override the model save function as well. I've been doing that like so:

def save(self, *args, **kwargs):
    old_fields = {}
    for field in self.fields:
        real_name = field.split("_")[1]
        old_fields[real_name] = self.fields[field]

    self.fields = old_fields
    super(Edit_Text_Block_Form, self).save(*args, **kwargs)

However, this is not working for reasons that I can't quite figure out. The save function completes without errors, but none of my form changes are being made. My only guess is that perhaps the field values aren't being copied over when I do old_fields[real_name] = self.fields[field].

My main question is: how do I get my save function to properly save data to the fields after I have changed their name in init() and changed them back during save()

My hopeful question is: Is there a better way for me to be doing this? (By "this", I mean "namespacing each HTML field with the object_id of the ModelForm's instance to ensure uniqueness with other fields contained within the same html form)?

Thanks for your help!

Upvotes: 0

Views: 1112

Answers (1)

Daniel Roseman
Daniel Roseman

Reputation: 600059

You don't need to do any of this. Just use the prefix parameter when instantiating the form.

Note that if your multiple forms are all of the same type, you should be using formsets instead.

Upvotes: 2

Related Questions