use crate::types::{ActorId, TenantId};
use std::collections::HashMap;
use std::error::Error;
use time::OffsetDateTime;
#[derive(Clone, Debug)]
pub struct AuthenticatedIdentity {
pub actor_id: ActorId,
pub tenant_id: Option<TenantId>,
pub roles: Vec<String>,
pub attributes: HashMap<String, String>,
pub authenticated_at: OffsetDateTime,
}
#[derive(Debug)]
#[non_exhaustive]
pub enum IdentityResolutionError {
InvalidToken,
Expired,
ProviderUnavailable,
Other(Box<dyn Error + Send + Sync + 'static>),
}
impl std::fmt::Display for IdentityResolutionError {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
match self {
Self::InvalidToken => write!(f, "invalid token"),
Self::Expired => write!(f, "token expired"),
Self::ProviderUnavailable => write!(f, "identity provider unavailable"),
Self::Other(e) => write!(f, "identity resolution error: {e}"),
}
}
}
impl Error for IdentityResolutionError {
fn source(&self) -> Option<&(dyn Error + 'static)> {
match self {
Self::Other(e) => Some(e.as_ref()),
_ => None,
}
}
}
#[allow(async_fn_in_trait)]
pub trait IdentitySource {
async fn resolve(&self, token: &str) -> Result<AuthenticatedIdentity, IdentityResolutionError>;
}