zoukankan      html  css  js  c++  java
  • Django之博客系统:增加评论

    3既然是博客,那肯定就有留言评论系统.在这一章就来建立一个评论系统.

    1 创建一个模型来保存评论

    2 创建一个表单来提交评论并且验证输入的数据

    3 添加一个视图函数来处理表单和保存新的评论到数据库

    4 编辑帖子模板来展示评论列表以及用来添加新评论的表单

    首先来创建一个模型来存储评论

    class Comment(models.Model):

        post=models.ForeignKey(Post,related_name='comments')

        name=models.CharField(max_length=80)

        email=models.EmailField()

        body=models.TextField()

        created=models.DateTimeField(auto_now_add=True)

        updated=models.DateTimeField(auto_now=True)

        active=models.BooleanField(default=True)

        class Meta:

            ordering = ('created',)

        def __str__(self):

            return 'Comments by {} on {}'.format(self.name,self.post)

    这就是我们增加评论的模型,其中最关键的是post,通过ForeignKeyCommentPost关联了起来,关联关系是多对一,原因是一个博客是有多个评论的.定义好之后,我们就可以通过commens.post来取得对应的帖子.以及通过postcomments.all()来取回一个帖子所有的评论.如果你没有定义related_name属性,Django会使用这个模型(model)的名称加上*_set*(在这里是:comment_set)来命名从相关联的对象反向定位到这个对象的manager

    接下来完成数据迁移

    zhf@zhf-maple:~/py_prj/mysite$ python manage.py makemigrations blog

    Migrations for 'blog':

      blog/migrations/0002_auto_20180303_1216.py

        - Create model Comment

        - Alter field author on post

        - Alter field body on post

        - Alter field created on post

        - Alter field publish on post

        - Alter field status on post

        - Alter field title on post

        - Alter field updated on post

        - Add field post to comment

    zhf@zhf-maple:~/py_prj/mysite$ python manage.py migrate

    Operations to perform:

      Apply all migrations: admin, auth, blog, contenttypes, sessions

    Running migrations:

      Applying blog.0002_auto_20180303_1216... OK

    同步增加一个评论的管理并在后台进行注册admin.site.register(Comment,CommentAdmin)

    class CommentAdmin(admin.ModelAdmin):

        list_display = ('name','email','post','created','active')

        list_filter = ('active','created','updated')

        search_fields = ('name','email','body')

     

    创建表单:

    在这里的表单和前面的邮件分享不太一样,这里通过模型来创建表单

    from .models import Comment

    class CommentsForm(forms.ModelForm):

        class Meta:

            model=Comment

            fields=('name','email','body')

    根据模型(model)创建表单,我们只需要在这个表单的Meta类里表明使用哪个模型(model)来构建表单。Django将会解析model并为我们动态的创建表单。每一种模型(model)字段类型都有对应的默认表单字段类型。表单验证时会考虑到我们定义模型(model)字段的方式。Django为模型(model)中包含的每个字段都创建了表单字段。然而,使用fields 列表你可以明确的告诉框架你想在你的表单中包含哪些字段,或者使用exclude 列表定义你想排除在外的那些字段。对于我们的CommentForm来说,我们在表单中只需要name,email,body字段,因为我们只需要用到这3个字段让我们的用户来填写。

    视图中操作ModelForm

    根据模型

    def post_list_page(request):

        object_list = Post.objects.all()

        paginator = Paginator(object_list, 1)  # 3 posts in each page

        page = request.GET.get('page')

        new_comment = None

        try:

            posts = paginator.page(page)

            comments=posts.object_list[0].comments.filter()

        except PageNotAnInteger:

            posts = paginator.page(1)

            comments = posts.object_list[0].comments.filter()

        except EmptyPage:

            posts = paginator.page(paginator.num_pages)

        id = posts.object_list[0].id

        post = get_object_or_404(Post, id=id, status='published')

        if request.method == 'POST':

            comment_form = CommentsForm()

            if comment_form.is_valid():

                new_comment = comment_form.save(commit=False)

                new_comment.post = post

                new_comment.save()

        else:

            comment_form = CommentsForm()

        return render(request,

                      'post/list.html',

                      {'page': page,

                       'posts': posts,

                       'comments':comments,

                       'new_comment': new_comment,

                       'comment_form': comment_form,

                       })

    通过comments=posts.object_list[0].comments.filter()得到每个博客对应的评论实例

    2 id = posts.object_list[0].id得到每个博客实例的id,并通过id得到Post实例

    通过上传的CommentsForm表单数据将评论和博客连接起来

    (1)我们通过调用这个表单的save()方法创建一个新的Comment对象

    new_comment = comment_form.save(commit=False)

    Save()方法创建了一个表单链接的model的实例,并将它保存到数据库中。如果你调用这个方法时设置commit=False,你创建的模型(model)实例不会即时保存到数据库中。当你想在最终保存之前修改这个model对象会非常方便,我们接下来将做这一步骤。save()方法是给ModelForm用的,而不是给Form实例用的,因为Form实例没有关联上任何模型(model

    为刚才的评论分配一个帖子

    new_comment.post = post

    (3) 最后,我们用下面的代码将新的评论保存到数据库中:

    new_comment.save()

    更新模板

    既然帖子有了评论功能,现在我们需要修改我们的list模板来适应这个功能。需要呈现如下功能

    评论总数

    显示评论的列表

    显示一个表单给用户来添加新的评论

    前面视图传递的comments参数。通过with comments.count as total_comments语句将评论的个数传递给total_comments.这样就能显示具体有多少个评论

          {% with comments.count as total_comments %}

      <h2>

    {{ total_comments }} comment{{ total_comments|pluralize }}

    现在加入评论列表我们使用{% for %}模板(template)标签(tag)来循环所有的评论。如果comments列为空我们会显示一个默认的信息,告诉我们的用户这篇帖子还没有任何评论。我们使用 {{ forloop.counter }}变量来枚举所有的评论,在每次迭代中该变量都包含循环计数。之后我们显示发送评论的用户名,日期,和评论的内容。

          {% for comment in comments %}

      <div class="comment">

        <p class="info">

          Comment {{ forloop.counter }} by {{ comment.name }}

          {{ comment.created }}

        </p>

        {{ comment.body|linebreaks }}

      </div>

    {% empty %}

      <p>还没有评论</p>

    {% endfor %}

    最后,你需要渲染表单或者显示一条成功的信息来代替之前的内容。在之前的代码后面添加如下内容

          {% if new_comment %}

      <h2>Your comment has been added.</h2>

      {% else %}

      <h2>添加新评论</h2>

      <form action="/blog/{{ p.id }}/comment/" method="post">

        {{ comment_form.as_p }}

        {% csrf_token %}

        <input type="submit" value="增加评论">

      </form>

    {% endif %}

    如果new_comment对象存在,我们会展示一条成功信息因为成功创建了一条新评论。否则,我们用段落<p>元素渲染表单中每一个字段

    下面来测试下功能:

    进入博客,此时还没有评论,因此显示0个评论。在下面有添加评论的界面

    2在评论表单中填入信息,点击增加评论。成功的话显示评论已经添加成功的页面

    3 此时在回到帖子的页面,可以看到添加的评论

  • 相关阅读:
    css常用字体
    多行文本显示省略号,点击展开隐藏
    某个公司采用公用电话传递数据,数据是四位的整数,在传递过程中是加密的, 加密规则如下:每位数字都加上5,然后用除以10的余数代替该数字,再将第一位和第四位交换, 第二位和第三位交换,请编写一个函数,传入原文,输出密文
    编写一个函数,计算任意两个数字之间所能组成的奇数个数,数字必须是个位数。 比如:计算0~3之间能组成的奇数是: 01、03、13、21、23、31
    Redis(一) 数据结构与底层存储 & 事务 & 持久化 & lua
    IO多路复用之Reactor
    IO多路复用之select poll epoll
    五种IO模型
    kafka(五) 流式处理 kafka stream
    kafka(二) 高性能技术分析
  • 原文地址:https://www.cnblogs.com/zhanghongfeng/p/8504325.html
Copyright © 2011-2022 走看看