- Create User model with bcrypt password hashing - Add auth routes: register, login, refresh, me - Implement JWT access and refresh tokens - Add get_current_user dependency for protected routes - Update Task model with user_id foreign key for data isolation - Update TaskService to filter tasks by authenticated user - Add auth configuration (secret key, token expiry)
68 lines
1.9 KiB
Python
68 lines
1.9 KiB
Python
from fastapi import APIRouter, Depends, HTTPException, status
|
|
from sqlalchemy.orm import Session
|
|
|
|
from ..db import get_db
|
|
from .schemas import UserCreate, UserLogin, UserResponse, TokenResponse, TokenRefresh
|
|
from .services import AuthService
|
|
from .dependencies import get_current_user
|
|
from .models import User
|
|
|
|
router = APIRouter(prefix="/auth", tags=["authentication"])
|
|
|
|
|
|
def get_auth_service(db: Session = Depends(get_db)) -> AuthService:
|
|
return AuthService(db)
|
|
|
|
|
|
@router.post("/register", response_model=UserResponse, status_code=201)
|
|
def register(
|
|
user_data: UserCreate,
|
|
service: AuthService = Depends(get_auth_service),
|
|
):
|
|
existing_user = service.get_user_by_email(user_data.email)
|
|
if existing_user:
|
|
raise HTTPException(
|
|
status_code=status.HTTP_400_BAD_REQUEST,
|
|
detail="Email already registered",
|
|
)
|
|
|
|
user = service.create_user(user_data)
|
|
return user
|
|
|
|
|
|
@router.post("/login", response_model=TokenResponse)
|
|
def login(
|
|
credentials: UserLogin,
|
|
service: AuthService = Depends(get_auth_service),
|
|
):
|
|
user = service.authenticate_user(credentials.email, credentials.password)
|
|
if not user:
|
|
raise HTTPException(
|
|
status_code=status.HTTP_401_UNAUTHORIZED,
|
|
detail="Invalid email or password",
|
|
)
|
|
|
|
return service.create_tokens(user)
|
|
|
|
|
|
@router.post("/refresh", response_model=TokenResponse)
|
|
def refresh(
|
|
token_data: TokenRefresh,
|
|
service: AuthService = Depends(get_auth_service),
|
|
):
|
|
tokens = service.refresh_tokens(token_data.refresh_token)
|
|
if tokens is None:
|
|
raise HTTPException(
|
|
status_code=status.HTTP_401_UNAUTHORIZED,
|
|
detail="Invalid or expired refresh token",
|
|
)
|
|
|
|
return tokens
|
|
|
|
|
|
@router.get("/me", response_model=UserResponse)
|
|
def get_current_user_info(
|
|
current_user: User = Depends(get_current_user),
|
|
):
|
|
return current_user
|