Создание шаблонов формы комментариев
Мы создадим шаблон комментарной формы, которая будет использоваться в двух местах:
-
в шаблоне детальной информации о посте, ассоциированном с представлением
post_detail, чтобы пользователи могли публиковать комментарии; -
в шаблоне комментария к посту, ассоциированном с представлением
post_comment, чтобы отображать форму снова, если в форме есть какие либо ошибки.
Мы создадим шаблон формы и будем использовать шаблонный тег {% include %}, чтобы вставлять его в два других шаблона.
Внутри каталога templates/blog/post/ создайте новый каталог includes/.
В этот каталог добавьте новый файл и назовите его comment_form.html.
Файловая структура должна выглядеть следующим образом:
Отредактируйте новый шаблон blog/post/includes/comment_form.html, добавив следующий ниже исходный код:
<h2>Add a new comment</h2>
<form action="{% url 'blog:post_comment' post.id %}" method="post">
{{ form.as_p }}
{% csrf_token %}
<p><input type="submit" value="Add comment"></p>
</form>
В указанном шаблоне мы динамически формируем URL-адрес action HTML-элемента <form>, используя шаблонный тег {% url %}.
Мы формируем URL-адрес представления post_comment, которое будет обрабатывать форму.
Мы отображаем форму, прорисованную абзацами HTML, и вставляем тег {% csrf_token %}, чтобы защититься от CSRF, поскольку данная форма будет передаваться на обработку методом POST.
Внутри каталога templates/blog/post/ создайте новый файл приложения blog и назовите его comment.html.
Теперь файловая структура должна выглядеть следующим образом:
Отредактируйте новый шаблон blog/post/comment.html, добавив следующий ниже исходный код:
{% extends "blog/base.html" %}
{% block title %}Add a comment{% endblock %}
{% block content %}
{% if comment %}
<h2>Your comment has been added.</h2>
<p><a href="{{ post.get_absolute_url }}">Back to the post</a></p>
{% else %}
{% include "blog/post/includes/comment_form.html" %}
{% endif %}
{% endblock %}
Это шаблон представления комментариев к посту. В данном представлении мы ожидаем, что форма будет передаваться на обработку методом POST.
Шаблон охватывает два разных сценария:
-
если переданные данные формы валидны, то переменная
commentбудет содержать созданный объектcomment,и на страницу будет выведено сообщение об успехе; -
если переданные данные формы не валидны, то переменной
commentбудет назначено значениеNone. В этом случае мы отобразим комментарную форму. Для вставки созданного ранее шаблонаcomment_form.htmlиспользуется шаблонный тег{% include %}.
Добавление комментариев в представление детальной информации о посте
Откройте файл views.py приложения blog и отредактируйте представление post_detail, как показано ниже:
def post_detail(request, year, month, day, post):
post = get_object_or_404(Post,
status=Post.Status.PUBLISHED,
slug=post,
publish__year=year,
publish__month=month,
publish__day=day)
# Список активных комментариев к этому посту
comments = post.comments.filter(active=True)
# Форма для комментирования пользователями
form = CommentForm()
return render(request,
'blog/post/detail.html',
{'post': post,
'comments': comments,
'form': form})
Давайте рассмотрим исходный код, который мы добавили в представление post_detail:
-
мы добавили набор запросов QuerySet, чтобы извлекать все активные комментарии к посту, как показано ниже:
comments = post.comments.filter(active=True) -
этот набор запросов сформирован с использованием объекта
post. Вместо того чтобы формировать набор запросов для комментарной модели напрямую, мы используем объектpost, чтобы извлекать связанные объектыComment. Мы применяем менеджерcommentsдля ранее определенных в моделиCommentсвязанных сCommentобъектов, используя атрибутrelated_nameполяForeignKeyв моделиPost; -
мы также создали экземпляр формы для комментария посредством инструкции
form = CommentForm().