first commit
This commit is contained in:
54
backend/auth.py
Normal file
54
backend/auth.py
Normal file
@@ -0,0 +1,54 @@
|
||||
from datetime import datetime, timedelta, timezone
|
||||
import importlib.util
|
||||
|
||||
from fastapi import Depends, HTTPException, status
|
||||
from fastapi.security import HTTPAuthorizationCredentials, HTTPBearer
|
||||
|
||||
_jose_spec = importlib.util.find_spec("jose")
|
||||
_jose_origin = _jose_spec.origin if _jose_spec else None
|
||||
|
||||
_incompatible_jose = bool(_jose_origin and _jose_origin.endswith("site-packages/jose.py"))
|
||||
|
||||
try:
|
||||
import jwt
|
||||
from jwt import InvalidTokenError as JWTError
|
||||
except Exception as exc:
|
||||
if not _incompatible_jose:
|
||||
try:
|
||||
from jose import JWTError, jwt
|
||||
except Exception as fallback_exc:
|
||||
raise RuntimeError(
|
||||
"JWT 依赖不可用,请安装 python-jose[cryptography] 或 PyJWT"
|
||||
) from fallback_exc
|
||||
else:
|
||||
raise RuntimeError(
|
||||
"检测到不兼容依赖 jose,请卸载 jose 后安装 python-jose[cryptography] 或安装 PyJWT"
|
||||
) from exc
|
||||
|
||||
from backend.config import settings
|
||||
|
||||
security = HTTPBearer()
|
||||
|
||||
|
||||
def create_access_token(subject: str) -> str:
|
||||
expire = datetime.now(timezone.utc) + timedelta(minutes=settings.access_token_expire_minutes)
|
||||
payload = {"sub": subject, "exp": expire}
|
||||
return jwt.encode(payload, settings.jwt_secret_key, algorithm=settings.jwt_algorithm)
|
||||
|
||||
|
||||
def verify_password(username: str, password: str) -> bool:
|
||||
return username == settings.admin_username and password == settings.admin_password
|
||||
|
||||
|
||||
def get_current_user(
|
||||
credentials: HTTPAuthorizationCredentials = Depends(security),
|
||||
) -> str:
|
||||
token = credentials.credentials
|
||||
try:
|
||||
payload = jwt.decode(token, settings.jwt_secret_key, algorithms=[settings.jwt_algorithm])
|
||||
username: str | None = payload.get("sub")
|
||||
if not username:
|
||||
raise HTTPException(status_code=status.HTTP_401_UNAUTHORIZED, detail="无效Token")
|
||||
return username
|
||||
except JWTError as exc:
|
||||
raise HTTPException(status_code=status.HTTP_401_UNAUTHORIZED, detail="登录已过期") from exc
|
||||
Reference in New Issue
Block a user