简体   繁体   中英

How to save a non ModelForm form to database in Django

I'm a newbie Django user, struggling with submitting form data to the database. So that I can generate dynamic forms I am using a non-ModelForm form to capture field data.

I'm commented out validation for now but I am trying to capture the POST data from the form to the database. The latest 'draft' of my views.py code is as follows - most interested in format from form_to_save = Scenario(...) :

def scenario_add(request, mode_from_url):
    urlmap = {
        'aviation': 'Aviation',
        'maritime': 'Maritime',
        'international_rail': 'International Rail',
        'uk_transport_outside_london': 'UK Transport (Outside London)',
        'transport_in_london': 'Transport in London',
    }
    target_mode = urlmap[mode_from_url]
    m = Mode.objects.filter(mode=target_mode)
    tl = m[0].current_tl.threat_l
    scenario_form = ScenarioForm(request.POST or None, current_tl=tl, mode=target_mode)
    if request.method == 'POST':
        #if scenario_form.is_valid():
        form_to_save = Scenario(
            target = Target(descriptor = scenario_form.fields['target']),
            t_type = ThreatType(t_type = scenario_form.fields['t_type']),
            nra_reference = NraReference(nra_code = scenario_form.fields['nra_reference']),
            subt = scenario_form.fields['subt'],
            ship_t = ShipType(ship_t = scenario_form.fields['ship_t']),
            likelihood = scenario_form.fields['likelihood'],
            impact = scenario_form.fields['impact'],
            mitigation = scenario_form.fields['mitigation'],
            compliance_score = scenario_form.fields['compliance_score'],
            notes = scenario_form.fields['notes']
        )
        form_to_save.save()
        # This needs to be changed to a proper redirect or taken to
        # a scenario summary page (which doesn't yet exit.)
        return render(request, "ram/new_scenario_redirect.html", {
            'scenario_form': scenario_form,
            'mode': mode_from_url,
            'mode_proper': target_mode
        })
    else:
        # if there is no completed form then user is presented with a blank
        # form
        return render(request, 'ram/scenario_add.html', {
            'scenario_form': scenario_form,
            'current_tl': tl,
            'mode': mode_from_url,
            'mode_proper': target_mode
        })

Any advice gratefully received. Many thanks.

You've commented out the is_valid check, for some reason. You need that: as well as checking for validity, it also populates the form's cleaned_data dictionary which is what you should be getting the data from to create your object. (And don't call that object "form_to_save": it's a model instance, not a form).

if request.method == 'POST':
    if scenario_form.is_valid():
        scenario = Scenario(
            target = Target(descriptor=scenario_form.cleaned_data['target']),
            t_type = ThreatType(t_type = scenario_form.cleaned_data['t_type'])
            ...etc

Plus, you should move the final "return render" call out of the else block, so that it is caught when the form is not valid, to show any errors.

However, as petkostas says, you would almost certainly be better off using an actual ModelForm in the first place.

You can add custom options by overriding the init function in your form. For example:

class SomeForm(forms.Form):
    department = forms.ChoiceField(widget=forms.Select, required=True)

...

    def __init__(self, *args, **kwargs):
        super(SomeForm, self).__init__(*args, **kwargs)
        self.fields['department'].choices = Department.objects.all().order_by('department_name).values_list('pk', 'department_name')

You can also change the queryset in the init function: where Department is a foreign key for example

queryset = Department.objects.filter(your logic)
self.fields['department'].queryset = queryset

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM