Flask学习之八 关注、联系人和好友
英文博客地址:http://blog.miguelgrinberg.com/post/the-flask-mega-tutorial-part-viii-followers-contacts-and-friends
中文翻译地址:http://www.pythondoc.com/flask-mega-tutorial/followers.html
开源中国社区:http://www.oschina.net/translate/the-flask-mega-tutorial-part-viii-followers-contacts-and-friends
一、“关注”功能
1.某一个用户想要知道都有谁关注了TA
2.某一个用户想要知道TA关注了谁
3.用户点击任何用户的信息页上一个 “关注” 的链接就开始关注这个用户。点击 “取消关注” 链接将会停止关注这个用户。
4.对于一个给定的用户,我们能够容易地查询数据库获取用户的被关注者的所有 blog
二、数据库内表示关注者和被关注者
对此我们需要一种多对多的关系,因为一个用户可以关注多个其他的用户,同样一个用户可以被其他多个用户关注。
多对多关系的图:

followers 表示我们的关联表。外键都是来自于用户表中,因为我们是用户连接到用户。在这个表中的每一个记录都是表示关注的用户以及被关注的用户的连接。
三、数据模型
根据多对多关系图,首先开始添加 followers 表(文件 app/models.py):
followers = db.Table('followers',
    db.Column('follower_id', db.Integer, db.ForeignKey('user.id')),
    db.Column('followed_id', db.Integer, db.ForeignKey('user.id'))
)
这是对上面图表上的关系表的直接翻译。注意我们并没有像对 users 和 posts 一样把它声明为一个模式。因为这是一个辅助表,我们使用 flask-sqlalchemy 中的低级的 APIs 来创建,没有使用关联模式。
接着我们在 users 表中定义一个多对多的关系:
class User(db.Model):
id = db.Column(db.Integer, primary_key=True)
nickname = db.Column(db.String(64), index=True, unique=True)
email = db.Column(db.String(120), index=True, unique=True)
posts = db.relationship('Post', backref='author', lazy='dynamic')
about_me = db.Column(db.String(140))
last_seen = db.Column(db.DateTime)
followed = db.relationship('User',
secondary=followers,
primaryjoin=(followers.c.follower_id == id),
secondaryjoin=(followers.c.followed_id == id),
backref=db.backref('followers', lazy='dynamic'),
lazy='dynamic')
像我们在前面章节设置一对多关系一样,我们使用了 db.relationship 函数来定义关系。我们连接 User 实例到其它 User 实例,在这种关系下连接的一对用户,左边的用户关注着右边的用户。
因为我们定义左边的用户为 followed,当我们从左边用户查询这种关系的时候,我们将会得到被关注用户的列表。
db.relationship() 中的所有参数:
- ‘User’是这种关系类型的右侧实体(左侧实体是父类)。因为定义一个自我指向的关系,我们在两边使用同样的类。
 - secondary 指明了用于这种关系的辅助表。
 - primaryjoin 表明通过association表映射到左侧实体(粉丝)的条件。注意因为 followers 表不是一个模式,获得字段名的语法有些怪异。
 - secondaryjoin 表示辅助表中连接右边实体(被关注的用户)的条件。
 - backref 定义这种关系将如何从右边实体进行访问。当我们做出一个名为 followed 的查询的时候,将会返回所有跟左边实体联系的右边的用户。当我们做出一个名为 followers 的查询的时候,将会返回一个所有跟右边联系的左边的用户。lazy 指明了查询的模式。dynamic 模式表示直到有特定的请求才会运行查询,这是对性能有很好的考虑。
 - lazy 是与 backref 中的同样名称的参数作用是类似的,但是这个是应用于常规查询。
 
