Python的Flask框架中实现简洁的登录功能的教程.docx

上传人:b****6 文档编号:5861237 上传时间:2023-01-01 格式:DOCX 页数:5 大小:19.21KB
下载 相关 举报
Python的Flask框架中实现简洁的登录功能的教程.docx_第1页
第1页 / 共5页
Python的Flask框架中实现简洁的登录功能的教程.docx_第2页
第2页 / 共5页
Python的Flask框架中实现简洁的登录功能的教程.docx_第3页
第3页 / 共5页
Python的Flask框架中实现简洁的登录功能的教程.docx_第4页
第4页 / 共5页
Python的Flask框架中实现简洁的登录功能的教程.docx_第5页
第5页 / 共5页
亲,该文档总共5页,全部预览完了,如果喜欢就下载吧!
下载资源
资源描述

Python的Flask框架中实现简洁的登录功能的教程.docx

《Python的Flask框架中实现简洁的登录功能的教程.docx》由会员分享,可在线阅读,更多相关《Python的Flask框架中实现简洁的登录功能的教程.docx(5页珍藏版)》请在冰豆网上搜索。

Python的Flask框架中实现简洁的登录功能的教程.docx

Python的Flask框架中实现简洁的登录功能的教程

Python的Flask框架中实现简洁的登录功能的教程_

Python的Flask框架中实现简洁的登录功能的教程,登录是各个web框架中的基础功能,需要的伴侣可以参考下

回顾

在前面的系列章节中,我们创建了一个数据库并且学着用用户和邮件来填充,但是到现在我们还没能够植入到我们的程序中。

两章之前,我们已经看到怎么去创建网络表单并且留下了一个实现完全的登陆表单。

在这篇文章中,我们将基于我门所学的网络表单和数据库来构建并实现我们自己的用户登录系统。

教程的最终我们小程序会实现新用户注册,登陆和退出的功能。

为了能跟上这章节,你需要前一章节最终部分,我们留下的微博程序。

请确保你的程序已经正确安装和运行。

在前面的章节,我们开头配置我们将要用到的Flask扩展。

为了登录系统,我们将用法两个扩展,Flask-Login和Flask-OpenID.配置如下所示(fileapp__init__.py):

importos

fromflaskext.loginimportLoginManager

fromflaskext.openidimportOpenID

fromconfigimportbasedir

lm=LoginManager()

lm.setup_app(app)

oid=OpenID(app,os.path.join(basedir,'tmp'))

Flask-OpenID扩展为了可以存储临时文件,需要一个临时文件夹路径。

为此,我们供应了它的位置。

重访我们的用户模型

Flask-Login扩展需要在我们的User类里实现一些方法。

除了这些方法以外,类没有被要求实现其它方法。

下面是我们的User类(fileapp/models.py):

classUser(db.Model):

id=db.Column(db.Integer,primary_key=True)

nickname=db.Column(db.String(64),unique=True)

email=db.Column(db.String(120),unique=True)

role=db.Column(db.SmallInteger,default=ROLE_USER)

=db.relationship('Post',backref='author',lazy='dynamic')

defis_authenticated(self):

returnTrue

defis_active(self):

returnTrue

defis_anonymous(self):

returnFalse

defget_id(self):

returnunicode(self.id)

def__repr__(self):

return'User%r'%(self.name)

is_authenticated方法是一个误导性的名字的方法,通常这个方法应当返回True,除非对象代表一个由于某种缘由没有被认证的用户。

is_active方法应当为用户返回True除非用户不是激活的,例如,他们已经被禁了。

is_anonymous方法应当为那些不被获准登录的用户返回True。

最终,get_id方法为用户返回唯一的unicode标识符。

我们用数据库层生成唯一的id。

用户加载回调

现在我们通过用法Flask-Login和Flask-OpenID扩展来实现登录系统

首先,我们需要写一个方法从数据库加载到一个用户。

这个方法会被Flask-Login用法(fileapp/views.py):

@lm.user_loader

defload_user(id):

returnUser.query.get(int(id))

记住Flask-Login里的userid始终是unicode类型的,所以在我们把id传递给Flask-SQLAlchemy时,有必要把它转化成integer类型。

