Django

时间:2016-10-16 17:24:33

标签: django django-forms

我遇到了一个与表单相关的问题,其中来自POST的数据显然已被发回,但是Django正在将其剥离,以便它不会进入我的表单类。

以下是我的类post()中的一些代码片段,它们显示了从模板返回的数据,以及数据是如何通过表单类过滤的。

为什么会这样?

直接从POST中获取数据而不使用内置表单类过滤有什么危害?

print(request.POST)

产生这个:

<QueryDict: {'book': ['Zippity do dah,'], 'weather': ["It's raining!"], 'dividend': ['Zippity aye!'], 'earnings': ['Yo man, one step at a time.'], 'csrfmiddlewaretoken': ['3MWFOwebVeYfCum8JaGvITRB542b3jbp']}>

main_form = self.main_form_class(request.POST)
print('\n','main_form: ',main_form)

产生这个:

main_form:  <tr><th><label for="id_weather">weather:</label></th><td><input id="id_weather" maxlength="256" name="weather" size="36" type="text" /></td></tr>
<tr><th><label for="id_book">book:</label></th><td><input id="id_book" maxlength="256" name="book" size="36" type="text" /></td></tr>
<tr><th><label for="id_dividend">dividend:</label></th><td><input id="id_dividend" maxlength="256" name="dividend" size="36" type="text" /></td></tr>
<tr><th><label for="id_earnings">earnings:</label></th><td><input id="id_earnings" maxlength="256" name="earnings" size="36" type="text" /></td></tr>
<tr><th><label for="id_csrfmiddlewaretoken">csrfmiddlewaretoken:</label></th><td><input id="id_csrfmiddlewaretoken" maxlength="256" name="csrfmiddlewaretoken" size="36" type="text" /></td></tr>

您可以看到main_form中没有包含“值”。

main_form.is_valid() is never True

main_form.cleaned_data throws an error - if I pull it out in front of main_form.is_valid()

帮助!

好的 - 这里有一些代码:

我有一个子类,其表单不会从POST请求返回数据。超类也有一个表单,这个IS从同一个POST请求返回数据。也就是说超类正在请求用户输入,并且有几个子类扩展超类并请求其他数据。超类总是从表单的一部分返回数据,但子类不会。

子类在POST中返回数据,但数据不会返回到Django视图。这似乎是一个错误,(但也许它是一个特征)或另一个可能的情况是我错过了一些东西。但是,我找不到它。

解决方案可能是没有超级级别,只有一个非DRY程序。呸。

我在终端命令中添加了一些print()来查看返回的内容(或不回来)来验证这一点。

我还使用浏览器的开发人员工具看到POST确实在其中有必要的数据,应该返回到视图进行处理。但是,此数据不会使其返回到视图。

子类视图代码如下所示:

class MainView(SidebarBaseView):
  main_form_class = MainViewForm
  template_name = 'myapp/my_view.html'

  def get(self, request, *args, **kwargs):
    context = super(MainView, self).get(request, *args, **kwargs)
    context.update(self.get_context_data(*args, **kwargs))
    main_form_initial = {}
    for detail in context['my_data']: # my_data comes from get_context_data()
      field_name = detail.datatype.name
      main_form_initial[field_name] = detail.note

    main_form = self.main_form_class(initial=main_form_initial)
    context['main_form'] = main_form
    return render(request, self.template_name, context)

  def post(self, request, *args, **kwargs):
    context = super(MainView, self).post(request, *args, **kwargs)
    context.update(self.get_context_data(*args, **kwargs))
    main_form = self.main_form_class(request.POST)

    print('\n','main_form',main_form,'\n') #to terminal

    if main_form.is_valid():
      main_form_data = main_form.cleaned_data

      print('\n', 'cleaned data', main_form_data, '\n') #to terminal

      for detail in context['my_data']:
        field_name = detail.datatype.name
        detail.note = main_form_data[field_name]
        detail.save()

    main_form_initial = {}
    for detail in context['my_data']:
      field_name = detail.datatype.name
      main_form_initial[field_name] = detail.note

    main_form = self.main_form_class(initial=main_form_initial)
    context['main_form'] = main_form

    return render(request, self.template_name, context)

  def get_context_data(self, *args, **kwargs):
    context = super(CompanyStatsView, self).get_context_data(**kwargs)
    ...
    return context

我的表单生成动态字段,因为我最终需要向其发送可变数量的字段:

class MyMainViewForm(forms.Form):
  fields = {}
  field_names = ['weather','book','dividend','earnings']
  def __init__(self, field_names, *args, **kwargs):
    super(MyMainViewForm, self).__init__(*args, **kwargs)
    for name in field_names:
      self.fields[name] = forms.CharField(label=name, max_length=256, required=False, widget=forms.TextInput(attrs={'size':'36'}))

我的模板如下所示:

{% extends 'my_sidebar.html' %}
{% block content_right %}

<div class="container-fluid">
  <h2>Table</h2>
  <div class="col-sm-4">
    <div class="table-responsive">
      <table class="table">
        <tbody>
        {% for detail in my_data %}
          <tr height="50">
            <td>{{ detail.datatype.full_name }}:</td>
            <td class="text-right">{{ detail }}</td>
         </tr>
        {% endfor %}
        </tbody>
      </table>
    </div>
  </div>
  <div class="col-sm-4">
    <div class="table-responsive">
      <table class="table">
        <tbody>
        <form action="." method="post"> {% csrf_token %}
          {% for note in main_form %}
          <tr height="50">
            <td>{{ note }}</td>
          </tr>
          {% endfor %}
          <p><input type="submit" value="Save"></p>
        </form>
        </tbody>
      </table>
    </div>
  </div>
  <div class="col-sm-4">
  </div>
</div>
{% endblock %}

有什么想法吗?

urls.py的相关部分是:

from django.conf.urls import url
from . import views

app_name = 'my_app'
urlpatterns = [
  url(r'^(?P<slug>[A-Z]+)/data/$', views.MainView.as_view(), name='main-view',),
...
]

0 个答案:

没有答案