use vti_common::auth::session::now_epoch;
use crate::acl::{VtcAclEntry, VtcRole, get_acl_entry};
use crate::error::AppError;
use crate::members::{Member, get_member};
use crate::server::AppState;
#[derive(Debug, Clone)]
pub struct ActiveMember {
pub entry: VtcAclEntry,
pub member: Member,
}
pub async fn active_member(state: &AppState, did: &str) -> Result<Option<ActiveMember>, AppError> {
let Some(entry) = get_acl_entry(&state.acl_ks, did).await? else {
return Ok(None);
};
if entry.is_expired(now_epoch()) || entry.is_suspended() || entry.role == VtcRole::Application {
return Ok(None);
}
let Some(member) = get_member(&state.members_ks, did).await? else {
return Ok(None);
};
if member.is_removed() {
return Ok(None);
}
Ok(Some(ActiveMember { entry, member }))
}
pub async fn require_active_member(state: &AppState, did: &str) -> Result<ActiveMember, AppError> {
active_member(state, did)
.await?
.ok_or_else(|| AppError::Forbidden("not an active member of this community".into()))
}