由于我们升级了数据库,所以现在我们需要产生一个新的迁移:
./db_migrate.py
备注:需要把 followers 放到 User 的前面(反正我增加到最后是不行的),否则会报错(name 'followers' is not defined):
aaarticlea/png;base64,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" alt="" />
成功后是:
aaarticlea/png;base64,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" alt="" />
四、添加和移除 ‘关注者’
为了增强可重用性,我们将在User模型里实现follow和unfollow方法而不是在view里直接实现它。
这种方法我们能在真实的应用中使用(通过view方法调用它)而且对我们的单元测试有好处。
原则上,从视图函数中移除应用程序的逻辑到数据模型中是一种好的方式。你们必须要保证视图函数尽可能简单,因为它能难被自动化测试。
下面是添加了添加和移除 ‘关注者’ 功能的 User 模型(文件 app/models.py):
class User(db.Model):
#...
def follow(self, user):
if not self.is_following(user):
self.followed.append(user)
return self def unfollow(self, user):
if self.is_following(user):
self.followed.remove(user)
return self def is_following(self, user):
return self.followed.filter(followers.c.followed_id == user.id).count() > 0
上面这些方法是很简单了,多亏了 sqlalchemy 在底层做了很多的工作。我们只是从 followed 关系中添加或者移除了表项,sqlalchemy 为我们管理辅助表。
follow和unfollow方法要在执行成功时返回一个user对象,失败的时候返回None,user对象会被添加到数据库会话,并提交。
is_following方法只有一行代码却做了很多事情。我们递交获取followed关系的请求,它返回所有以我们的user为follower的(follower, followed)元组, 以followed user为条件进行过滤。上述方法是可行的,因为followed关系有一个懒惰模式的动态属性,我们得到的是请求执行之前请求对象而不是请求的结果。
过滤操作返回的是更改后、依然没有被执行的请求。当我们在这条请求上调用count()方法时,请求才会被执行并返回查询到的记录数目。若返回的记录数目是1,这俩用户之间已经存在联系;相反,则没有联系。
五、测试
让我们编写单元测试框架来检验目前我们已经写好的代码(文件 tests.py):
class TestCase(unittest.TestCase):
#...
def test_follow(self):
u1 = User(nickname='john', email='john@example.com')
u2 = User(nickname='susan', email='susan@example.com')
db.session.add(u1)
db.session.add(u2)
db.session.commit()
assert u1.unfollow(u2) is None
u = u1.follow(u2)
db.session.add(u)
db.session.commit()
assert u1.follow(u2) is None
assert u1.is_following(u2)
assert u1.followed.count() == 1
assert u1.followed.first().nickname == 'susan'
assert u2.followers.count() == 1
assert u2.followers.first().nickname == 'john'
u = u1.unfollow(u2)
assert u is not None
db.session.add(u)
db.session.commit()
assert not u1.is_following(u2)
assert u1.followed.count() == 0
assert u2.followers.count() == 0
执行测试:
./tests.py
aaarticlea/png;base64,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" alt="" />
六、数据库查询
我们目前的数据库模型支持在开始罗列的大多数需求,缺少的部分也是最难的部分。索引页需要显示被当前登录用户follow的人所发布的所有帖子,因此我们需要这样一个请求能返回这些帖子。
数据库有索引,因此允许以一种高效地方式去查询以及排序。
所以我们真正想要的是要拿出一个单一的数据库查询,表示我们想要得到什么样的信息,然后我们让数据库弄清楚什么是最有效的方式来为我们获取数据。
下面这种查询可以实现上述的要求,这个单行的代码又被我们添加到 User 模型(文件 app/models.py):
class User(db.Model):
#...
def followed_posts(self):
return Post.query.join(followers, (followers.c.followed_id == Post.user_id)).filter(followers.c.follower_id == self.id).order_by(Post.timestamp.desc())
上面这个查询分为三部分:
1. join。
Post.query.join(followers,
(followers.c.followed_id == Post.user_id))
学过数据库的都能理解,join操作实现的是创建一个临时表,数据根据指定条件从Post和followers表合并得到。在这个例子中,我们使用followers的follower_id字段和Post的user_id字段做匹配。
2.过滤。
filter(followers.c.follower_id == self.id)
就是按要求返数据。连接操作给我们被某人关注的用户的 blog 的列表,但是没有指出谁是关注者。我们仅仅对这个列表的子集感兴趣,我们只需要被某一特定用户关注的用户的 blog 列表。
3.排序。
order_by(Post.timestamp.desc())
在这里,我们要说的结果应该按照 timestamp 字段按降序排列,这样的第一个结果将是最近的 blog。
这里还有一个小问题。当用户阅读他们关注者的 blog 的时候,他们可能也想看到自己的 blog。因此最好把用户自己的 blog 也包含进查询结果中。
其实这不需要做任何改变。我们只需要把自己添加为自己的关注者。
七、测试查询
为我们查询写些单元测试(文件 tests.py):
#...
from datetime import datetime, timedelta
from app.models import User, Post
#...
class TestCase(unittest.TestCase):
#...
def test_follow_posts(self):
# make four users
u1 = User(nickname='john', email='john@example.com')
u2 = User(nickname='susan', email='susan@example.com')
u3 = User(nickname='mary', email='mary@example.com')
u4 = User(nickname='david', email='david@example.com')
db.session.add(u1)
db.session.add(u2)
db.session.add(u3)
db.session.add(u4)
# make four posts
utcnow = datetime.utcnow()
p1 = Post(body="post from john", author=u1, timestamp=utcnow + timedelta(seconds=1))
p2 = Post(body="post from susan", author=u2, timestamp=utcnow + timedelta(seconds=2))
p3 = Post(body="post from mary", author=u3, timestamp=utcnow + timedelta(seconds=3))
p4 = Post(body="post from david", author=u4, timestamp=utcnow + timedelta(seconds=4))
db.session.add(p1)
db.session.add(p2)
db.session.add(p3)
db.session.add(p4)
db.session.commit()
# setup the followers
u1.follow(u1) # john follows himself
u1.follow(u2) # john follows susan
u1.follow(u4) # john follows david
u2.follow(u2) # susan follows herself
u2.follow(u3) # susan follows mary
u3.follow(u3) # mary follows herself
u3.follow(u4) # mary follows david
u4.follow(u4) # david follows himself
db.session.add(u1)
db.session.add(u2)
db.session.add(u3)
db.session.add(u4)
db.session.commit()
# check the followed posts of each user
f1 = u1.followed_posts().all()
f2 = u2.followed_posts().all()
f3 = u3.followed_posts().all()
f4 = u4.followed_posts().all()
assert len(f1) == 3
assert len(f2) == 2
assert len(f3) == 2
assert len(f4) == 1
assert f1 == [p4, p2, p1]
assert f2 == [p3, p2]
assert f3 == [p4, p3]
assert f4 == [p4]
这个测试有一大部分是配置代码,实际上测试非常短小。我们先检查下每个用户关注帖子的返回数量和预期的是否一致,接着检查下返回的帖子是否正确,帖子的顺序是否和预期一样(注意我们按照时间顺序排列帖子,保证我们总是使用相同的排序方式)。
注意followed_posts()方法的用法,这个方法返回一个查询对象,而不是结果集,这就如同lazy=''dynamic'的关系。通常来说返回一个查询对象而不是结果集是一个很好的点子,因为这给调用者在执行查询前提供了添加更多查询条件的机会。
在查询对象中有几个方法触发查询的执行。我们看到的count()运行查询时返回的是一个结果集的数量(不关注实际结果的内容);我们也经常使用first()来返回结果集的第一条记录,在这个测试中我们使用了all()方法来获取所有结果集的一个数组。
aaarticlea/png;base64,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" alt="" />
八、在应用程序中应用
上面那些配置好了,但还没有应用到我们的应用程序中。下面继续。
1.做自己的关注者
在 after_login 中处理 OpenID 的时候就设置自己成为自己的关注者(文件 app/views.py):
@oid.after_login
def after_login(resp):
if resp.email is None or resp.email == "":
flash('Invalid login. Please try again.')
return redirect(url_for('login'))
user = User.query.filter_by(email=resp.email).first()
if user is None:
nickname = resp.nickname
if nickname is None or nickname == "":
nickname = resp.email.split('@')[0]
nickname = User.make_unique_nickname(nickname)
user = User(nickname=nickname, email=resp.email)
db.session.add(user)
db.session.commit()
# make the user follow him/herself
db.session.add(user.follow(user))
db.session.commit()
remember_me = False
if 'remember_me' in session:
remember_me = session['remember_me']
session.pop('remember_me', None)
login_user(user, remember=remember_me)
return redirect(request.args.get('next') or url_for('index'))
2.关注以及取消关注的链接
定义关注以及取消关注用户的视图函数(文件 app/views.py):
@app.route('/follow/<nickname>')
@login_required
def follow(nickname):
    user = User.query.filter_by(nickname=nickname).first()
    if user is None:
        flash('User %s not found.' % nickname)
        return redirect(url_for('index'))
    if user == g.user:
        flash('You can\'t follow yourself!')
        return redirect(url_for('user', nickname=nickname))
    u = g.user.follow(user)
    if u is None:
        flash('Cannot follow ' + nickname + '.')
        return redirect(url_for('user', nickname=nickname))
    db.session.add(u)
    db.session.commit()
    flash('You are now following ' + nickname + '!')
    return redirect(url_for('user', nickname=nickname))
