"""JWT authentication dependencies for Hospitality service."""
from __future__ import annotations

from functools import lru_cache

from fastapi import Depends
from fastapi.security import HTTPAuthorizationCredentials, HTTPBearer

from app.core.config import settings
from shared.auth import JWTSettings, JWTValidator
from shared.exceptions import UnauthorizedError
from shared.security import CurrentUser

_bearer = HTTPBearer(auto_error=False)


@lru_cache
def get_jwt_validator() -> JWTValidator:
    return JWTValidator(
        JWTSettings(
            keycloak_enabled=settings.keycloak_enabled,
            keycloak_server_url=settings.keycloak_server_url,
            keycloak_realm=settings.keycloak_realm,
            jwt_algorithm=settings.jwt_algorithm,
            jwt_audience=settings.jwt_audience,
            jwt_verify_signature=settings.jwt_verify_signature,
            jwt_issuer=settings.keycloak_public_realm_url,
        )
    )


async def get_current_user(
    credentials: HTTPAuthorizationCredentials | None = Depends(_bearer),
) -> CurrentUser:
    if not settings.auth_required:
        return CurrentUser(user_id="test-user", username="test", roles=["tenant_admin"])
    if credentials is None or not credentials.credentials:
        raise UnauthorizedError("توکن احراز هویت ارائه نشده است")
    return await get_jwt_validator().validate(credentials.credentials)


async def get_optional_user(
    credentials: HTTPAuthorizationCredentials | None = Depends(_bearer),
) -> CurrentUser | None:
    if not settings.auth_required:
        return CurrentUser(user_id="test-user", username="test", roles=["tenant_admin"])
    if credentials is None or not credentials.credentials:
        return None
    return await get_jwt_validator().validate(credentials.credentials)
