有了用户以后,那最常用的一个功能就是,用户互相关注了.
在网上搜索了一下,有用ManytoMany建立关系的,也有建一个中间表的,我选择了后者,用一个中间表来代表关注和被关注的关系.
我在users这个app下面的models里面,建立了Relationship这个模型
两个字段,都是外键,都是对应用户。
每个Relationship的实例,都包含了作为粉丝的用户的id,以及被关注者的id
class Relationship(models.Model):
following = models.ForeignKey(User,related_name='following_users',on_delete=models.CASCADE)
follower = models.ForeignKey(User,related_name='follower_users',on_delete=models.CASCADE)
模型建立完以后,不用单独设置url了,因为我们只需要在Relationship类里面进行操作就ok了。所以我们来看下views视图函数.
在进入用户页面之后,会定义2个用户信息:
一个是user_name,这个是根据URL内的信息定义的用户
另一个是self_user,这个是当前登录的用户
进入页面后,首先判断,当前用户和页面信息内的客户是否已经存在关注关系。
follower就是粉丝,也就是登录用户自己,following是当前页面信息的用户
如果不存在的话,我们就让关注功能这个按钮上的文字show_button显示为“关注”
如果已经存在的话,就让按钮显示为“取消关注”
在取消关注的功能中,用到了
relationship = Relationship.objects.get(Q(follower=self_user) & Q(following=to_follow_user))
这样的查询是Django的Queryset内的Q查询.
无论是关注或者是取消关注,数据保存过以后,都会重定向到之前进行关注/取消的用户页面
def user_profile(request,user_name):
user_name = user_name
user_info = User.objects.get(username=user_name) # URL中指向的是哪个用户的profile页面
self_user = request.user # 登录用户自己的用户信息,用于Follow
to_follow_user = User.objects.get(username=user_name) # 通过URL获取的对象信息,用于Follow
if not Relationship.objects.filter(follower=request.user, following=to_follow_user).exists(): #如果登录用户和对象用户没有关注
show_button = "关注"
if request.method == "POST":
relationship = Relationship()
relationship.following = User.objects.get(username=to_follow_user) # 要去关注谁
relationship.follower = User.objects.get(username=self_user) # 由谁来关注
relationship.save()
return redirect('users:user_profile', user_name)
else:
return render(request,'user_profile.html',locals())
else:
show_button="取消关注"
if request.method == "POST":
relationship = Relationship.objects.get(Q(follower=self_user) & Q(following=to_follow_user)) # 通过关注者和被关注的信息,查出这个关系实例
relationship.delete()
return redirect('users:user_profile', user_name)
else:
return render(request,'user_profile.html',locals())
最后,进入前端页面的渲染
额外需要注意的是,我在前端进行了一个判断,如果用户访问的页面是自己的用户页面,那就不会显示这个按钮,也就是用户无法关注自己.
{% extends 'base_page.html' %}
{% block title %}用户页面{% endblock %}
{% load staticfiles %}
{% block content %}
<p>Username: {{user_info}}</p>
<p>Email: {{ user_info.email }}</p>
{% if user != user_info %}
<form method="post" action="{% url 'users:user_profile' user_info.username %}">
{% csrf_token %}
<input type="submit" value="{{ show_button }}" >
</form>
{% endif %}
{% endblock %}
这样就实现了关注和取消关注的功能
关注 取消关注
网友评论