Django個人博客搭建9-增加文章評論模塊

Django個人博客搭建1-創建Django項目和第一個App
Django個人博客搭建2-編寫文章Model模型,View視圖
Django個人博客搭建3-創建superuser並向數據庫中添加數據並改寫視圖
Django個人博客搭建4-配置使用 Bootstrap 4 改寫模板文件
Django個人博客搭建5-編寫文章詳情頁面並支持markdown語法
Django個人博客搭建6-對文章進行增刪查改
Django個人博客搭建7-對用戶登陸註冊等需求的實現
Django個人博客搭建8-優化文章模塊
Django個人博客搭建9-增加文章評論模塊

1.增加文章評論模塊

首先在命令行中新建評論app:

python manage.py startapp comment

然後在settiings.py中註冊comment模塊


INSTALLED_APPS = [
    'django.contrib.admin',
    ...
    'comment',
]

然後修改my_blog/urls.py中註冊根路由:

...
path('comment/', include('comment.urls', namespace='comment')),
...

在comment文件夾下新建urls.py編寫如下代碼:

app_name = 'comments'

urlpatterns = [
    
]

接下來編寫評論的模型comment/models:

from django.contrib.auth.models import User
from django.db import models

# Create your models here.
from article.models import ArticlePost


class Comment(models.Model):
    article = models.ForeignKey(
        ArticlePost,
        on_delete=models.CASCADE,
        related_name='comments',
    )
    
    user = models.ForeignKey(
        User,
        on_delete=models.CASCADE,
        related_name='comments',
    )
    body = models.TextField()
    created = models.DateTimeField(auto_now_add=True)
    
    class Meta:
        ordering = ('created',)
        
    def __str__(self):
        return self.body[:20]

模型的兩個外鍵分別是被評論的文章和評論發佈者
接着我們進行數據遷移:

F:\Desktop\myblog>python manage.py makemigrations
System check identified some issues:

WARNINGS:
article.ArticlePost.created: (fields.W161) Fixed default value provided.
        HINT: It seems you set a fixed date / time / datetime value as default for this field. This may not be what you want. If you want to have the current date as default, use `django.utils.timezone.now`
Migrations for 'article':
  article\migrations\0004_auto_20190212_1049.py
    - Alter field created on articlepost
Migrations for 'comment':
  comment\migrations\0001_initial.py
    - Create model Comment

F:\Desktop\myblog>
F:\Desktop\myblog>python manage.py migrate
System check identified some issues:

WARNINGS:
article.ArticlePost.created: (fields.W161) Fixed default value provided.
        HINT: It seems you set a fixed date / time / datetime value as default for this field. This may not be what you want. If you want to have the current date as default, use `django.utils.timezone.now`
Operations to perform:
  Apply all migrations: admin, article, auth, comment, contenttypes, sessions, userprofile
Running migrations:
  Applying article.0004_auto_20190212_1049... OK
  Applying comment.0001_initial... OK

F:\Desktop\myblog>

用戶提交評論時會用到表單,因此新建表單類comment/forms.py

from django import forms

from comment.models import Comment


class CommentForm(forms.ModelForm):
    class Meta:
        model = Comment
        fields = ['body']

評論的兩個外鍵通過視圖邏輯自動填寫,所以這裏只需要提交body就可以了

接下來修改comment/urls.py

from django.urls import path
from . import views

app_name = 'comments'

urlpatterns = [
    path('post-comment/<int:article_id>/', views.post_comment, name='post_comment'),
]

接下來在comment/views.py中新增post_comment視圖:

from django.contrib.auth.decorators import login_required
from django.http import HttpResponse
from django.shortcuts import render, get_object_or_404, redirect

# Create your views here.
from article.models import ArticlePost
from comment.forms import CommentForm


@login_required(login_url='/userprofile/login/')
def post_comment(request, article_id):
    article = get_object_or_404(ArticlePost, id=article_id)

    # 處理POST請求
    if request.method == 'POST':
        comment_form = CommentForm(request.POST)
        if comment_form.is_valid():
            new_comment = comment_form.save(commit=False)
            new_comment.article = article
            new_comment.user = request.user
            new_comment.save()
            return redirect(article)
        else:
            return HttpResponse('表單內容有誤,請重新填寫')


    else:
        return HttpResponse("發表評論僅接受post請求")

