Django-autocomplete-light как получить данные из html?

Я не могу понять, как получить данные из HTML-элемента, содержащего данные, сгенерированные django-autocomplete-light. Вот код формы:

class ThreadForm(forms.Form):
topic = forms.CharField(label="Topic", max_length=255)
body = forms.CharField(label="Body", widget=forms.Textarea(attrs={'rows': '12', 'cols':'100'}))
tags = autocomplete_light.fields.MultipleChoiceField(choices=(tuple((tag.name, tag.name) for tag in Tag.objects.all())),
                                      label='Tags',
                                      widget=autocomplete_light.widgets.MultipleChoiceWidget('TagAutocomplete',
                                                                                    attrs={'class':'form-control',
                                                                                           'placeholder':'Tag'}
                                                                                     )
                                                  )

def save(self, author, created):
  topic = self.cleaned_data['topic']
  body = self.cleaned_data['body']
  tags = self.cleaned_data['tags']
  th = Thread(author = author,
              topic = topic,
              body = body,
              created = created,
                )
  rtags = []
  for tag in tags:
      sr = Tag.objects.get(tag)
      rtags.append(sr.name)
  th.save()
  Tag.objects.update_tags(th, tags)

И autocomplete_light_registry.py:

from threads.models import Thread
import autocomplete_light
from tagging.models import Tag

class TagAutocomplete(autocomplete_light.AutocompleteModelBase):
    search_fields = ['^name']
autocomplete_light.register(Tag, TagAutocomplete, attrs={
    'data-autocomplete-minimum-characters': 1,
},)

Как видите, я изменил приложение django-autocomplete. В base.py я нашел переменную choice_html_format = '<span data-value="%s" name="choice">%s</span>' Attribute name, которая была добавлена ​​мной для получения таких данных:

tags = request.POST.get('name')

Но это не работает. Я получаю сообщение об ошибке типа "NoneType in not callable" Следующее, что я попробовал, это изменить choice_html с base.py:

def choice_html(self, choice):
    """
    Format a choice using :py:attr:`choice_html_format`.
    """
    return self.choice_html_format % (
        escape(self.choice_value(choice)),
        escape(self.choice_label(choice)))

Это оригинальная функция, я изменил choice_value(choice) на choice_label(choice). И получил ошибку "invalid literal for int() with base 10: <tag_name_here>". Похоже, что атрибут data-value предназначен только для типа int() (но я не могу найти, где его можно изменить, может быть, в js-функции, я не знаю).

И последнее, я пытаюсь получить pk каждого тега, а затем получить имя через менеджер. Но я получаю ошибку Cannot resolve keyword '4' into field. Choices are: id, items, name.

Я абсолютно уверен, что есть простой способ выполнить нужную мне задачу.


person kozlone    schedule 23.08.2015    source источник


Ответы (1)


autocomplete-light имеет шаблон с именем widget.html, который отображается в шаблоне:

...
{% block select %}
    {# a hidden select, that contains the actual selected values #}
    <select style="display:none" class="value-select" name="{{ name }}" id="{{ widget.html_id }}" multiple="multiple">
        {% for value in values %}
            <option value="{{ value|unlocalize }}" selected="selected">{{ value }}</option>
        {% endfor %}
    </select>
{% endblock %}
...

как видите, этот элемент <select> содержит все выбранные варианты для виджета автозаполнения.

Его имя (позже мы собираемся идентифицировать его по атрибуту имени) — это просто имя автозаполнения («теги»).

Итак, теперь вам нужно убедиться, что ваше поле автозаполнения в шаблоне заключено в теги <form>, чтобы значения были отправлены (если вы еще этого не сделали).

Следующим шагом является получение данных в представлении:

request.POST.getlist('tags')

Вот и все. Теперь у вас есть список первичных ключей выбранных значений:

>>> print(str(request.POST.getlist('tags'))
['1', '3', '4', '7', ...]
person Leistungsabfall    schedule 24.08.2015
comment
Я нахожу свою ошибку. Это было в sr = Tag.objects.get(tag), забыл добавить пк sr = Tag.objects.get(pk=tag) - person kozlone; 24.08.2015