【问题标题】:Django Multivaluefield Optional FieldsDjango Multivaluefield 可选字段
【发布时间】:2018-02-10 22:20:20
【问题描述】:

我搜遍了所有我能找到的都是几年前的东西和/或不适用的东西。

我正在尝试将 MultiValueField 添加到我的表单中,以便人们可以轻松地输入一到三个输入。应该只需要这些字段中的第一个,但表单验证器仍然需要所有三个字段,除非我将整个内容设为可选(它不应该是)。

下面是我的 MultiWidget、MultiValueField 和表单的代码。我已经尝试从字段属性中删除除required=False 之外的所有内容,但它仍然需要所有这些属性。当我调用字段而不是字段__init__ 时,我尝试在表单中设置require_all_fields=False,它仍然需要所有这些。

我觉得我已经读了又读了,关于如何实现这类事情的信息很少。

class ThreeNumFields(forms.MultiWidget):
    def __init__(self, attrs=None):
        self.widgets = [
            forms.TextInput(),
            forms.TextInput(),
            forms.TextInput()
        ]
        super().__init__(self.widgets, attrs)

    def decompress(self, value):
        if value:
            return value.split(' ')
        return [None, None]


class LocationMultiField(forms.MultiValueField):
    widget = ThreeNumFields()
    validators = [RegexValidator]

    def __init__(self):
        fields = (
            forms.CharField(
                error_messages={'incomplete': 'Please enter at least one valid zip code.'},
                validators=[
                    RegexValidator(r'^[0-9]{5}$', 'Enter a valid US zip code.'),
                ],
                max_length=5,
            ),
            forms.CharField(
                required=False,
                validators=[
                    RegexValidator(r'^[0-9]{5}$', 'Enter a valid US zip code.'),
                ],
                max_length=5,
            ),
            forms.CharField(
                required=False,
                validators=[
                    RegexValidator(r'^[0-9]{5}$', 'Enter a valid US zip code.'),
                ],
                max_length=5,
            )
        )
        super(LocationMultiField, self).__init__(
            fields=fields,
            require_all_fields=False,
        )

    def compress(self, data_list):
        return ' '.join(data_list)


class NewForecastForm(forms.ModelForm):
    class Meta:
        model = ForecastProfile
        exclude = ['userid', 'last_updated']

    nickname = forms.CharField(
        label=_('Forecast Nickname')
    )
    locations = LocationMultiField()
    timezone = forms.ChoiceField(
        label=_('Timezone for your forecast'),
        choices=choices.timezones
    )
    start_time = forms.ChoiceField(
        label=_('Earliest time you want in your forecast'),
        help_text=_('(Time will not be exact to account for timezone conversions and forecast data.)'),
        choices=choices.times
    )
    end_time = forms.ChoiceField(
        label=_('Latest time you want in your forecast'),
        help_text=_('(Time will not be exact to account for timezone conversions and forecast data.)'),
        choices=choices.times
    )
    alerts = forms.MultipleChoiceField(
        choices=choices.alerts,
        widget=forms.CheckboxSelectMultiple()
    )
    days_in_forecast = forms.ChoiceField(
        choices=choices.forecastdays
    )

    def clean(self):
        cleaned_data = super(NewForecastForm, self).clean()
        start = cleaned_data.get("start_time")
        end = cleaned_data.get("end_time")

        if start > end:
            raise forms.ValidationError(
                "Your start time must be before your end time."
            )

【问题讨论】:

    标签: python django django-forms


    【解决方案1】:

    我遇到了同样的问题,它看起来像是 Django 的一个错误。有一张公开票,#29205

    也就是说,通过设置required=Falserequire_all_fields=False,并在表单的 init 方法中明确添加所需的小部件属性,我确实让表单在我的情况下正常工作。

    在您的情况下,这意味着将 self.fields['locations'].widget.widgets[0].attrs['required'] = True 放入 NewForecastForm 的 init 方法中

    【讨论】:

      猜你喜欢
      • 2012-05-14
      • 1970-01-01
      • 2012-04-18
      • 1970-01-01
      • 1970-01-01
      • 2015-02-08
      • 2010-12-09
      • 2016-06-19
      • 2013-04-27
      相关资源
      最近更新 更多