登录视图函数

接下来我们要更新登录视图函数(fileapp/views.py):

fromflaskimportrender_template,flash,redirect,session,url_for,request,g

fromflaskext.loginimportlogin_user,logout_user,current_user,login_required

fromappimportapp,db,lm,oid

fromformsimportLoginForm

frommodelsimportUser,ROLE_USER,ROLE_ADMIN

@app.route('/login',methods=['GET','POST'])

@oid.loginhandler

deflogin():

ifg.userisnotNoneandg.user.is_authenticated():

returnredirect(url_for('index'))

form=LoginForm()

ifform.validate_on_submit():

session['remember_me']=form.remember_me.data

returnoid.try_login(form.openid.data,ask_for=['nickname','email'])

returnrender_template('login.html',

title='SignIn',

form=form,

providers=app.config['OPENID_PROVIDERS'])

留意到我们导入了一些新的模块,其中有些后面会用到。

跟上个版本的改变很小。

我们给视图函数添加了一个新的装饰器:

oid.loginhandler。

它告诉Flask-OpenID这是我们的登录视图函数。

在方法体的开头,我们检测是是否用户是已经经过登录认证的,假如是就重定向到index页面。

这儿的思路是假如一个用户已经登录了,那么我们不会让它做二次登录。

全局变量g是Flask设置的,在一个request生命周期中,用来存储和共享数据的变量。

所以我猜你已经想到了,我们将把已经登录的用户放到g变量里。

我们在调用redirect()时用法的url_for()方法是Flask定义的从给定的view方法猎取url。

假如你想重定向到index页面,你h很可能用法redirect('/index'),但是我们有很好的理由让Flask为你构造url。

当我们从登录表单得到返回数据,接下来要运行的代码也是新写的。

这儿我们做两件事。

首先我们保存remember_me的布尔值到Flask的session中,别和Flask-SQLAlchemy的db.session混淆了。

我们已经知道在一个request的生命周期中用Flask的g对象来保存和共享数据。

沿着这条线路Flask的session供应了更多,更简单的服务。

一旦数据被保存到session中,它将在同一客户端发起的这次恳求和这次以后的恳求中永存而不会消亡。

数据将保持在session中直到被明确的移除。

为了做到这些,Flask为每个客户端建立各自的session。

下面的oid.try_login是通过Flask-OpenID来执行用户认证。

这个方法有两个参数,web表单供应的openid和OpenIDprovider供应的我们想要的list数据项。

由于我们定义了包含nickname和email的User类,所以我们要从找nickname和email这些项。

基于OpenID的认证是异步的。

假如认证胜利,Flask-OpenID将调用有由oid.after_login装饰器注册的方法。

假如认证失败那么用户会被重定向到login页面。

Flask-OpenID登录回调

这是我们实现的after_login方法(app/views.py)

@oid.after_login

defafter_login(resp):

ifresp.emailisNoneorresp.email=="":

flash('Invalidlogin.Pleasetryagain.')

redirect(url_for('login'))

user=User.query.filter_by(email=resp.email).first()

ifuserisNone:

nickname=resp.nickname

ifnicknameisNoneornickname=="":

nickname=resp.email.split(]

user=User(nickname=nickname,email=resp.email,role=ROLE_USER)

db.session.add(user)

mit()

remember_me=False

if'remember_me'insession:

remember_me=session['remember_me']

session.pop('remember_me',None)

login_user(user,remember=remember_me)

returnredirect(request.args.get('next')orurl_for('index'))

传给after_login方法的resp参数包含了OpenIDprovider返回的一些信息。

第一个if声明仅仅是为了验证。

我们要求一个有效的email,所以一个没有没供应的email我们是没法让他登录的。

接下来,我们将依据email查找数据库。

假如email没有被找到我们就认为这是一个新的用户,所以我们将在数据库中增加一个新用户,做法就像我们从之前章节学到的一样。

留意我们没有处理nickname,由于一些OpenIDprovider并没有包含这个信息。

做完这些我们将从Flasksession中猎取remember_me的值,假如它存在,那它是我们之前在loginview方法中保存到session中的boolean类型的值。

