文章详情与点赞和评论

前端代码:

{% extends 'base.html' %}

{% block css %}
    <style>
        #div_digg {
            float: right;
            margin-bottom: 10px;
            margin-right: 30px;
            font-size: 12px;
            width: 128px;
            text-align: center;
            margin-top: 10px;
        }

        .diggit {
            float: left;
            width: 46px;
            height: 52px;
            background: url('/static/img/upup.gif') no-repeat;
            text-align: center;
            cursor: pointer;
            margin-top: 2px;
            padding-top: 5px;
        }

        .buryit {
            float: right;
            margin-left: 20px;
            width: 46px;
            height: 52px;
            background: url('/static/img/downdown.gif') no-repeat;
            text-align: center;
            cursor: pointer;
            margin-top: 2px;
            padding-top: 5px;
        }

        .clear {
            clear: both;
        }

        .diggword {
            margin-top: 5px;
            margin-left: 0;
            font-size: 12px;
            color: #808080;
        }
    </style>
{% endblock %}

{% block content %}
    <h2>{{ article_obj.title }}</h2>
    <div>{{ article_obj.content|safe }}</div>




    {#    点赞点踩前端样式渲染#}
    <div class="clearfix">
        <div id="div_digg">
            <div class="diggit action">
                <span class="diggnum" id="digg_count">{{ article_obj.up_num }}</span>
            </div>
            <div class="buryit action">
                <span class="burynum" id="bury_count">{{ article_obj.down_num }}</span>
            </div>
            <div class="clear"></div>
            <span style="color: red" id="info"></span>
        </div>
    </div>

{#    评论楼渲染#}
    <div>
        <p>评论列表</p>
{#    #1楼 2018-04-11 23:03 最咸的咸鱼#}
    <ul class="list-group">
        {% for comment in comment_list %}
            <li class="list-group-item">
                <span>#{{ forloop.counter }}楼</span>
                <span>{{ comment.create_time|date:'Y-m-d h:i:s' }}</span>
                <span><a href="/{{ comment.user.username }}/">{{ comment.user.username }}</a></span>
                <span><a class="pull-right reply" username="{{ comment.user.username }}" comment_id = "{{ comment.pk }}">回复</a></span>
                <p>
                    {% if comment.parent_id %}
                        <p>@{{ comment.parent.user.username }}</p>
                    {% endif %}
                    {{ comment.content }}
                </p>
            </li>
        {% endfor %}
</ul>


    </div>

    {#    渲染前端评论样式#}
    {% if request.user.is_authenticated %}
        <div>
        <p>发表评论</p>
        <p>
            昵称:<input type="text" id="tbCommentAuthor" class="author" disabled="disabled" size="50"
                      value="{{ request.user.username }}">
        </p>
        <p>评论内容:</p>
        <p><textarea name="comment" id="comment" cols="60" rows="10"></textarea></p>
        <p>
            <button class="btn btn-primary" id="submit">提交评论</button>
            <span style="color: red" class="error"></span>
        </p>
    </div>
    {% else %}
        <a href="/login/">登录</a>
        <a href="/register/">注册</a>
    {% endif %}

{% endblock %}


{% block js %}
    <script>
        // 点赞点踩
        $('.action').on('click', function () {
            var $btn = $(this);
            // 如何判断用户点的是赞还是踩
            var isUp = $(this).hasClass('diggit');
            $.ajax({
                url: '/UpAndDown/',  // 专门朝处理点赞点踩业务逻辑的后端视图函数提交请求
                type: 'post',
                data: {
                    'article_id': '{{ article_obj.pk }}',
                    'is_up': isUp,
                    'csrfmiddlewaretoken': '{{ csrf_token }}'
                },
                success: function (data) {
                    if (data.code == 1000) {
                        $('#info').text(data.msg);
                        // 动态修改数字
                        var old_num = $btn.children().text();
                        $btn.children().text(Number(old_num) + 1)  // 一定要转数字 才能做加减
                    } else {
                        $('#info').html(data.msg)
                    }
                }
            })
        });

        // 提交评论
        // 先在全局定义一个变量
        var commentId = null;
        $('#submit').click(function () {
            var conTent = $('#comment').val();
            var conTent1 = $('#comment').val();
            if(commentId){
                // 找到\n所对应的索引
                var indexN = conTent.indexOf('\n') + 1;
                conTent = conTent.slice(indexN)  // 将indexN前面所有的内容全部切掉 只保留后面的内容
            }
            $.ajax({
                url:'/comment/',
                type:'post',
                data:{
                    'article_id':'{{ article_obj.pk }}',
                    'content':conTent,
                    'parent_id':commentId,
                    'csrfmiddlewaretoken':'{{ csrf_token }}'
                },
                success:function (data) {
                    if (data.code == 1000){
                        $('.error').text(data.msg);
                        $('#comment').val('');
                        // 用户提交评论之后  先用DOM操作临时渲染一个评论楼出来 当用户刷新页面的时候再按照统一的评论楼样式渲染
                        // 1 动态生成标签
                        var userName = '{{ request.user.username }}';

                        var temp = `
                            <li class="list-group-item">
                            <span><span class="glyphicon glyphicon-comment"></span><a href="/${userName}/">${userName}:</a></span>
                            <p>
                                ${conTent1}
                            </p>
                        </li>
                        `;
                        // 2 将生成好的标签 添加到ul标签内
                        $('.list-group').append(temp);
                        // 清空全局变量 commmentId
                        commentId = null;
                    }
                }
            })
        });

        // 点击恢复按钮
        $('.reply').click(function () {
            // 不仅要获取评论的评论人用户名 还需要获取评论的主键值
            var commentUserName = $(this).attr('username');
            commentId = $(this).attr('comment_id');  // 给全局的commentId赋值
            // 将信息写入textarea中 并自动聚焦
            $('#comment').val('@'+commentUserName+'\n').focus()
        })
    </script>
{% endblock %}

后端代码:

def article_detail(request,username,article_id):
    article_obj = models.Article.objects.filter(pk=article_id).first()
    comment_list = models.Comment.objects.filter(article=article_obj)
    return render(request,'article_detail.html',locals())


import json
from django.db.models import F
from django.utils.safestring import mark_safe
def UpAndDown(request):
    if request.is_ajax():
        if request.method == 'POST':
            back_dic = {'code':1000,'msg':''}
            # 1 判断当前用户是否登录
            if request.user.is_authenticated():
                article_id = request.POST.get('article_id')
                is_up = request.POST.get('is_up')  # true false
                # print(is_up,type(is_up))
                is_up = json.loads(is_up)  # 将前端js数据格式的布尔值类型 转换成后端python格式的布尔值类型
                # print(is_up, type(is_up))
                # 2 判断当前文章是否是当前用户自己写的
                article_obj = models.Article.objects.filter(pk=article_id).first()
                if not article_obj.blog.userinfo == request.user:
                    # 3 校验当前用户是否已经点过了
                    is_click = models.UpAndDown.objects.filter(user=request.user,article=article_obj)
                    if not is_click:
                        # 4 操作数据库 更新记录
                        # 判断用户是点了赞 还是点了踩 从而决定到底给哪个普通字段加一
                        if is_up:
                            models.Article.objects.filter(pk=article_id).update(up_num = F('up_num') + 1)
                            back_dic['msg'] = '点赞成功'
                        else:
                            models.Article.objects.filter(pk=article_id).update(down_num=F('down_num') + 1)
                            back_dic['msg'] = '点踩成功'
                        # 真正的操作 点赞点踩表
                        models.UpAndDown.objects.create(user=request.user,article=article_obj,is_up=is_up)
                    else:
                        back_dic['code'] = 1001
                        back_dic['msg'] = '你已经点过了!'
                else:
                    back_dic['code'] = 1002
                    back_dic['msg'] = '你个臭不要脸的,不能给自己点'
            else:
                back_dic['code'] = 1003
                back_dic['msg'] = mark_safe('请先<a href="/login/">登录</a>')
            return JsonResponse(back_dic)


from django.db import transaction

def comment(request):
    if request.is_ajax():
        if request.method == 'POST':
            back_dic = {'code':1000,'msg':''}
            article_id = request.POST.get('article_id')
            content = request.POST.get('content')
            parent_id = request.POST.get('parent_id')
            with transaction.atomic():
                models.Article.objects.filter(pk=article_id).update(comment_num = F("comment_num") + 1)
                models.Comment.objects.create(user=request.user,article_id=article_id,content=content,parent_id=parent_id)
            back_dic['msg'] = '评论成功'
            return JsonResponse(back_dic)
posted @ 2019-11-12 21:40  chanyuli  阅读(253)  评论(1编辑  收藏  举报