@app.route('/unfollow/<nickname>')
@login_required
def unfollow(nickname):
    user = User.query.filter_by(nickname=nickname).first()
    if user is None:
        flash('User %s not found.' % nickname)
        return redirect(url_for('index'))
    if user == g.user:
        flash('You can\'t unfollow yourself!')
        return redirect(url_for('user', nickname=nickname))
    u = g.user.unfollow(user)
    if u is None:
        flash('Cannot unfollow ' + nickname + '.')
        return redirect(url_for('user', nickname=nickname))
    db.session.add(u)
    db.session.commit()
    flash('You have stopped following ' + nickname + '.')
    return redirect(url_for('user', nickname=nickname))
注意的是检查周围的错误,为了防止期望之外的错误,试着给用户提供信息并且重定向到合适的位置当错误发生的时候。
最后需要修改下模版(文件 app/templates/user.html):
<!-- extend base layout -->
{% extends "base.html" %} {% block content %}
<table>
<tr valign="top">
<td><img src="{{ user.avatar(128) }}"></td>
<td>
<h1>User: {{ user.nickname }}</h1>
{% if user.about_me %}<p>{{ user.about_me }}</p>{% endif %}
{% if user.last_seen %}<p><i>Last seen on: {{ user.last_seen }}</i></p>{% endif %}
<p>{{ user.followers.count() }} followers |
{% if user.id == g.user.id %}
<a href="{{ url_for('edit') }}">Edit your profile</a>
{% elif not g.user.is_following(user) %}
<a href="{{ url_for('follow', nickname=user.nickname) }}">Follow</a>
{% else %}
<a href="{{ url_for('unfollow', nickname=user.nickname) }}">Unfollow</a>
{% endif %}
</p>
</td>
</tr>
</table>
<hr>
{% for post in posts %}
{% include 'post.html' %}
{% endfor %}
{% endblock %}
Flask学习之八 关注、联系人和好友的更多相关文章
- Flask 学习 十一 关注者
		
