zoukankan      html  css  js  c++  java
  • Flask框架的学习与实战(三):登陆管理

    继续flask的学习之旅。今天介绍flask的登陆管理模块,还记得上一篇中的blog小项目么,登录是咱们自己写的验证代码,大概有以下几个步骤:

    1、在登录框中输入用户名和密码

    2、flask view函数获取用户密码,然后到数据库中查询该用户信息,进行匹配

    3、如果成功,就写入session中,重定向到首页

    4、如果对于特定视图,必须要登录才能访问,那么需要在每个视图函数验证session里是否存在该用户。

    今天继续改造blog项目,介绍的flask-login模块就是替我们来搞定这些业务相关度较少的公用功能,它可以帮助我们:

    • 在会话中存储当前活跃的用户 ID,让你能够自由地登入和登出。
    • 让你限制登入(或者登出)用户可以访问的视图。
    • 处理让人棘手的 “记住我” 功能。
    • 帮助你保护用户会话免遭 cookie 被盗的牵连。
    • 可以与以后可能使用的 Flask-Principal 或其它认证扩展集成。

    一、如何使用flask-login模块?

    1、安装flask-login

    E:workdirdct-server-5055187src>pip install flask-login

    2、使用flask-login

     2.1)  在/blog2/__init__.py添加:

     1 #引用包
     2 from flask.ext.login import LoginManager
     3 
     4 #登陆管理
     5 #声明login对象
     6 login_manager = LoginManager()
     7 #初始化绑定到应用
     8 login_manager.init_app(app)
     9 
    10 #声明默认视图函数为login,当我们进行@require_login时,如果没登陆会自动跳到该视图函数处理
    11 login_manager.login_view = "login"
    12 
    13 
    14 #当登陆成功后,该函数会自动从会话中存储的用户 ID 重新加载用户对象。它应该接受一个用户的 unicode ID 作为参数,并且返回相应的用户对象。
    15 @login_manager.user_loader
    16 def load_user(userid):
    17     return User.query.get(int(userid))

    2.2) 修改User模型(红色部分为新增代码)

    from flask.ext.login import UserMixin
    
    from blog2 import db
    
    class User(db.Model, UserMixin):
        __tablename__ = 'b_user'
        id = db.Column(db.Integer,primary_key=True)
        username = db.Column(db.String(10),unique=True)
        password = db.Column(db.String(16))
    
        def __init__(self,username,password):
            self.username  = username
            self.password = password
        def __repr__(self):
            return '<User %r>' % self.username

    该用户类必须实现以下几个方法:

    is_authenticated
    当用户通过验证时,也即提供有效证明时返回 True(只有通过验证的用户会满足 login_required 的条件。)
    is_active
    如果这是一个活动用户且通过验证,账户也已激活,未被停用,也不符合任何你 的应用拒绝一个账号的条件,返回 True 。不活动的账号可能不会登入(当然, 是在没被强制的情况下)。
    is_anonymous
    如果是一个匿名用户,返回 True 。(真实用户应返回 False 。)
    get_id()
    返回一个能唯一识别用户的,并能用于从 user_loader 回调中加载用户的 unicode 。注意着 必须 是一个 unicode —— 如果 ID 原本是 一个 int 或其它类型,你需要把它转换为 unicode

    要简便地实现用户类,你可以从 UserMixin 继承,它提供了对所有这些方法的默认实现。我们这里使用UserMixin实现。

    2.3) 修改view函数(红色部分为新增)

    from flask.ext.login import login_required, login_user, logout_user
    
    from blog2.model.User import  User
    from blog2.model.Category import Category
    import os
    
    from blog2 import app,db
    from flask import request,render_template,flash,abort,url_for,redirect,session,Flask,g
    
    @app.route('/')
    @login_required
    def show_entries():
        categorys = Category.query.all()
        return render_template('show_entries.html',entries=categorys)
    
    @app.route('/add',methods=['POST'])
    @login_required
    def add_entry():
        #——————————————————————————————————————————————
        # 第一版登陆方式
        # if not session.get('logged_in'):
        #     abort(401)
        #——————————————————————————————————————————————
    
        title = request.form['title']
        content = request.form['text']
        category = Category(title,content)
        db.session.add(category)
        db.session.commit()
        flash('New entry was successfully posted')
        return redirect(url_for('show_entries'))
    
    @app.route('/login',methods=['GET','POST'])
    def login():
        error = None
        if request.method == 'POST':
            user = User.query.filter_by(username=request.form['username']).first()
            #——————————————————————————————————————————————————————————————————————————
            #第一版登陆方式
            # passwd = User.query.filter_by(password=request.form['password']).first()
            #
            # if user is None:
            #     error = 'Invalid username'
            # elif passwd is None:
            #     error = 'Invalid password'
            # else:
            #     session['logged_in'] = True
            #     flash('You were logged in')
            #     return redirect(url_for('show_entries'))
            #——————————————————————————————————————————————————————————————————————————
    
            login_user(user)
            flash('Logged in successfully.')
            return redirect(url_for('show_entries'))
    
        return render_template('login.html', error=error)
    
    
    @app.route('/logout')
    @login_required
    def logout():
        #—————————————————————————————————————————————— 
        # 第一版登出方式
        # session.pop('logged_in', None)
        #—————————————————————————————————————————————— 
       logout_user()
        flash('You were logged out')
        return redirect(url_for('show_entries'))

    通过flask-login管理登陆,代码非常简洁简单:

    @login_required:该装饰器放到需要登陆才能访问的视图上,如果没有登陆访问有限制的视图就会跳到login页面,由__init__.py中login_manager.login_view = "login"控制
    login_user(user):传入一个user对象进行登陆验证,正确返回true,否则返回false
    logout_user():登出函数,清空session中用户信息

    2.4) 模板中引用用户
    {% if current_user.is_authenticated() %}
      Hi {{ current_user.name }}!
    {% endif %}

    将之前layout.html和show_entries.html模板中判断用户是否登陆方式改为flask-login中的方式:

    {% if not current_user.is_authenticated() %}
    current_user值:在用户没有登陆时,值为<flask_login.AnonymousUserMixin object at 0x0000000003DCF550>,也就是匿名用户
    用户登陆后,值为<User u'admin'>


    当然,用户登陆还可以根据实际情况自己定制,具体不在一一详述。


    【参考文档】
    Flask-Login中文版:http://www.pythondoc.com/flask-login/#id1
    Flask-Login英文版:http://flask-login.readthedocs.io/en/latest/


  • 相关阅读:
    继承 多态
    封装练习
    PHP 面向对象封装
    面向对象 类和对象
    PHP前端和数据库的连接
    数组2
    PHP数组
    正则表达式
    PHP字符串
    linux基础
  • 原文地址:https://www.cnblogs.com/mysql-dba/p/6080709.html
Copyright © 2011-2022 走看看