4

何らかの理由で、フォームセットを送信した後、フォームセットが検証されません。これが起こっているかもしれない方法についてのアイデアはありますか?

#models.py

class Department(models.Model):
  department = models.CharField(verbose_name = "Department Name", max_length=100)
  description = models.TextField(verbose_name = "Description", blank=True, null=True)
  sp_description = models.TextField(verbose_name = "Description (Spanish)", blank=True, null=True)
  phone = PhoneNumberField()
  phone_ext = models.CharField(max_length=10, blank=True)

  #Relations
  provider = models.ForeignKey(Provider, blank=True, null=True)
  services_offered = models.ManyToManyField(ServiceType)

  def __unicode__(self):
    return self.department

#view.py

def display_step5(request):
    msg = ''
    email = request.session.get('email')
    provider_obj = retrieve_provider_instance(email)
    AddDepartmentFormSet = inlineformset_factory(Provider, Department, extra=0)
    if is_authenticated(request):
        AddDepartmentFormSet = inlineformset_factory(Provider, Department, extra=0)
        if request.method=='POST':
            if 'add_department' in request.POST:
                cp = request.POST.copy()
                cp['department-TOTAL_FORMS'] = int(cp['department-TOTAL_FORMS'])+ 1
                new_department = AddDepartmentFormSet(cp, prefix='department', instance=provider_obj)
            elif 'submit' in request.POST:
                formset = AddDepartmentFormSet(request.POST, instance=provider_obj)
                instances = formset.save(commit=False)
                for instance in instances:
                    instance.provider = provider_obj
                    instance.save()
                return HttpResponse("Departments have been added")
        else:
            new_department = AddDepartmentFormSet(prefix='department', instance=provider_obj)

    else:
        return HttpResponseRedirect(reverse('health.register.views.display_auth'))
    return render_to_response('step5-test.html',
{'department': new_department}, context_instance=RequestContext(request))

step5-test.html

<form method='post' action='{{request.path}}'>{% csrf_token %}
  <fieldset>
    <legend>Departments</legend>
      {{ department.management_form }}
      {% for form in department.forms %}
        <HR> <div><table>{{form.as_table}}</table></div>
      {% endfor %}
     <BR/> 
     <input title='Add a new department' type='submit' name='add_department' value='Add-Another-Department' />
    </fieldset>
    <BR/><BR/>
    <input title='Submit this form' type='submit' name='submit' value='Submit' />
</form>

フォローアップ(解決策):

提供されたブラントは、エラーが発生した理由についての洞察を提供しました。私の場合、彼の洞察は、私の状況に適したハックを構築するのに役立ちました。このハックは、テンプレート内で特定の方法で変更された可能性のあるフォームセットに適用できるようです。私の場合、フォームセットが複雑になり、よりユーザーフレンドリーにするためにいくつかのajaxが必要になりました。

「retrieve_provider_instance(email)」は、データベースに設定されたさまざまな基準(約200行のコード嘔吐)に基づいてプロバイダーオブジェクトを取得する動的な方法でした。

いくつかの大規模なデバッグの後、次のハックがうまくいきました。テンプレートの「for」ループに 次の非表示フィールドを追加することで解決しました

{% {for form in formset.forms %}
                     <tr>
                      <td>
                         {% if form.instance.pk %} <!--- if instance already exists on db --->  
                         {{ form.DELETE }}
                         <input type='hidden' name="department_set-{{ forloop.counter0 }}-id" id="id_department_set-{{ forloop.counter0 }}-id"  value={{ form.instance.pk }} />
                         {% endif %}
                      Name: <br/> {{ form.department}} <br/>
                      Phone Number: <br/> {{ form.phone }} <br/>
                      Phone Ext: <br/> {{ form.phone_ext }}</td>
                      <td>Description: <br/> {{ form.description }}</td>
                      <td>Description (Spanish): <br/> {{ form.sp_description }}</td>
                      <td>Services Provided: <br/> {{ form.services_offered }}</td>
                      <td></td>
                   </tr>
                   {% endfor %} 

私が尋ねていた特定の質問にはるかに当てはまるので、私はマークの答えを受け入れました。うまくいけば、これはこの例を実装しようとする将来の他のユーザーに役立つでしょう。実際、送信時に「プレフィックス」を割り当てるのが正しい方法であり、最も理にかなっています。

たくさんのご回答ありがとうございました。

よろしく、マット


フォローアップ:問題の一部を見つけた可能性があると思います。しかし、それはまだ解決されていません。

問題の解決に役立つ可能性のある追加情報を次に示します。間違ったPOSTデータがこれを台無しにしている可能性がありますか?もしそうなら、どうすればこれを回避できますか?

これは、フォームセットを送信した後に発生することです(この場合はフォームが1つだけです)。

トレースバックは次のとおりです。

_management_form68のファイル"/home/mhjohnson/webapps/resourcedb/lib/python2.6/django/forms/formsets.py"。raiseValidationError('ManagementFormデータが見つからないか、改ざんされています')

これは私のPOSTデータです:

department-0-phone_ext -----> u'222'

department-0-id -----> u''

department-0-services_offered -----> u'2'

department-0-phone -----> u'222-222-2222'

department-INITIAL_FORMS -----> u'0'

submit -----> u'Submit'

department-MAX_NUM_FORMS -----> u''

department-0-department -----> u'Test 1'

department-0-provider -----> u''

department-TOTAL_FORMS -----> u'1'

csrfmiddlewaretoken -----> u'92a39322b16ed7e5e10dbd6c5ac64bf4'

department-0-description -----> u'Blah blah'

department-0-sp_description -----> u'....'

何か案は?

4

2 に答える 2

6

あなたの問題はここにあります:

       if request.method=='POST':
            if 'add_department' in request.POST:
                cp = request.POST.copy()
                cp['department-TOTAL_FORMS'] = int(cp['department-TOTAL_FORMS'])+ 1
                new_department = AddDepartmentFormSet(cp, prefix='department', instance=provider_obj)
            elif 'submit' in request.POST:
                formset = AddDepartmentFormSet(request.POST, instance=provider_obj)
                instances = formset.save(commit=False)
                for instance in instances:
                    instance.provider = provider_obj
                    instance.save()
                return HttpResponse("Departments have been added")
        else:
            new_department = AddDepartmentFormSet(prefix='department', instance=provider_obj)

POSTがない場合は、「department」というプレフィックスを渡します。'add_department'がPOSTにある場合は、'department'のプレフィックスを渡します。ただし、「submit」がPOSTにある場合は、プレフィックスを渡しません。プレフィックスがないと、フォームセットはPOSTで適切なデータを見つけることができません。

于 2011-01-11T13:17:51.450 に答える
3

2つのことが私に飛び出します...

まず、この部分を行う必要はありません。

for instance in instances:
   instance.provider = provider_obj
   instance.save()

あなたがこれをするとき、それは世話をされます:

formset = AddDepartmentFormSet(request.POST, instance=provider_obj)

次に、上部のコード:

provider_obj = retrieve_provider_instance(email)

動作していない可能性があります。提供したトレースバックでは、プロバイダーがそこに到達しているようには見えません...

department-0-provider -----> u''
于 2011-01-11T12:17:22.260 に答える