当还给出实例时如何为 ModelForm 设置初始值 [英] How to set initial values for a ModelForm when instance is also given

查看:20
本文介绍了当还给出实例时如何为 ModelForm 设置初始值的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

似乎如果 ModelForm 有一个实例,它会忽略您为 initial 提供的任何值,而是将其设置为实例的值——即使该实例是一个空的模型记录.

It seems like if a ModelForm is given an instance, it ignores any values you provide for initial and instead sets it to the value of the instance -- even if that instance is an empty model record.

有没有办法用实例创建一个表单让它设置初始数据?

Is there any way to create a form with an instance and have it set initial data?

我需要它,因为我正在保存相关记录并且它们似乎无法正确保存,除非在创建 ModelForm 时提供了一个实例.

I need it because I'm saving related records and they don't appear to save correctly unless the ModelForm is given an instance when created.

我相信这个问题的答案很简单,只是我遗漏了一些明显的东西.

I'm sure the answer to this is straightforward and I'm just missing something obvious.

相关代码如下:

form = form_class(person=person, conference=conference, initial=initial, instance=registration)

其中 form_class 是 RegistrationForm 然后在注册表单中:

where form_class is RegistrationForm and then in the registration form:

class RegisterForm(forms.ModelForm):
    ... fields here ...

    def __init__(self, *args, **kwargs):
        ... other code ...
        self.person = kwargs.pop('person')
        super(RegisterForm, self).__init__(*args, **kwargs)
        for key, in self.fields.keys():
            if hasattr(self.person, key):
                self.fields[k].initial = getattr(self.person, key)

然后当我调用该字段时,相关字段为空.

Then when I call the field, the related fields are empty.

推荐答案

在谷歌上搜索了一点点后想通了这一点.

Figured this out after a little bit of googling.

你必须在调用super之前设置初始值.

You have to set the initial value before calling super.

因此,不是循环遍历 self.fields.keys(),我必须输入我想要的字段列表并循环遍历它:

So instead of looping through self.fields.keys(), I had to type out the list of fields that I wanted and looped through that instead:

class RegisterForm(forms.ModelForm):
    ... fields here ...
    initial_fields = ['first_name', 'last_name', ... ]

    def __init__(self, *args, **kwargs):
        ... other code ...
        self.person = kwargs.pop('person')
        for key in self.initial_fields:
            if hasattr(self.person, key):
                self.fields[k].initial = getattr(self.person, key)
        super(RegisterForm, self).__init__(*args, **kwargs)

@Daria 正确地指出在调用 super 之前您没有 self.fields.我很确定这会奏效:

@Daria rightly points out that you don't have self.fields before calling super. I'm pretty sure this will work:

class RegisterForm(forms.ModelForm):
    ... fields here ...
    initial_fields = ['first_name', 'last_name', ... ]

    def __init__(self, *args, **kwargs):
        ... other code ...
        initial = kwargs.pop('initial', {})
        self.person = kwargs.pop('person')
        for key in self.initial_fields:
            if hasattr(self.person, key):
                initial[key] = initial.get(key) or getattr(self.person, key)
        kwargs['initial'] = initial
        super(RegisterForm, self).__init__(*args, **kwargs)

在这个版本中,我们使用 initial 参数来传递值.它也被这样写,如果我们已经有一个值在该字段的初始值,我们不会覆盖它.

In this version, we use the initial argument to pass the values in. It's also written so that if we already have a value in initial for that field, we don't overwrite it.

这篇关于当还给出实例时如何为 ModelForm 设置初始值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