/ polls / 1 /投票时的BootstrapError

时间:2017-08-28 12:24:12

标签: python django

我正在通过浏览Django教程创建一个网站。但

/ polls / 1 /投票时的BootstrapError 参数“form”应包含有效的Django表单。

错误发生。 回溯是

Traceback:

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/utils/datastructures.py" in __getitem__
  83.             list_ = super(MultiValueDict, self).__getitem__(key)

During handling of the above exception ('choice'), another exception occurred:

File "/Users/XXX/djangostudy/polls/views.py" in vote
  26.         selected_choice = question.choice_set.get(pk=request.POST['choice'])

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/utils/datastructures.py" in __getitem__
  85.             raise MultiValueDictKeyError(repr(key))

During handling of the above exception ("'choice'"), another exception occurred:

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/core/handlers/exception.py" in inner
  41.             response = get_response(request)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/core/handlers/base.py" in _get_response
  187.                 response = self.process_exception_by_middleware(e, request)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/core/handlers/base.py" in _get_response
  185.                 response = wrapped_callback(request, *callback_args, **callback_kwargs)

File "/Users/XXX/djangostudy/polls/views.py" in vote
  30.             'error_message':"You didn't select a choice",

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/shortcuts.py" in render
  30.     content = loader.render_to_string(template_name, context, request, using=using)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/loader.py" in render_to_string
  68.     return template.render(context, request)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/backends/django.py" in render
  66.             return self.template.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render
  207.                     return self._render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in _render
  199.         return self.nodelist.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render
  990.                 bit = node.render_annotated(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render_annotated
  957.             return self.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/loader_tags.py" in render
  177.             return compiled_parent._render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in _render
  199.         return self.nodelist.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render
  990.                 bit = node.render_annotated(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render_annotated
  957.             return self.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/loader_tags.py" in render
  177.             return compiled_parent._render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in _render
  199.         return self.nodelist.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render
  990.                 bit = node.render_annotated(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render_annotated
  957.             return self.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/loader_tags.py" in render
  72.                 result = block.nodelist.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render
  990.                 bit = node.render_annotated(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/base.py" in render_annotated
  957.             return self.render(context)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/template/library.py" in render
  203.         output = self.func(*resolved_args, **resolved_kwargs)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/bootstrap3/templatetags/bootstrap3.py" in bootstrap_form
  338.     return render_form(*args, **kwargs)

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/bootstrap3/forms.py" in render_form
  53.     return renderer_cls(form, **kwargs).render()

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/bootstrap3/renderers.py" in __init__
  161.                 'Parameter "form" should contain a valid Django Form.')

Exception Type: BootstrapError at /polls/1/vote
Exception Value: Parameter "form" should contain a valid Django Form.

模板中的base.html是

{% load staticfiles %}
{% load bootstrap3 %}
<html lang="en">
  <head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1">
    <meta name="description" content="">
    <meta name="author" content="">
    <link rel="icon" href="../../favicon.ico">

    <title>Starter Template for Bootstrap</title>

    <!-- Bootstrap core CSS -->
    <link href="{% static 'css/bootstrap.min.css' %}" rel="stylesheet">
    <style type="text/css">
body {
  padding-top: 50px;
}
    </style>
  </head>

  <body>
    <nav class="navbar navbar-inverse navbar-fixed-top">
      <div class="container">
        <div class="navbar-header">
          <button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#navbar" aria-expanded="false" aria-controls="navbar">
            <span class="sr-only">Toggle navigation</span>
            <span class="icon-bar"></span>
            <span class="icon-bar"></span>
            <span class="icon-bar"></span>
          </button>
          <a class="navbar-brand" href="{% url 'index' %}">Tutorial</a>
        </div>
        <div id="navbar" class="collapse navbar-collapse">
          <ul class="nav navbar-nav">
            <li class="{% block nav_polls %}{% endblock %}"><a href="{% url 'polls:index' %}">polls</a></li>
            <li class=""><a href="{% url 'admin:index' %}">admin</a></li>
          </ul>
        </div><!--/.nav-collapse -->
      </div>
    </nav>

    <div class="container">
        {% bootstrap_messages messages %}
        {% block contents %}{% endblock %}
    </div>
    <!-- Bootstrap core JavaScript
    ================================================== -->
    <!-- Placed at the end of the document so the pages load faster -->
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.3/jquery.min.js"></script>
    <script>window.jQuery || document.write('<script src="../../assets/js/vendor/jquery.min.js"><\/script>')</script>
    <script src="{% static 'js/bootstrap.min.js' %}"></script>
  </body>
</html>
民意调查中的

views.py是

from django.shortcuts import render
from django.urls import reverse_lazy
from .models import Question
from django.shortcuts import get_object_or_404,redirect
from .models import Choice
from .forms import MyForm
from .forms import VoteForm
from django.views.generic import FormView
from django.views.generic.detail import SingleObjectMixin
from django.shortcuts import resolve_url
from django.contrib import messages
from django.urls import reverse

# Create your views here.
def index(request):
    return render(request,'polls/index.html',{
        'questions': Question.objects.all(),
    })


def vote(request,pk):
    question = get_object_or_404(Question,pk=pk)
    try:
        selected_choice = question.choice_set.get(pk=request.POST['choice'])
    except (KeyError,Choice.DoesNotExist):
        return render(request,'polls/detail.html',{
            'question':question,
            'error_message':"You didn't select a choice",
        })
    else:
        selected_choice.votes += 1
        selected_choice.save()
    # return redirect(reverse('polls:poll_results'), pk=pk)
    # return redirect('results_url', pk=pk)
    return redirect('polls:polls_results', pk=pk)


def results(request,pk):
    obj = get_object_or_404(Question,pk=pk)
    return render(request,'polls/results.html',{
        'question':obj,
    })

class FormTest(FormView):
   form_class = MyForm
   template_name = 'polls/form.html'
   success_url = reverse_lazy('polls:index')
form_test = FormTest.as_view()

class Detail(SingleObjectMixin,FormView):
    model = Question
    form_class = VoteForm
    context_object_name = 'question'
    template_name = 'polls/detail.html'

    def get(self, request, *args, **kwargs):
        self.object = self.get_object()
        return super().post(request, *args, **kwargs)

    def post(self, request, *args, **kwargs):
        self.object = self.get_object()
        return super().post(request, *args, **kwargs)

    def get_form_kwargs(self):
        kwargs = super().get_form_kwargs()
        kwargs['question'] = self.object
        return kwargs

    def form_valid(self, form):
        form.vote()
        choice = form.cleaned_data['choice']
        messages.success(self.request,'"%s"に投票しました' % choice)
        return super().form_valid(form)

    def get_success_url(self):
        return resolve_url('polls:results',self.kwargs['pk'])

detail = Detail.as_view()

我能理解为什么会发生这种错误。这是否需要Form类?我该如何解决这个问题?

1 个答案:

答案 0 :(得分:1)

当您查看Traceback时,您可以看到顶部的某处:

File "/Users/XXX/djangostudy/polls/views.py" in vote
26.         selected_choice =question.choice_set.get(pk=request.POST['choice'])

File "/Users/XXX/anaconda/envs/py36/lib/python3.6/site-packages/django/utils/datastructures.py" in __getitem__
85.             raise MultiValueDictKeyError(repr(key))

您未在try:...except:块中发现此错误。

首先,我会检查request.POST['choice']是否会返回您认为的内容。

编辑:

正如评论中所指出的,使用try / except可能是一个坏主意。最好检查POST字典是否具有键“选择”。例如,使用.get()方法。另请参阅https://docs.djangoproject.com/en/dev/ref/request-response/#httprequest-objects