六、文章详情、点赞、评论

文章详情页面:

def article_detail(request, username, article_id):
# user_obj = models.UserInfo.objects.filter(username=username)
article_obj = models.Article.objects.filter(pk=article_id).first()
blog = models.Blog.objects.filter(userinfo__username=username).first()
comment_list = models.Comment.objects.filter(article_id=article_id)
return render(request, 'article_detail.html', locals())

views.py 文章详情页

{% extends 'base.html' %}

{% block css %}
<style>
#div_digg {
float: right;
margin-bottom: 10px;
margin-right: 30px;
font-size: 12px;
width: 125px;
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;
} #div_digg .diggnum {
line-height: 1.5em !important;
} .diggnum {
font-size: 14px;
color: #075db3;
font-family: Verdana;
} .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: gray;
}
</style>
{% endblock %}
{% block content %}
{# <h3>{{ article_obj.title }}</h3>#}
{{ article_obj.content|safe }}
<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>
<div class="diggword" id="digg_tips" style="color: red;"></div>
</div>
</div>
<hr>
{# --------------------评论内容部分 开始 ------------------- #}
<p>评论列表:</p>
<div class="form-group list-group">
{% for comment in comment_list %} <div class="form-group"><span style="color: cornflowerblue">#{{ forloop.counter }}楼&nbsp;</span>
{{ comment.create_time|date:'Y-m-d' }}&nbsp;
<a href="/{{ comment.user.username }}/">{{ comment.user.username }}</a>
<span class="pull-right reply" comment_id="{{ comment.pk }}" username={{ comment.user.username }}><a>回复</a></span>
<div>
{% if comment.parent %}
<p>@&nbsp;{{ comment.parent.user.username }}</p>
{% endif %}
<p style="color: darkgray">&nbsp;&nbsp;{{ comment.content }}</p>
<hr>
</div>
</div>
{% endfor %} </div>
{# --------------------评论内容部分 结束 ------------------- #}
{% if request.user.is_authenticated %}
{# -----------------------------评论部分 开始 ---------------------- #}
<div>
<p><span class="glyphicon glyphicon-comment"></span>发表评论</p>
<p>
<span>昵称:<span class="glyphicon glyphicon-user"></span></span>
<input type="text" value="{{ request.user.username }}" disabled>
</p>
<p>评论内容:</p>
<textarea name="" cols="80" rows="10" id="id_comment"></textarea>
<p>
<button class="btn btn-primary" id="id_submit">提交评论</button>
</p>
<br><br><br>
</div>
{# ------------------------------评论部分 结束 ---------------------- #}
{% endif %}
{% endblock %} {% block js %}
<script>
console.log("this is script!");
// 点赞点踩
$('.action').click(function () {
{#alert($(this).hasClass('diggit')) 利用类操作判断是否有某一个类属性从而区分是点赞还是点踩#}
let isUp = $(this).hasClass('diggit');
let $info = $('#digg_tips');
let $span = $(this).children();
$.ajax({
url: "/up_or_down/",
type: 'post',
data: {
'article_id':{{ article_obj.pk }},
'is_up': isUp,
'csrfmiddlewaretoken': '{{ csrf_token }}'
},
success: function (data) {
if (data.code == 200) {
$info.html(data.msg);
// 将span标签内部的文本数字加1
$span.text(Number($span.text()) + 1)
} else {
$info.html(data.msg)
}
}
})
}); let parentId = '';
// 提交评论
$('#id_submit').click(function () {
console.log("this is 提交数据!");
let sub_content = $('#id_comment').val();
if (sub_content == ''){
alert("评论不能为空!")
}else{
console.log('this is sub_content:', sub_content);
if (parentId){
let indexVal = sub_content.indexOf('\n') +1;
sub_content = sub_content.slice(indexVal);
console.log(sub_content)
}
// 分析: 将评论提交到后端,需要传 文章id、评论内容,评论人的id
$.ajax({
url: '/comment/',
type: 'post',
data: {
'article_id': '{{ article_id }}',
'content': sub_content,
'csrfmiddlewaretoken': '{{ csrf_token }}',
'parentId': parentId, },
success: function (data) {
if (data.code == 100) {
let userName = '{{ request.user.username }}';
let content = sub_content;
let tempStr = `
<div>
<p class="form-group"><span style="color: cornflowerblue">
<a href="/${userName}/">${userName}</a>
</p>
<p style="color: darkgray">&nbsp;&nbsp;${content}</p>
<hr>
</div>
`;
$(".list-group").append(tempStr);
// 将textarea框中的内容清空
$('#id_comment').val('');
// 将全局的parentId清空
parentId = ''
}
}
}) }
}); // 回复按钮逻辑代码
$('.reply').click(function () {
// 1.把你想评论的那条评论所属者的名字添加到textarea中(@+用户名) 如何获取评论人名
let pUserName = $(this).attr('username');
let pCommentId = $(this).attr('comment_id');
// 2.自动换行
$('#id_comment').val('@'+pUserName+'\n');
// 3.textarea自动聚焦
$('#id_comment').focus();
// 4.将全局的parentId赋值
parentId = pCommentId;
});
</script>
{% endblock %}

article_detail.html

def up_or_down(request):
back_dic = {'code': 100, 'msg': ''}
if request.is_ajax():
is_up = request.POST.get('is_up')
is_up = json.loads(is_up) # 利用json模块反序列称后端python布尔值类型
article_id = request.POST.get('article_id') # 1.判断用户是否登录
if request.user.is_authenticated():
# 2.判断文章是否是当前用户写的
article_obj = models.Article.objects.filter(pk=article_id).first()
if not article_obj.blog.userinfo.pk == request.user.id:
# 3.判断当前用户是否对该文章点赞或点踩了
res = models.UpAndDown.objects.filter(user=request.user, article=article_obj)
if not res:
# 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'] = '点踩成功'
# 最后修改UpAndDown表数据
models.UpAndDown.objects.create(user=request.user, article=article_obj, is_up=is_up)
back_dic['code'] = 200
else:
back_dic['code'] = 201
back_dic['msg'] = '你已经点过了'
else:
back_dic['code'] = 202
back_dic['msg'] = '你个臭不要脸的不能点自己的'
else:
back_dic['code'] = 203
back_dic['msg'] = mark_safe('请先<a href="/login/">登录</a>')
return JsonResponse(back_dic)

views.py 点赞点踩

def comment(request):
back_dic = {'code': 100, 'msg': ''}
if request.is_ajax():
# 获取前端发过来的数据
# print("this is comment!")
article_id = request.POST.get('article_id')
# print(article_id)
content = request.POST.get('content')
# print(content)
parent_id = request.POST.get('parentId')
# print(parent_id)
if request.user.is_authenticated():
# print("已经登录,正要去写评论入库")
with transaction.atomic():
# 在文章表中普通的评论字段加1
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'] = '评论成功!'
else:
back_dic['code'] = 101
back_dic['msg'] = '请想登录!'
return JsonResponse(back_dic)

views.py 评论

BBS论坛 文章详情、点赞、评论的更多相关文章

  1. BBS之文章详情页搭建

    博客评论相关 博客文章详情页搭建 {% extends 'base.html' %} {% block css %} <style> #div_digg { float: right; m ...

  2. Django:文章详情页面评论功能需要登录后才能使用,登录后自动返回到文章详情页

    背景: 文章详情页正在查看文章,想评论一下写的不错,但是需要先登录才能.页面长这个样子: 方案: 1.点击登录链接时,将该页面的URL传递到登录视图中 request.path获取的是当前页面的相对路 ...

  3. $Django 站点:样式--文章--分类文章--文章详情--文章评论点赞--文章评论点赞统计(数据库优化)

    <h3>个人站点下的</h3> 知识点 url (r'(?P<username>\w+)/p/(?P<id>\d+)', xiangxi,name='x ...

  4. BBS项目分布搭建三(个人站点时间归档补充,实现侧边栏跳转、无线级分类、实现文章详情页展示功能)

    BBS项目分布搭建三(个人站点时间归档补充,) 1. 个人站点时间归档 """ settings.py设置最好更改以下: LANGUAGE_CODE = 'zh-hans ...

  5. Python之路【第十八篇】Django小项目简单BBS论坛部分内容知识点

    开发一个简单的BBS论坛 项目需求: 整体参考“抽屉新热榜” + “虎嗅网” 实现不同论坛版块 帖子列表展示 帖子评论数.点赞数展示 在线用户展示 允许登录用户发贴.评论.点赞 允许上传文件 帖子可被 ...

  6. python 学习笔记二十 django项目bbs论坛

    项目:开发一个简单的BBS论坛 需求: 整体参考“抽屉新热榜” + “虎嗅网” 实现不同论坛版块 帖子列表展示 帖子评论数.点赞数展示 在线用户展示 允许登录用户发贴.评论.点赞 允许上传文件 帖子可 ...

  7. python第一百三十天 ---简单的BBS论坛

    简单的BBS论坛 实现功能 git仓库地址:https://github.com/uge3/BBS 1.整体参考“抽屉新热榜” + “博客园” 2.实现不同论坛版块 3.帖子列表展示 4.个人博客主页 ...

  8. Django小项目简单BBS论坛

    开发一个简单的BBS论坛 项目需求: 1 整体参考"抽屉新热榜" + "虎嗅网" 2 实现不同论坛版块 3 帖子列表展示 4 帖子评论数.点赞数展示 5 在线用 ...

  9. Python开发一个简单的BBS论坛

    项目:开发一个简单的BBS论坛 需求: 整体参考“抽屉新热榜” + “虎嗅网” 实现不同论坛版块 帖子列表展示 帖子评论数.点赞数展示 在线用户展示 允许登录用户发贴.评论.点赞 允许上传文件 帖子可 ...

随机推荐

  1. Zabbix Server 和 Zabbix Agentd 开机自动运行

    Zabbix Server 和 Zabbix Agentd 开机自动运行 请问:怎样 Zabbix Server 和 Zabbix Agentd 开机自动运行? 注:如果你的命令行写进了 /etc/r ...

  2. flask中配置并使用mongodb

    在你安装并运行了mongodb的情况下: 随便在一个文件中写入以下代码: import pymongo client = pymongo.MongoClient(host="localhos ...

  3. [轉]Reverse a singly linked list

    Reverse a singly linked list  http://angelonotes.blogspot.tw/2011/08/reverse-singly-linked-list.html ...

  4. Process Array

    http://xiaorui.cc/2016/05/10/%E6%BA%90%E7%A0%81%E5%88%86%E6%9E%90multiprocessing%E7%9A%84value-array ...

  5. 实现一个EventEmitter类,这个类包含以下方法: on/ once/fire/off

    实现一个EventEmitter类,这个类包含以下方法: on(监听事件,该事件可以被触发多次)- once(也是监听事件,但只能被触发一次)- fire(触发指定的事件)- off(移除指定事件的某 ...

  6. CentOs如何找回root密码

    当CentOs的root密码忘了的时候,可以进入单用户模式,更改一下root密码就可以了. 具体操作如下 1.重启Linux后,在此界面,3秒内按下回车键 2.出现此界面 3.按e键,进入下图,然后把 ...

  7. JSON对象排序并生成URL参数

    1、for in function jsontourl(param) { let params = {}, data=[]; let arr = Object.keys(param).sort(); ...

  8. webpack配置(使用react,es6的项目)

    const path = require('path');const webpack = require('webpack');const HtmlWebpackPlugin = require('h ...

  9. Python文件路径操作

    print(os.environ.get('HOME')) # 打印`HOME`这个环境变量 /Users/<> file_path = os.environ.get('HOME') + ...

  10. CodeFirst命令

    CodeFirst get-help entityFramework          NuGet命令 Add-Migration                     Adds a new mig ...