get_object_or_404作用時用戶請求一個不存在的對象時會返回ERROR404
redirect:返回到一個適合的url中:即用戶發送評論後,重新定向到文章詳情頁面.當其參數是一個Model對象時,會自動調用這個Model對象的get_absolute_url()方法。因此接下來馬上修改article(article/models.py)的模型。

# 博客文章數據模型
class ArticlePost(models.Model):
    ...

    def get_absolute_url(self):
        return reverse('article:article_detail', args=[self.id])

通過reverse方法返回文章詳情頁面的url,實現了路由的重定向
接下來因爲評論也需要咋i文章詳情頁面展示,所以必須把評論模塊的上下文也傳遞到模板中
修改article/views.py中的article_detail:


# 文章詳情
def article_detail(request, id):
    ...
    comments = Comment.objects.filter(article=id)

    ...
    context = {'article': article, 'toc': md.toc, 'comments': comments}
    # 載入模板,並返回context對象p
    return render(request, 'article/detail.html', context)

很簡單就是取出對應文章的所有評論( filter() 可以取出多個滿足條件的對象,而 get() 只能取出1個)

最後一步修改文章詳情頁面templates/article.detail.html:

...
<div>
                    瀏覽量:{{ article.total_views }}
                </div>
                <div class="col-12">
                    <p>{{ article.body|safe }}</p>
                </div>
                <!-- 發表評論 -->
                <hr>
                {% if user.is_authenticated %}
                    <div>
                        <form action="{% url 'comment:post_comment' article.id %}"
                              method="post">
                            {% csrf_token %}
                            <div class="form-group">
                                <label for="body">
                                    <strong>
                                        我也要發言:
                                    </strong>
                                </label>
                                <textarea type="text" class="form-control" id="body" name="body" rows="2"></textarea>
                            </div>
                            <button type="submit" class="btn btn-primary">發送</button>
                        </form>
                    </div>
                    <br>
                    {% else %}
                        <br>
                    <h5 class="row justify-content-center"><a href="{% url 'userprofile:login' %}">登錄</a>後回覆
                    </h5>
                    <br>
                {% endif%}
                <!-- 顯示評論 -->
                <h4>
                    共有{{ comments.count }}條評論
                </h4>
                <div>
                    {% for comment in comments %}
                        <hr>
                        <p>
                            <strong style="color: pink">
                                {{ comment.user }}
                            </strong><span style="color: green">
                                {{ comment.created|date:"Y-m-d H:i:s" }}
                            </span>時說:
                        </p>
                        <pre style="font-family: inherit; font-size: 1em;white-space: pre-wrap;word-wrap: break-word;">        {{ comment.body }}
                        </pre>
                    {% endfor %}
                </div>
            </div>
            {# 目錄 #}
            <div class="col-3 mt-4">
            ...

我們在pre style中添加的**white-space: pre-wrap;word-wrap: break-word;**時爲了讓評論過長時自動換行,不會出現滾動條.
我們重啓服務器並評論查看效果
在這裏插入圖片描述
我們可以看到評論過長時也不會出現不美觀的現象或者影響觀看了
可以看奧評論功能已經可以正常使用了,退出登陸後:
在這裏插入圖片描述
這樣文章評論模塊就已經全部完成了

Django個人博客搭建1-創建Django項目和第一個App
Django個人博客搭建2-編寫文章Model模型,View視圖
Django個人博客搭建3-創建superuser並向數據庫中添加數據並改寫視圖
Django個人博客搭建4-配置使用 Bootstrap 4 改寫模板文件
Django個人博客搭建5-編寫文章詳情頁面並支持markdown語法
Django個人博客搭建6-對文章進行增刪查改
Django個人博客搭建7-對用戶登陸註冊等需求的實現
Django個人博客搭建8-優化文章模塊
Django個人博客搭建9-增加文章評論模塊

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章