# app/routers/auth.py from datetime import timedelta from fastapi import APIRouter, Depends, HTTPException, status from fastapi.security import HTTPBearer from pydantic import BaseModel from sqlalchemy.orm import Session from app.config import get_settings from app.database import get_db from app.models.admin import Admin from app.auth import verify_password, get_password_hash, create_access_token, get_current_admin router = APIRouter() settings = get_settings() security = HTTPBearer() # Schemas class LoginRequest(BaseModel): username: str password: str class LoginResponse(BaseModel): code: int = 200 message: str data: dict class AdminInfoResponse(BaseModel): code: int = 200 data: dict class ChangePasswordRequest(BaseModel): old_password: str new_password: str # Routes @router.post("/login", response_model=LoginResponse) def login(request: LoginRequest, db: Session = Depends(get_db)): admin = db.query(Admin).filter(Admin.username == request.username).first() if not admin or not verify_password(request.password, admin.password_hash): raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="用户名或密码错误" ) access_token_expires = timedelta(minutes=settings.ACCESS_TOKEN_EXPIRE_MINUTES) access_token = create_access_token( data={"sub": admin.username}, expires_delta=access_token_expires ) return LoginResponse( message="登录成功", data={ "token": access_token, "admin": { "id": admin.id, "username": admin.username } } ) @router.get("/me", response_model=AdminInfoResponse) def get_me(current_admin: Admin = Depends(get_current_admin)): return AdminInfoResponse( data={ "id": current_admin.id, "username": current_admin.username } ) @router.post("/change-password") def change_password( request: ChangePasswordRequest, current_admin: Admin = Depends(get_current_admin), db: Session = Depends(get_db) ): if not verify_password(request.old_password, current_admin.password_hash): raise HTTPException( status_code=status.HTTP_400_BAD_REQUEST, detail="原密码错误" ) current_admin.password_hash = get_password_hash(request.new_password) db.commit() return {"code": 200, "message": "密码修改成功"}