Общие представления Django 1.7

В настоящее время я просматриваю официальный учебник Django, и у меня возникают проблемы с попыткой понять, как на самом деле работают общие представления.

Исходный код из официальной документации:

class DetailView(generic.DetailView):
    model = Question
    template_name = 'polls/detail.html'


class ResultsView(generic.DetailView):
    model = Question
    template_name = 'polls/results.html'

Detail.html

<h1>{{ question.question_text }}</h1>

{% if error_message %}<p><strong>{{ error_message }}</strong></p>{% endif %}

<form action="{% url 'polls:vote' question.id %}" method="post">
{% csrf_token %}
{% for choice in question.choice_set.all %}
    <input type="radio" name="choice" id="choice{{ forloop.counter }}" value="{{ choice.id }}" />
    <label for="choice{{ forloop.counter }}">{{ choice.choice_text }}</label><br />
{% endfor %}
<input type="submit" value="Vote" />
</form>

результаты.html

<h1>{{ question.question_text }}</h1>

<ul>
{% for choice in question.choice_set.all %}
    <li>{{ choice.choice_text }} -- {{ choice.votes }} vote{{ choice.votes|pluralize }}</li>
{% endfor %}
</ul>

<a href="{% url 'polls:detail' question.id %}">Vote again?</a>

Теперь я понимаю, что ListView и DetailView — это общие представления по умолчанию, предоставляемые Django.

Как DetailView и ResultsView генерируют переменную контекста question в detail.html и result.html? Кроме того, как переменная контекста error_message внутри detail.html генерируется DetailView?


person Manas Chaturvedi    schedule 20.01.2015    source источник


Ответы (2)


Объект question назван в честь атрибута model общего представления (в данном случае Question). Детальные виды включают такой объект автоматически.

Если вы спрашиваете, как выбирается конкретный объект question, подробному представлению по умолчанию должно быть передано значение pk из URL-адреса, которое затем используется для поиска этого объекта. Соответствующий код из polls/urls.py выглядит следующим образом:

url(r'^(?P<pk>\d+)/$', views.DetailView.as_view(), name='detail'),

error_message, с другой стороны, не включается в общие представления. Он используется только в примере для неуниверсального представления, потому что оно явно включает его в контекст:

return render(request, 'polls/detail.html', {
    'question': p,
    'error_message': "You didn't select a choice.",
})
person Daniel Robinson    schedule 20.01.2015

DetailView имеет параметр context_object_name, который вы можете использовать для установки имени объекта в шаблоне, но если вы его не установите, метод get_context_object_name сделает следующее:

def get_context_object_name(self, obj):
    """
    Get the name to use for the object.
    """
    if self.context_object_name:
        return self.context_object_name
    elif isinstance(obj, models.Model):
        return obj._meta.model_name
    else:
        return None

Он использует название модели. Затем get_context_data из SingleObjectMixin помещает этот идентификатор в контекст. В любом случае вы также можете получить доступ к объекту с идентификатором object.

Я уверен, что вы можете прочитать все это в документации Django, но есть отличная страница, на которой вы можете изучить представления на основе классов.

person Paulo Almeida    schedule 20.01.2015