flask Flask-Login 插件及继承 UserMixin 类login_user 源码分析session源码分析
Posted 胖虎是只mao
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了flask Flask-Login 插件及继承 UserMixin 类login_user 源码分析session源码分析相关的知识,希望对你有一定的参考价值。
一、继承 UserMixin 类
Flask 项目可以使用 Flask-Login 插件来实现登录功能,这是一个被广泛使用的优质第三方库。
登录功能设计用户表,我们要使用 Flask-Login 就需要让 User 映射类继承 UserMixin 类。修改 models.py 如下:
from flask_login import UserMixin
class User(Base, UserMixin):
...
继承 UserMixin 是干嘛呢?我们看下源码,这个类定义在 flask_login.mixins 模块中:
如上图所示的内容就是 UserMixin 的核心代码。使用 property
装饰器定义了几个属性:
property的作用主要是把方法的调用变成给属性直接赋值(s.set_score(9999)啊,直接写s.score = 9999)
is_active
这个属性通常用来判断用户是否处于活跃状态,当管理员要封号时,就把用户的这个属性设为 False ;is_authenticated
用来标识用户是否通过了验证。这个验证包括邮箱、手机短信验证码等,我们的项目没有涉及这些验证流程,所以注册之后就是算通过验证了;is_anonymous
用于识别用户是否是匿名用户,没有登录的状态下,就相当于匿名用户。
最后还有一个get_id
方法,此方法用于获取用户对应的信息在数据库中的 id 主键字段值的字符串,37 行的 text_type 方法就是把整数转换成字符串。
所以继承了 UserMixin 类后的 User 映射类就多了这几个属性和方法。
二、login_user 源码分析
在 flask_login.utils 模块中定义了 login_user 函数:
它提供了一些参数:
- user 就是 User 映射类的实例;
remember
是布尔值,当用户在表单中选中「记住我」时,remember 参数的值为 True ;duration
是有效时间,也就是绿码的有效时间,在我们的项目中,它就是 session 的有效时间,中文名字是「会话」;force
表示强制登录,当用户处于封禁状态时,user.is_active
属性值为 False (封号)。这种情况下 force 参数的值为 True 的话,会强行执行登录逻辑;fresh
字面意思就是「新鲜」,对于敏感操作,比如修改密码,就需要用户处于新鲜的登录状态。例如用户登录时验证了信息,session 使得用户处于登录状态,但不是新鲜的登录状态。如果用户想修改密码,就需要重新验证一次信息,这次验证会设置 session ,使得本次验证后的用户处于新鲜的登录状态。这样起到对敏感操作的保护作用。
下面看下函数内的代码:
如上图所示,第 166 行处理force
参数,判断是否强行登录。
第 169 行代码,current_app
就是应用对象,它的 login_manager
属性在前面的步骤中已经分析过,就是登录管理对象,LoginManager 类的实例。这个实例的 id_attribute
属性值是变量 ID_ATTRIBUTE
,这个变量来自配置文件 flask_login.config
模块:
如上图所示,此变量的值就是字符串 'get_id'
,回到第 169 行代码,内置方法 getattr
获取的就是登录管理对象的 get_id
方法,后面又加了一组括号,也就是调用这个方法。我们在前面的步骤中已经分析了 get_id
方法的返回值,它是 user 对象的 id 属性值的字符串,如果用户的 id 是 306 ,那么 get_id 方法的返回值就是 ‘306’ 。最后将这个字符串赋值给变量 user_id
。
紧接着,第 170 行将这个字符串又赋值给 session 的 _user_id
属性。
三、session源码分析
这里要提到 session 了。在课程的第一阶段最后一个实验「Flask 框架的栈与上下文对象」中,我们提到过 session 是一个请求上下文代理对象,它其实是 LocalProxy
类的实例。我们完全可以把它看作是请求上下文对象的 session 属性值,也就是定义在 flask.sessions 模块中的 SecureCookieSession
类的实例。
首先我们看下定义请求上下文对象的 session 属性的代码,它们在 flask.ctx
模块中 RequestContext 类的 push
方法中:
如上图所示,self 就是请求上下文对象,当某个浏览器第一次向服务器发送请求,初始化请求上下文时,self.session
通常是 None。进到第 389 行,self.app 是应用对象,其 session_interface 属性值就是定义在 flask.sessions 模块中的 SecureCookieSessionInterface
类的实例。390 行调用其 open_session
方法,参数是应用对象和请求对象:
如上图所示 340 行的 s 是一个令牌生成器,用于根据字典对象生成令牌和根据令牌获取对应的字典对象。
第 343 行的 request.cookies
属性是字典对象,app.session_cookie_name
是固定值 'session'
,所以 val 的值就是字典中 key 为 'session'
对应的 value ,也就是令牌。令牌也叫做加密签名,它是一个不定长的字符串。
以上是关于flask Flask-Login 插件及继承 UserMixin 类login_user 源码分析session源码分析的主要内容,如果未能解决你的问题,请参考以下文章
[Python][flask][flask-login]关于flask-login中各种API使用实例
Python flask 框架使用 flask-login 模块,来学习一下吧