然后我们调用Flask-Login的login_user方法,来注册这个有效的登录。

最终,在最终一行我们重定向到下一个页面,或者假如在request恳求中没有供应下个页面时,我们将重定向到index页面。

跳转到下一页的这个概念很简洁。

比方说我们需要你登录才能导航到一个页面,但你现在并未登录。

在Flask-Login中你可以通过login_required装饰器来限定未登录用户。

假如一个用户想连接到一个限定的url,那么他将被自动的重定向到login页面。

Flask-Login将保存最初的url作为下一个页面,一旦登录完成我们便跳转到这个页面。

做这个工作Flask-Login需要知道用户当前在那个页面。

我们可以在app的初始化组件里配置它(app/__init__.py):

lm=LoginManager()

lm.setup_app(app)

lm.login_view='login'

全局变量g.user

假如你留意力很集中,那么你应当记得在loginview方法中我们通过检查g.user来推断一个用户是否登录了。

为了实现这个我们将用法Flask供应的before_request大事。

任何一个被before_request装饰器装饰的方法将会在每次request恳求被收到时提前与view方法执行。

所以在这儿来设置我们的g.user变量(app/views.py):

@app.before_request

defbefore_request():

g.user=current_user

这就是它要做的一切,current_user全局变量是被Flask-Login设定的,所以我们只需要把它拷贝到更简单被访问的g变量就OK了。

这样,全部的恳求都能访问这个登录的用户,甚至于内部的模板。

index视图

在之前的章节中我们用假代码遗留了我们的index视图,由于那个时候我们系统里并没有用户和博客文章。

现在我们有用户了,所以,让我们来完成它吧:

@app.route('/')

@app.route('/index')

@login_required

defindex():

user=g.user

=[

{

'author':

{'nickname':

'John'},

'body':

'BeautifuldayinPortland!

'

},

{

'author':

{'nickname':

'Susan'},

'body':

'TheAvengersmoviewassocool!

'

}

]

returnrender_template('index.html',

title='Home',

user=user,

=)

在这个方法中只有两处变动。

首先,我们增加了login_required装饰器。

这样表明白这个页面只有登录用户才能访问。

另一个改动是把g.user传给了模板,替换了之间的假对象。

现在可以运行我们的应用了。

当我们连接到你将会看到登陆页面。

记着假如你通过OpenID登录那么你必需用法你的供应者供应的OpenIDURL。

你可以下面URL中的任何一个OpenIDprovider来为你产生一个正确的URL。

作为登录进程的一部分,你将会被重定向到OpenID供应商的网站,你将在那儿认证和授权你共享给我们应用的一些信息(我们只需要email和nickname,放心,不会有任何密码或者其他个人信息被曝光)。

一旦登录完成你将作为已登录用户被带到index页面。

试试勾选remember_me复选框。

有了这个选项当你在扫瞄器关闭应用后重新打开时,你还是已登录状态。

注销登录

我们已经实现了登录,现在是时候来实现注销登录了。

注销登录的方法灰常简洁(fileapp/views.py):

@app.route('/logout')

deflogout():

logout_user()

returnredirect(url_for('index'))

但我们在模板中还没有注销登录的链接。

我们将在base.html中的顶部导航栏添加这个链接(fileapp/templates/base.html):

html

head

{%iftitle%}

title{{title}}-microblog/title

{%else%}

titlemicroblog/title

{%endif%}

/head

body

divMicroblog:

ahref="{{url_for('index')}}"Home/a

{%ifg.user.is_authenticated()%}

|ahref="{{url_for('logout')}}"Logout/a

{%endif%}

/div

hr

{%withmessages=get_flashed_messages()%}

{%ifmessages%}

ul

{%formessageinmessages%}

li{{message}}/li

{%endfor%}

/ul

{%endif%}

{%endwith%}

{%blockcontent%}{%endblock%}

/body

/html

这是多么多么简洁啊,我们只需要检查一下g.user中是否有一个有效的用户,假如有我们就添加注销链接。

在我们的模板中我们再一次用法了url_for方法。

更多信息请查看IT技术专栏

...

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 经管营销

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1