# -*- coding:utf-8 -*-

from operator import itemgetter

from fastapi import Depends
from fastapi.security import HTTPAuthorizationCredentials, HTTPBearer
import jwt
from jwt.exceptions import ExpiredSignatureError
from pydantic import BaseModel, Field

from odoo_api.core.connection import sanitize_error_message
from odoo_api.dependencies.auth import decrypt
from odoo_api.core.config import get_settings
from odoo_api.exceptions import UnauthorizedException, DecryptionError

bearer_scheme = HTTPBearer()


def get_logged_in_user(credentials: HTTPAuthorizationCredentials = Depends(bearer_scheme)):
    token = credentials.credentials
    try:
        settings = get_settings()
        payload = jwt.decode(token, settings.jwt_secret_key, algorithms=[settings.hash_algorithm])
        resp_db, resp_uid, resp_password = itemgetter("db", "uid", "password")(payload)
        decrypted_password = decrypt(resp_password, settings.aes_secret_key)
        return AuthenticatedUser(**{
            "uid": resp_uid,
            "password": decrypted_password,
            "host": settings.odoo_host,
            "db": resp_db
        })
    except ExpiredSignatureError:
        raise UnauthorizedException(message="Access token has expired.")
    except DecryptionError:
        raise UnauthorizedException(message="Could not validate credentials")
    except Exception as e:
        error_message = sanitize_error_message(e)
        raise UnauthorizedException(message="Could not validate credentials: %s" % error_message)


class Token(BaseModel):
    access_token: str = Field(..., description="JWT access token")
    token_type: str = Field(..., description="Token type (bearer)")

    model_config = {"json_schema_extra": {"examples": [{"access_token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9...", "token_type": "bearer"}]}}


class AuthenticationBody(BaseModel):
    db: str | None = Field(None, description="Odoo database name (optional if ODOO_DB is configured)")
    username: str = Field(..., description="Odoo username")
    password: str = Field(..., description="Odoo password")

    model_config = {"json_schema_extra": {"examples": [{"username": "admin", "password": "admin"}]}}


class AuthenticatedUser(BaseModel):
    uid: int
    password: str
    host: str
    db: str
