flask第三方登陆插件flask_login用法详解

flask_login模块主要是用来验证登陆的插件,使用起来肯定比自己写要方便得多

Flask-Login 通过 user session,提供登录的常见任务,比如登入 (logging in)、登出 (logging out) 和当前用户 (current user)
login_user() 函数:实现用户的登入,一般在登入的视图函数中调用
logout_user() 函数:实现登出功能
current_user 属性:获取当前用户
对于使用者来说,如果需要页面是授权用户才可见,在相应视图函数前加上 @login_required 装饰器进行声明即可,@login_required 装饰器对于未登录用户访问,默认处理是重定向到 LoginManager.login_view 所指定的视图

下面我们来看看flask_login的具体用法

首先安装模块

pip install flask_login

然后需要我们去应用工厂注册注册该模块和app绑定,还是把我项目的工厂函数发上来

#!/usr/bin/python3
#coding:utf-8
from flask import Flask
from app.web import web
from config import load_json
from .common import db,mail
from flask_login import LoginManager
import logging
import os
import time
config = load_json()
loginmanager=LoginManager()
loginmanager.login_view='web.login'
loginmanager.session_protection='strong'
loginmanager.login_message='please login !'

def create_app():
    app = Flask(__name__)
    app.secret_key = 'sulao'
    configure_db(app)
    db.init_app(app)
    register_blueprint(app)
    configure_mail(app)
    mail.init_app(app)
    configure_logger(app)
    loginmanager.init_app(app)
    return app

def configure_db(app):
    #查询时会显示原始SQL语句
    app.config['SQLALCHEMY_ECHO'] = True
    app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = True
    app.config['SQLALCHEMY_DATABASE_URI'] = 'mysql+pymysql://{db_user}:{db_pass}@{db_host}:{db_port}/{db_name}?charset=utf8mb4'.format(
        db_user=config['db']['db_user'],
        db_pass=config['db']['db_pass'],
        db_host=config['db']['db_host'],
        db_port=config['db']['db_port'],
        db_name=config['db']['db_name'])

def configure_mail(app):
    app.config['MAIL_SERVER'] = config['mail']['mail_host']
    app.config["MAIL_PORT"] = config['mail']['mail_port']
    app.config["MAIL_USE_SSL"] = True
    app.config["MAIL_USERNAME"] = config['mail']['mail_user']
    app.config["MAIL_PASSWORD"] = config['mail']['mail_pass']

def configure_logger(app):
    log_dir_name = "logs"
    log_file_name = 'logger-' + time.strftime('%Y-%m-%d', time.localtime(time.time())) + '.log'
    log_file_str = log_dir_name + os.sep + log_file_name
    log_level = logging.WARNING
    handler = logging.FileHandler(log_file_str, encoding='UTF-8')
    handler.setLevel(log_level)
    logging_format = logging.Formatter(
        '%(asctime)s - %(levelname)s - %(filename)s - %(funcName)s - %(lineno)s - %(message)s')
    handler.setFormatter(logging_format)
    app.logger.addHandler(handler)

def register_blueprint(app):
    app.register_blueprint(web, url_prefix='')

然后还需要对模型进行修改,我的模型如下

#!/usr/bin/python3
#coding:utf-8
from datetime import datetime
from app.common import db
from flask_login import AnonymousUserMixin

class Category(db.Model):
    __tablename__ = "category"
    cateid = db.Column(db.Integer, primary_key=True, autoincrement=True)
    catname = db.Column(db.String(255))
    thumb = db.Column(db.String(255))
    listorder = db.Column(db.Integer)
    aliasname = db.Column(db.String(255))
    ismenu = db.Column(db.Integer, default=1)
    rootid = db.Column(db.Integer, default=0)
    parentid = db.Column(db.Integer, default=0)
    __mapper_args__ = {
        "order_by": cateid.desc()
    }

class Post(db.Model):
    __tablename__ = 'post'
    postid = db.Column(db.Integer, primary_key=True, autoincrement=True)
    cateid = db.Column(db.Integer)
    userid = db.Column(db.Integer)
    tag = db.Column(db.String(255))
    thumb = db.Column(db.String(255))
    status = db.Column(db.Integer, default=1)
    aliasname = db.Column(db.String(255))
    istop = db.Column(db.Integer)
    title = db.Column(db.String(255))
    intro = db.Column(db.Text(65536))
    content = db.Column(db.Text(16777216))
    posttime = db.Column(db.DateTime, default=datetime.utcnow)
    updatetime = db.Column(db.DateTime, default=datetime.utcnow)
    __mapper_args__ = {
        "order_by": postid.desc()
    }

