Django FormWizard无限循环

时间:2013-10-15 16:28:46

标签: python django django-forms django-formwizard

我使用Django 1.4.8

I am able to dynamically change the form from a choice made on the previous step,但现在我需要更加准确。

实际上,在我的表格“步骤0”中,我有一个从我选择值的位置下拉,然后在步骤2,我需要加载与“步骤0”相同的数据而没有在步骤0中选择的值。 / p>

我是这样做的:

urls.py

# wizard
url(r'^service/create/$',
    UserServiceWizard.as_view([ProviderForm,
                               DummyForm,
                               ConsummerForm,
                               DummyForm,
                               ServicesDescriptionForm]),

views.py

def get_form(self, step=None, data=None, files=None):
    """
        change the form instance dynamically from the data we entered
        at the previous step
    """
    #
    if step is None:
        step = self.steps.current

    if step == '1':

        prev_data = self.get_cleaned_data_for_step('0')
        service_name = str(prev_data['provider']).split('Service')[1]
        class_name = 'th_' + service_name.lower() + '.forms'
        form_name = service_name + 'ProviderForm'
        form_class = class_for_name(class_name, form_name)
        form = form_class(data)

    elif step == '2':
        data = self.get_cleaned_data_for_step('0')
        form = ConsummerForm(initial={'provider': data['provider']})

        # EDIT 10/16 @ 10:00 
        # to track what's wrong I added 
        print form['consummer'].errors #return nothing 
        print form.is_valid() #return false
        print "form.non_field_errors ", form.non_field_errors() #return nothing


    elif step == '3':

        prev_data = self.get_cleaned_data_for_step('2')
        service_name = str(prev_data['consummer']).split('Service')[1]
        class_name = 'th_' + service_name.lower() + '.forms'
        form_name = service_name + 'ConsummerForm'
        form_class = class_for_name(class_name, form_name)
        form = form_class(data)

    else:
        form = super(UserServiceWizard, self).get_form(step, data, files)

    return form

我的表单是:

class ServiceChoiceForm(forms.Form):

    def activated_services(self, provider=None):
        """
        get the activated services added from the administrator
        """
        services = ServicesActivated.objects.filter(status=1)

        choices = []
        datas = ()

        if provider is not None:
            services = services.exclude(name__exact=provider)

        for class_name in services:
            datas = (class_name, class_name.name.rsplit('Service', 1)[1])
            choices.append(datas)

        return choices

class ProviderForm(ServiceChoiceForm):

    provider = forms.ChoiceField()

    def __init__(self, *args, **kwargs):
        super(ProviderForm, self).__init__(*args, **kwargs)
        self.fields['provider'].choices = self.activated_services()


class ConsummerForm(ServiceChoiceForm):

    consummer = forms.ChoiceField()

    def __init__(self, *args, **kwargs):
        super(ConsummerForm, self).__init__(*args, **kwargs)
        # get the list of service without the one selected in
        # the provider form
        self.fields['consummer'].choices = self.activated_services(
            self.initial['provider'])

现在发生了什么:

当我在表格“第2步”并提交数据时......我无限期地回到“第2步”

如果我不将elif step == '2'的部分放在get_form()中,并将相同的代码放在ConsummerForm的表单中:

self.fields['consummer'].choices = self.activated_services()

然后这个过程继续进行,但这不是我想要的:(

最后的事情 “= 我注意到get_form()在“步骤0”之后被调用了太多次:实际上是4次。 我在print form,step中使用get_form()进行了跟踪,但表单从来不是预期的。

如果有人能解释我如何在向导中修复infite循环的行为;我会很感激;)

1 个答案:

答案 0 :(得分:0)

我找到了解决方案:

在第2步我必须这样做

    elif step == '2':
        step0_data = self.get_cleaned_data_for_step('0')
        form = ConsummerForm(
            data, initial={'provider': step0_data['provider']})

而不是

    elif step == '2':
        data = self.get_cleaned_data_for_step('0')
        form = ConsummerForm(initial={'provider': data['provider']})

因为在第一部分我没有像第二段代码那样意外地覆盖“数据”字典...

现在一切都很棒!