获取评论数和细节处理
1、如何获取评论数
方法:filter筛选再用count方法计数
问题:页面和代码更加复杂了(博客列表页面的评论计数需要每篇博客都算一次也可以,也可以设计一个方法让博客类继承)
2、自定义模版标签
标签不用在views中做处理,在模版页面可以直接去使用
降低耦合度,代码更加独立和使用更加简单
在app内创建templatetags包(我们这个自定义模版标签,有一套后台处理的运算代码,代码与当前app关联性很大,我们此时是需要获取评论相关的东西)
创建py文件(比如comment_tags.py,接着我们在里边写一些方法,这些方法可以在模版页面当做标签来使用)
load标签加载该文件
comment_tags.py
from django import template from django.contrib.contenttypes.models import ContentType from ..models import Comment #用于注册,我们一会做的那些方法变成一个模版标签,可以给这个磨板试用,所以导入的是模版这个库 register = template.Library() #写一个方法 #发这个方法注册一下 @register.simple_tag def get_comment_count(obj): content_type = ContentType.objects.get_for_model(obj) return Comment.objects.filter(content_type=content_type, object_id=obj.pk).count()
前端
{% load comment_tags %}
<li>评论({% get_comment_count blog %})</li>
comment_tags.py
@register.simple_tag def get_comment_form(obj): content_type = ContentType.objects.get_for_model(obj) form = CommentForm( initial={'content_type': content_type.model, 'object_id': obj.pk, 'reply_comment_id': 0}) return form @register.simple_tag def get_comment_list(obj): content_type = ContentType.objects.get_for_model(obj) comments = Comment.objects.filter(content_type=content_type, object_id=obj.pk, parent=None) return comments.order_by('-comment_time')
前端
<form id="comment_form" action="{% url 'update_comment' %}" method="POST" style="overflow: hidden"> <label>{{ user.username }},欢迎评论~</label> <div id="reply_content_container" style="display: none;"> <p>回复:</p> <div id="reply_content"> </div> </div> {% csrf_token %} {% get_comment_form blog as comment_form %} {% for field in comment_form %} {{ field }} {% endfor %} <span id="comment_error" class="text-danger pull-left"></span> <input type="submit" value="评论" class="btn btn-primary pull-right"> </form>
{% get_comment_list blog as comments %} {% for comment in comments %} <div id="root_{{ comment.pk }}" class="comment"> <span>{{ comment.user.username }}</span> <span>({{ comment.comment_time|date:"Y-m-d H:i:s" }}):</span> <div id="comment_{{ comment.pk }}"> {{ comment.text|safe }} </div> <a href="javascript:reply({{ comment.pk }});">回复</a> {% for reply in comment.root_comment.all %} <div class="reply"> <span>{{ reply.user.username }}</span> <span>({{ reply.comment_time|date:"Y-m-d H:i:s" }})</span> <span>回复</span> <span>{{ reply.reply_to.username }}:</span> <div id="comment_{{ reply.pk }}"> {{ reply.text|safe }} </div> <a href="javascript:reply({{ reply.pk }});">回复</a> </div> {% endfor %} </div> {% empty %} <span id="no_comment">暂无评论</span> {% endfor %}
这样可以吧博客views中关于评论的处理方法都放到评论的模版标签中,使页面更加清晰整洁。
3、细节处理
一、ajax返回的日期
data['comment_time'] = comment.comment_time.strftime('%Y-%m-%d %H:%M:%S')
返回的时间直接格式化了,会去掉时区的信息,我们又不能整个传到前端,那么我们这里需要利用一个东西,叫时间戳
它是一个方法,会返回一串数字,返回的时间——>时间戳timestamp
指距离格林威治时间1970年01月01日00时00分00秒的秒数,这里包含了时区的信息,传给前端模版页面,前端模版页面再再把这个时间戳还原或解析成我们需要的那个时间格式就可以了。
data['comment_time'] = comment.comment_time.timestamp()
前端页面需要定义一个方法来转换时间戳
function numFormat(num) { //00并上数字之后从后面截取2位 return ('00' + num).substr(-2); } function timeFormat(timestamp){ //首先把timestamp转换成Datezhe这个类型 var datetime = new Date(timestamp * 1000); //没有提供直接转换成我们需要的格式,那我们需要一个个获取我们需要的具体的数据 var year = datetime.getFullYear(); var month = numFormat(datetime.getMonth() + 1); var day = numFormat(datetime.getDate()); var hour = numFormat(datetime.getHours()); var minute = numFormat(datetime.getMinutes()); var second = numFormat(datetime.getSeconds()); //返回我们需要的那个格式 return year + '-' + month + '-' + day + ' ' + hour + ':' + minute + ':' + second; }
需要用的时候可以调用方法timeFormat(data['comment_time'])
二、CSS样式调整
在谷歌浏览器利用F12修改前端页面
div#reply_content_container{ border: 1px solid #d7d7d7; border-bottom: none; background-color: #f8f8f8; overflow: hidden; padding: 1em 1em 0.5em; } p#reply_title{ border-bottom: 1px dashed #ccc; padding-bottom: 0.5em; }
三、级联删除
DO_NOTHING——>CASCADE级联删除,保证数据完整性
DO_NOTHING不做任何处理,不保证数据完整性