Flask-Principal 权限管理实战:从安装到角色控制

云舒
云舒
发布时间:2026-10-11| 5人浏览过
原创

Flask-Principal 是 Flask 框架中用于处理权限管理的扩展。它通过 Identity(身份)、Needs(需求)和 Permission(权限)等核心组件,实现细粒度的访问控制。本文将通过实例分析,展示如何安装配置、定义角色、监听身份信号并实现基于角色的权限拦截。

Flask-Principal 核心组件与原理

Flask-Principal 的主要组件包括 Identity、Needs、Permission 和 IdentityContext。理解这些组件是正确使用该扩展的基础:

  • Identity(身份):代表当前用户,负责存储和加载每个请求的身份信息,包含用户拥有的访问权限。
  • Needs(需求):访问控制的最小粒度,代表具体的权限参数,例如“管理用户”或“编辑帖子”。
  • Permission(权限):由一个或多个 Needs 组成,用于判断用户是否拥有执行某操作的资格。
  • IdentityContext:针对特定权限的上下文,可用作上下文管理器或装饰器。

安装与初始化

首先,通过 pip 安装 Flask-Principal:

pip install flask-principal

在 Flask 应用中初始化 Principal 实例:

from flask_principal import Principal
principal = Principal()
principal.init_app(app)

定义角色与权限控制

我们需要定义角色常量,并创建基于角色的权限对象。以下代码定义了普通用户(NORMAL)和管理员(ADMIN)角色,并创建了一个仅允许 Admin 执行的权限:

from flask-principal import Permission,RoleNeed
from functools import wraps

# 定义相关角色
NORMAL = "NORMAL"
ADMIN = "ADMIN"
ROLES = (
  ("NORMAL","普通用户"),
  ("ADMIN","管理员")
)

# 创建仅允许 Admin 的权限
admin_permission = Permission(RoleNeed(ADMIN))

def admin_authority(func):
  @wraps(func)
  def decorated_view(*args,**kwargs):
    if admin_permission.can():
      return func(*args,**kwargs)
    else:
      return "非Admin用户"
  return decorated_view

用户模型与登录集成

结合 Flask-Login 和 SQLAlchemy 定义用户模型,并实现用户加载回调。注意,这里使用 ChoiceType 存储角色:

from app import login_manager
from app.db import Base,engine,session
from sqlalchemy import Column,String,Integer,create_engine
from sqlalchemy_utils.types.choice import ChoiceType
from flask_login import UserMixin
from permissions import ADMIN,ROLES

class User(Base,UserMixin):
  __tablename__ = "user"
  id = Column(Integer,primary_key=True)
  user = Column(String(16))
  password = Column(String(16))
  roles = Column(ChoiceType(ROLES),default=ADMIN)

@login_manager.user_loaded
def user_loaded(id):
  return session.query(User).filter_by(id=id).first()

Base.metadata.create_all(engine)

登录流程与信号发送

在登录接口中,验证用户凭据后调用 Flask-Login 的 login_user,并发送 identity_changed 信号以触发权限加载:

from app import app
from flask import request
from flask_login import login_user
from flask_principal import current_app,identity_changed,Identity
from userinfo import User
from app.db import session

@app.route("/login",methods=["POST"])
def login():
  user = request.form.get("user",None)
  password = request.form.get("password",None)
  if not user or not password:
    ...
  user = session.query(User).filter_by(user=user,password=password).first()
  if not user:
    ...
  # 登录
  login_user(user)
  # 发送信号,载入用户权限
  identity_changed.send(current_app._get_current_object(),identity=Identity(user.id))
  return ...

监听身份信号并加载权限

通过 identity_loaded 信号监听器,将当前用户的 ID 和角色添加到 Identity 的 provides 集合中,从而完成权限加载:

from flask_login import current_user
from flask_principal import identity_loaded,UserNeed,RoleNeed

@identity_loaded.connect_via(app)
def on_identity_loaded(sendder,identity):
  identity.user = current_user
  if hasattr(current_user,"id"):
    identity.provides.add(UserNeed(current_user.id))
  if hasattr(current_user,"roles"):
    identity.provides.add(RoleNeed(current_user.roles.code))

应用权限控制

最后,在需要保护的路由上使用自定义的 admin_authority 装饰器,实现只有 Admin 权限用户才能操作删除用户:

from app import app
from permission import admin_authority

@app.route("/delete_user",methods=["POST"])
@admin_authority
def delete_user():
  ...

以上就是 Flask-Principal 基本用法与权限控制实例的详细内容,更多关于 Flask 权限管理、Python Web 开发、Flask-Principal 配置的资料请关注本站其它相关文章!

相关标签:

免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。

Python 相关产品和应用

全部下载
Selenium

Selenium

4.51.0 · Windows

用于浏览器自动化和 Web 测试的 Python 工具。

scikit-learn

scikit-learn

1.9.1 · Windows

常用 Python 机器学习算法与模型评估工具库。

Black

Black

26.10.1 · Windows

强调一致性的 Python 自动代码格式化工具。

Ruff

Ruff

0.17.1 · macOS

由 Rust 编写的高速 Python 代码检查和格式化工具。

pytest

pytest

9.1.1 · Windows

简洁而强大的 Python 自动化测试框架。

FastAPI

FastAPI

0.146.0 · Windows

高性能 Python API 框架,支持类型提示和自动接口文档。

Flask

Flask

3.1.3 · Windows

轻量灵活的 Python Web 应用框架。

Django

Django

6.1.2 · Windows

成熟的 Python Web 框架,适合构建内容站点和业务系统。

Spyder

Spyder

6.1.7 · Windows

面向科学计算与数据分析的 Python 集成开发环境。

SciPy

SciPy

1.18.1 · Windows

面向科学、工程和技术计算的 Python 算法库。