class Tag(db.Model):
    __tablename__ = 'tag'
    tagid = db.Column(db.Integer, primary_key=True, autoincrement=True)
    tagname = db.Column(db.String(32))
    letter = db.Column(db.String(64))
    postid = db.Column(db.Integer)
    __mapper_args__ = {
        "order_by": tagid.desc()
    }

class Comment(db.Model):
    __tablename__ = 'comment'
    commentid = db.Column(db.Integer, primary_key=True, autoincrement=True)
    postid = db.Column(db.Integer)
    status = db.Column(db.Integer, default=0)
    title = db.Column(db.String(32))
    email = db.Column(db.String(128))
    content = db.Column(db.String(255))
    posttime = db.Column(db.DateTime, default=datetime.utcnow)
    ipaddress = db.Column(db.String(16))
    useragent = db.Column(db.String(255))
    __mapper_args__ = {
        "order_by": commentid.desc()
    }

class User(db.Model):
    __tablename__ = 'user'
    userid = db.Column(db.Integer, primary_key=True, autoincrement=True)
    level = db.Column(db.Integer)
    status = db.Column(db.Integer, default=1)
    name = db.Column(db.String(32))
    nick = db.Column(db.String(32))
    password = db.Column(db.String(32))
    email = db.Column(db.String(128))
    ipaddress = db.Column(db.String(16))
    posttime = db.Column(db.DateTime, default=datetime.utcnow)
    __mapper_args__ = {
        "order_by": userid.desc()
    }
    def is_authenticated(self):
        if isinstance(self,AnonymousUserMixin):
            return False
        else:
            return True
    def is_active(self):
        return True
    def is_anonymous(self):
        if isinstance(self,AnonymousUserMixin):
            return True
        else:
            return False
    def get_id(self):
        return unicode(self.id)

class Upload(db.Model):
    __tablename__ = 'upload'
    attchmentid = db.Column(db.Integer, primary_key=True, autoincrement=True)
    userid = db.Column(db.Integer)
    size = db.Column(db.Integer)
    filepath = db.Column(db.String(255))
    alt = db.Column(db.String(255))
    mimetype = db.Column(db.String(255))
    posttime = db.Column(db.DateTime, default=datetime.utcnow)
    __mapper_args__ = {
        "order_by": attchmentid.desc()
    }

class Setting(db.Model):
    __tablename__ = 'setting'
    systemid = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String(32))
    configure = db.Column(db.Text(65536)

以上添加的类的方法介绍

is_authenticated:表示user对象是否登录
is_active:表示用户是否激活,如:激活状态和未激活状态采用不同的处理
is_anonymous:表示访问者是否处于未登录的匿名状态
get_id:返回user对象的唯一识别标志

然后是视图函数的使用方法

首先需要在login函数中注册

from flask_login import login_user,login_required,logout_user,current_user
@web.route('/login/', methods=['POST', 'GET'])
def login():
    form = LoginForm(request.form)
    if request.method == "POST" and form.validate():
        username = request.form.get('username')
        password = request.form.get('password')
        user = db.session.query(User).filter_by(username == username).first()
        if user:
            # 将用户信息注册到flask-login中
            login_user(user)
        	next = request.args.get('next')
            if user.check_password(password):
                return redirect(url_for('web.member'))
            else:
                pass_err = "密码不正确"
                return render_template('mylogin.html', pass_err=pass_err, form=form)
        else:
            name_err = "用户名不正确"
            return render_template('mylogin.html', name_err=name_err, form=form)
    return render_template('account.html', form=form)
    
@web.route('/logout/')
@login_required# 装饰器,必须登录才能有权限 ****
def logout():
    logout_user()
    return redirect(url_for('web.login'))

前端示例

<--> 用户如果登录则显示用户名,否则给出登录和注册的链接 </--> 
{% if current_user.is_authenticated %}
   <li class="layui-nav-item">
       <a href="javascript:;">
           {{ current_user.username }}
       </a>
   <dl class="layui-nav-child">
       <dd><a href="" target="page_content">基本资料</a></dd>
       <dd><a href="">安全设置</a></dd>
   </dl>
   </li>
   <li class="layui-nav-item"><a href="{{ url_for("cms.logout") }}">退了</a></li>
 {% else %}
   <li class="layui-nav-item"><a href="{{ url_for("cms.login") }}">登录</a></li>
   <li class="layui-nav-item"><a href="{{ url_for("cms.register") }}">注册</a></li>
 {% endif %}


内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://sulao.cn/post/672.html

我要评论

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。