数据库关系 1.1多对多关系 添加第三张表(关联表),多对多关系可以分解成原表和关联表之间的两个一对多的关系 多对多仍然使用db.relationship()方法定义,但是secondary参数必须设 ...
 - jackson学习之八:常用方法注解
		
欢迎访问我的GitHub https://github.com/zq2599/blog_demos 内容:所有原创文章分类汇总及配套源码,涉及Java.Docker.Kubernetes.DevOPS ...
 - [ZHUAN]Flask学习记录之Flask-SQLAlchemy
		
From: http://www.cnblogs.com/agmcs/p/4445583.html 各种查询方式:http://www.360doc.com/content/12/0608/11/93 ...
 - Flask 学习目录
		
Flask 学习目录 Flask 的学习过程是一个了解如何从单个模块搭建一个 Web 框架的过程. Python.Flask 的安装和设置 简单的 Hello World 程序 使用 Jinjia2 ...
 - Python Flask学习笔记之模板
		
Python Flask学习笔记之模板 Jinja2模板引擎 默认情况下,Flask在程序文件夹中的templates子文件夹中寻找模板.Flask提供的render_template函数把Jinja ...
 - Python Flask学习笔记之Hello World
		
Python Flask学习笔记之Hello World 安装virtualenv,配置Flask开发环境 virtualenv 虚拟环境是Python解释器的一个私有副本,在这个环境中可以安装私有包 ...
 - 【Spark-core学习之八】 SparkShuffle & Spark内存管理
		
