123 lines
4.6 KiB
Python
123 lines
4.6 KiB
Python
from fastapi import APIRouter, Depends, HTTPException, status
|
|
from fastapi.security import OAuth2PasswordRequestForm
|
|
from sqlalchemy.ext.asyncio import AsyncSession
|
|
from sqlalchemy import select
|
|
|
|
from app.db.session import get_db
|
|
from app.services.auth_service import AuthService
|
|
from app.core.security import create_access_token, RANK_MAP
|
|
from app.schemas.auth import (
|
|
UserLiteRegister, Token, PasswordResetRequest,
|
|
UserKYCComplete, PasswordResetConfirm
|
|
)
|
|
from app.api.deps import get_current_user
|
|
from app.models.identity import User
|
|
|
|
router = APIRouter()
|
|
|
|
@router.post("/register-lite", response_model=Token, status_code=status.HTTP_201_CREATED)
|
|
async def register_lite(user_in: UserLiteRegister, db: AsyncSession = Depends(get_db)):
|
|
"""Step 1: Alapszintű regisztráció. Az új felhasználó alapértelmezetten 'user' (Rank 10)."""
|
|
stmt = select(User).where(User.email == user_in.email)
|
|
result = await db.execute(stmt)
|
|
if result.scalar_one_or_none():
|
|
raise HTTPException(
|
|
status_code=status.HTTP_400_BAD_REQUEST,
|
|
detail="Ez az e-mail cím már regisztrálva van."
|
|
)
|
|
|
|
try:
|
|
user = await AuthService.register_lite(db, user_in)
|
|
|
|
# Kezdeti token generálása
|
|
token_data = {
|
|
"sub": str(user.id),
|
|
"role": "user",
|
|
"rank": 10,
|
|
"scope_level": "individual",
|
|
"scope_id": str(user.id)
|
|
}
|
|
|
|
token = create_access_token(data=token_data)
|
|
return {
|
|
"access_token": token,
|
|
"token_type": "bearer",
|
|
"is_active": user.is_active
|
|
}
|
|
except Exception as e:
|
|
raise HTTPException(
|
|
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
|
|
detail=f"Sikertelen regisztráció: {str(e)}"
|
|
)
|
|
|
|
@router.post("/login", response_model=Token)
|
|
async def login(
|
|
db: AsyncSession = Depends(get_db),
|
|
form_data: OAuth2PasswordRequestForm = Depends()
|
|
):
|
|
"""Bejelentkezés és okos JWT generálása RBAC adatokkal."""
|
|
user = await AuthService.authenticate(db, form_data.username, form_data.password)
|
|
if not user:
|
|
raise HTTPException(
|
|
status_code=status.HTTP_401_UNAUTHORIZED,
|
|
detail="Hibás e-mail cím vagy jelszó."
|
|
)
|
|
|
|
# Szerepkör string kinyerése és rang meghatározása a RANK_MAP-ből
|
|
role_name = user.role.value if hasattr(user.role, 'value') else str(user.role)
|
|
user_rank = RANK_MAP.get(role_name, 10)
|
|
|
|
token_data = {
|
|
"sub": str(user.id),
|
|
"role": role_name,
|
|
"rank": user_rank,
|
|
"scope_level": user.scope_level or "individual",
|
|
"scope_id": user.scope_id or str(user.id),
|
|
"region": user.region_code
|
|
}
|
|
|
|
token = create_access_token(data=token_data)
|
|
return {
|
|
"access_token": token,
|
|
"token_type": "bearer",
|
|
"is_active": user.is_active
|
|
}
|
|
|
|
@router.get("/verify-email")
|
|
async def verify_email(token: str, db: AsyncSession = Depends(get_db)):
|
|
"""E-mail megerősítése."""
|
|
success = await AuthService.verify_email(db, token)
|
|
if not success:
|
|
raise HTTPException(status_code=400, detail="Érvénytelen vagy lejárt token.")
|
|
return {"message": "Email sikeresen megerősítve!"}
|
|
|
|
@router.post("/complete-kyc")
|
|
async def complete_kyc(
|
|
kyc_in: UserKYCComplete,
|
|
db: AsyncSession = Depends(get_db),
|
|
current_user: User = Depends(get_current_user)
|
|
):
|
|
"""Step 2: KYC adatok rögzítése és aktiválás."""
|
|
user = await AuthService.complete_kyc(db, current_user.id, kyc_in)
|
|
if not user:
|
|
raise HTTPException(status_code=404, detail="Felhasználó nem található.")
|
|
return {"status": "success", "message": "A profil aktiválva."}
|
|
|
|
@router.post("/forgot-password")
|
|
async def forgot_password(req: PasswordResetRequest, db: AsyncSession = Depends(get_db)):
|
|
"""Elfelejtett jelszó folyamat."""
|
|
result = await AuthService.initiate_password_reset(db, req.email)
|
|
if result == "cooldown":
|
|
raise HTTPException(status_code=429, detail="Kérjük várjon 2 percet.")
|
|
return {"message": "Amennyiben a cím létezik, a linket kiküldtük."}
|
|
|
|
@router.post("/reset-password")
|
|
async def reset_password(req: PasswordResetConfirm, db: AsyncSession = Depends(get_db)):
|
|
"""Új jelszó beállítása."""
|
|
if req.password != req.password_confirm:
|
|
raise HTTPException(status_code=400, detail="A jelszavak nem egyeznek.")
|
|
|
|
success = await AuthService.reset_password(db, req.email, req.token, req.password)
|
|
if not success:
|
|
raise HTTPException(status_code=400, detail="Hiba a jelszó frissítésekor.")
|
|
return {"message": "A jelszó sikeresen frissítve!"} |