One html form, multiple interconnected django forms - how to save?

There is a problem, I need to submit two interconnected modelforms with one html form. I know how to submit two separate forms, but the foreign key is making me crazy in the case of linked models.

The problem is that the second form has to fill the foreign key field to the instance from the first form.

In this particular case, I decided to combine the two models, but I think there must be cases where a workaround for the problem described would be helpful.

Pay attention to the following code:

Model:

from django.db import models

class Facility(models.Model):
    name = models.CharField(max_length=255)

class FacilityDetail(models.Model):
    some_details = models.CharField(max_length=255)
    facility = models.ForeignKey(Facility)

      

Relevant django forms:

from django import forms

class FacilityForm(forms.ModelForm):

    class Meta:
        model = Facility
        fields = ('name')

class FacilityDetailForm(forms.ModelForm):

    class Meta:
        model = FacilityDetail
        fields = ('some_details', 'facility')

      

Form processing view:

from django.views.generic import View

FACILITY_PREFIX = 'facility'
FACILITY_DETAIL_PREFIX = 'facility_detail'

class FacilityCreateView(View):

    def get(self, request, *args, **kwargs):
        facility_form = FacilityForm(prefix=FACILITY_PREFIX)
        facility_detail_form = FacilityDetailForm(prefix=FACILITY_DETAIL_PREFIX)

        context = {
            'facility_form': facility_form,
            'facility_detail_form': facility_detail_form,
        }

        return render(request, 'facility_create.html', context)

    def post(self, request, *args, **kwargs):
        facility_form = FacilityForm(request.POST, prefix=FACILITY_PREFIX)
        facility_detail_form = FacilityDetailForm(request.POST, prefix=FACILITY_DETAIL_PREFIX)

        if facility_form.is_valid():
            facility = facility_form.save()

            # is not valid, because there is no `facility`
            if facility_detail_form.is_valid():
                facility_detail_form.cleaned_data['facility'] = facility

                facility_detail_form.save()

                return redirect(...)

        context = {
            'facility_form': facility_form,
            'facility_detail_form': facility_detail_form,
        }

        return render(response, 'facility_list.html', context)

      

How should I handle form validation and saving FacilityCreateView.post

?

+2


source to share


1 answer


One way to fix this:

facility_detail_form.cleaned_data['facility'] = facility

      

can be replaced with:



facility_detail = facility_detail_form.save(commit=False)
facility_detail.facility = facility
facility_detail.save()

#rest of the code.. .

      

Here commit=False

creates
an object for you without storing it in the database where you can assign your foreign key object before saving.

+2


source







All Articles