from typing import Optional from fastapi import Request, HTTPException, status, Depends from fastapi.security import HTTPBearer, HTTPAuthorizationCredentials from jose import JWTError, jwt from app.config.settings import settings from app.database.connection import get_db from app.database.models import User security = HTTPBearer() def get_current_user_optional( credentials: Optional[HTTPAuthorizationCredentials] = Depends(HTTPBearer(auto_error=False)) ) -> Optional[User]: """ Get current user from JWT token (optional - doesn't raise error if no token). Args: credentials: Optional HTTP authorization credentials Returns: User object if authenticated, None otherwise """ if not credentials: return None try: token = credentials.credentials payload = jwt.decode( token, settings.secret_key, algorithms=[settings.algorithm] ) user_id: str = payload.get("sub") if user_id is None: return None # Get user from database db = next(get_db()) user = db.query(User).filter(User.id == user_id).first() return user except JWTError: return None def get_current_user( credentials: HTTPAuthorizationCredentials = Depends(security) ) -> User: """ Get current user from JWT token (required - raises error if no valid token). Args: credentials: HTTP authorization credentials Returns: User object Raises: HTTPException: If token is invalid or user not found """ try: token = credentials.credentials payload = jwt.decode( token, settings.secret_key, algorithms=[settings.algorithm] ) user_id: str = payload.get("sub") if user_id is None: raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="Could not validate credentials" ) # Get user from database db = next(get_db()) user = db.query(User).filter(User.id == user_id).first() if user is None: raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="User not found" ) return user except JWTError: raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, detail="Could not validate credentials" )