Извлечение моделей из формы с ModelMultipleChoiceField - PullRequest
1 голос
/ 12 апреля 2010

У меня проблемы с формами, особенно ModelMultipleChoiceField.

Я собрал этот код из различных примеров, но, к сожалению, он не работает.

Я бы хотел:

  1. Поиск некоторых работ на work_search.html
  2. Показать результаты поиска с флажками рядом с каждым результатом
  3. Выберите работы, которые я хочу, с помощью флажков
  4. После нажатия Добавить, показать, какие работы были выбраны.

Я верю, что все в порядке, кроме последней части. На странице просто отображаются «работы»: (

Вот код - извините за длину.

Models.py

class Work(models.Model):
    title = models.CharField(max_length=200)
    artist = models.CharField(max_length=200)
    writers = models.CharField(max_length=200)

    def __unicode__(self):
        return self.title + ' - ' + self.artist

forms.py

class WorkSelectForm(forms.Form):
    def __init__(self, queryset, *args, **kwargs):
        super(WorkSelectForm, self).__init__(*args, **kwargs)
        self.fields['works'] = forms.ModelMultipleChoiceField(queryset=queryset,       widget=forms.CheckboxSelectMultiple())

views.py

def work_search(request):
    query = request.GET.get('q', '')
    if query:
        qset = (
            Q(title__icontains=query) |
            Q(artist__icontains=query) |
            Q(writers__icontains=query)
        )
        results = Work.objects.filter(qset).distinct()
        form = WorkSelectForm(results)
        return render_to_response("work_search.html", {"form": form, "query": query })    
    else:
        results = []
    return render_to_response("work_search.html", {"query": query })

def add_works(request):
    #if request.method == POST:
    form = WorkSelectForm(request.POST)
    #if form.isvalid():
    items = form.fields['works'].queryset
    return render_to_response("add_works.html", {"items":items})

work_search.html

{% extends "base.html" %}
{% block content %}
  <h1>Search</h1>
  <form action="." method="GET">
    <label for="q">Search: </label>
    <input type="text" name="q" value="{{ query|escape }}">
    <input type="submit" value="Search">
  </form>

  {% if query %}
    <h2>Results for "{{ query|escape }}":</h2>
    <form action="add_works" method="post">
        <ul>
        {% if form %}
            {{ form.as_ul }}
        {% endif %}
        </ul>
        <input type="submit" value="Add">
    </form>
  {% endif %}
{% endblock %}

add_works.html

{% extends "base.html" %}
{% block content %}
    {% if items %}
        {% for item in items %}
            {{ item }}
        {% endfor %}
    {% else %}
        <p>Nothing selected</p>
    {% endif %}
{% endblock %}

1 Ответ

1 голос
/ 13 апреля 2010

В add_works вы не правильно строите WorkSelectForm. В качестве первого параметра он ожидает набор запросов возможных / авторизованных вариантов, , затем POST данных.

Кроме того, вы не получаете доступ к выбранным работам правильно из формы. Вы должны использовать is_valid метод в форме, затем использовать cleaned_data, как описано в Документ .

Из того, что я вижу в вашем work_search представлении, нет ограничений на то, какие Work объекты вы можете искать, а затем добавлять к результату, так что вы можете сделать просто:

def add_works(request):
    #if request.method == POST:
    form = WorkSelectForm(Work.objects.all(), request.POST)
    if form.is_valid():
        # the items are in form.cleaned_data['works']
        items = form.cleaned_data['works']
        return render_to_response("add_works.html", {"items":items})
    else:
       # handle error case here
       ...
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...