[Spark-core学习之八] SparkShuffle & Spark内存管理环境 虚拟机:VMware 10 Linux版本:CentOS-6.5-x86_64 客户端:Xshell4 ...
 - Flask学习-Wsgiref库
		
一.前言 前面在Flask学习-Flask基础之WSGI中提到了WerkZeug,我们知道,WerkZeug是一个支持WSGI协议的Server,其实还有很多其他支持WSGI协议的Server.htt ...
 - Flask 学习篇二:学习Flask过程中的记录
		
Flask学习笔记: GitHub上面的Flask实践项目 https://github.com/SilentCC/FlaskWeb 1.Application and Request Context ...
 
随机推荐
- swiper 报错 ‘ Can't find variable: Dom7’
			
一般报这个错是因为浏览器兼容问题,例如低版本的IE 现在通过npm install swiper 安装的版本都是4.x的 我的解决方法就是安装低版本的swiper, npm install swipe ...
 - poj 3468 A Simple Problem with Integers (线段树区间更新求和lazy思想)
			
A Simple Problem with Integers Time Limit: 5000MS Memory Limit: 131072K Total Submissions: 75541 ...
 - char类型和int类型之间的转换
			
在视屏课程第二章里,我们已经学习了一些常用的数据类型转换.然而,有一些时候我们会经常会遇到将char类型转换成int类型,或者需要将int类型转换为char类型的情况. 这里,我们来探讨一下这种不常用 ...
 - 解决Cesium1.50对gltf2.0/3dtiles数据读取的问题
			
问题说明 Cesium 1.50(2018/10/01)版本打开3dtiles可能会出现加载不上导致渲染停止的错误. 错误说明为:RuntimeError: Unsupported glTF Exte ...
 - 解决驱动版本不对应导致的UnsupportedClassVersionError: com/mysql/jdbc/Driver : Unsupported major.minor version 52.0
			
org.springframework.web.util.NestedServletException: Handler processing failed; nested exception is ...
 - python基础--迭代器、生成器、内置函数、面向对象编程
			
迭代器:迭代器对象从集合的第一个元素开始访问,直到所有的元素都被访问完结束.迭代器只能往前不会后退 迭代:更新换代(重复)的过程,每次的迭代都必须基于上一次的结果 迭代器:迭代取值的工具 使用迭代器的 ...
 - 2019.7.29 NOIP模拟测试10 反思总结【T2补全】
			
这次意外考得不错…但是并没有太多厉害的地方,因为我只是打满了暴力[还没去推T3] 第一题折腾了一个小时,看了看时间先去写第二题了.第二题尝试了半天还是只写了三十分的暴力,然后看到第三题是期望,本能排斥 ...
 - top进程命令
			
top命令用来显示系统当前的进程状况. 格式:top [选项] 主要选项如下. d:指定更新的间隔,以秒计算. q:没有任何延迟的更新.如果使用者有超级用户,则top命令将会以最高的优先序执行. c: ...
 - js计算精度问题(浮点数误差,大数计算出错)
			
https://github.com/camsong/blog/issues/9 0.1+0.2 //0.30000000000000004 1-0.9 //0.09999999999999998 9 ...
 - DirectX11笔记(六)--Direct3D渲染2--VERTEX BUFFER
			
原文:DirectX11笔记(六)--Direct3D渲染2--VERTEX BUFFER 版权声明:本文为博主原创文章,未经博主允许不得转载. https://blog.csdn.net/u0103 ...