use async_trait::async_trait;
use serde::Serialize;
use tideway::auth::{AccessTokenClaims, AuthProvider, JwtVerifier};
use tideway::Result;

#[derive(Debug, Clone, Serialize)]
pub struct SimpleUser {
    pub id: String,
    pub email: Option<String>,
    pub name: Option<String>,
}

#[derive(Clone)]
pub struct SimpleAuthProvider {
    verifier: JwtVerifier<AccessTokenClaims<serde_json::Value>>,
}

impl SimpleAuthProvider {
    pub fn from_secret(secret: &str) -> Self {
        Self {
            verifier: JwtVerifier::from_secret(secret.as_bytes()),
        }
    }
}

#[async_trait]
impl AuthProvider for SimpleAuthProvider {
    type Claims = AccessTokenClaims<serde_json::Value>;
    type User = SimpleUser;

    async fn verify_token(&self, token: &str) -> Result<Self::Claims> {
        let token_data = self.verifier.verify_access_token(token).await?;
        Ok(token_data.claims)
    }

    async fn load_user(&self, claims: &Self::Claims) -> Result<Self::User> {
        Ok(SimpleUser {
            id: claims.standard.sub.clone(),
            email: claims.email.clone(),
            name: claims.name.clone(),
        })
    }
}
