45 lines
1.6 KiB
Python
45 lines
1.6 KiB
Python
"""菜单 code 权限守卫(V0.3:通过 sys_user_role → sys_role_menu → sys_menu.perms)"""
|
||
from typing import Callable, Set
|
||
|
||
from fastapi import Depends, HTTPException
|
||
from sqlalchemy.orm import Session
|
||
|
||
from app.core.auth import get_current_user
|
||
from app.core.database import get_db
|
||
from app.services.web_auth_roles import iter_user_menu_perm_codes
|
||
|
||
ADMIN_ROLES = {"admin", "super_admin"}
|
||
SUPER_ADMIN_ROLE = "super_admin"
|
||
|
||
|
||
def require_admin_or_super_admin(current_user: dict = Depends(get_current_user)):
|
||
"""运营端角色守卫:admin / super_admin 可访问。"""
|
||
role = current_user.get("role")
|
||
if role not in ADMIN_ROLES:
|
||
raise HTTPException(status_code=403, detail="需要运营人员权限")
|
||
return current_user
|
||
|
||
|
||
def get_user_menu_codes(db: Session, user_id: str) -> Set[str]:
|
||
"""读取用户授权的菜单权限标识集合(与前端 meta.menuCode / perms 对齐)。"""
|
||
return iter_user_menu_perm_codes(db, user_id or "")
|
||
|
||
|
||
def require_menu_code(menu_code: str) -> Callable:
|
||
"""接口菜单权限守卫。super_admin 直接放行。"""
|
||
normalized = (menu_code or "").strip()
|
||
|
||
def _dep(
|
||
current_user: dict = Depends(require_admin_or_super_admin),
|
||
db: Session = Depends(get_db),
|
||
):
|
||
role = current_user.get("role")
|
||
if role == SUPER_ADMIN_ROLE:
|
||
return current_user
|
||
codes = get_user_menu_codes(db, current_user.get("user_id"))
|
||
if normalized not in codes:
|
||
raise HTTPException(status_code=403, detail="无菜单访问权限")
|
||
return current_user
|
||
|
||
return _dep
|