use serde::{Deserialize, Serialize};
#[derive(Copy, Clone, Eq, PartialEq, Ord, PartialOrd, Hash, Debug, Serialize, Deserialize)]
#[serde(transparent)]
pub struct ExternalId(pub u64);
#[non_exhaustive]
#[derive(Clone, Eq, PartialEq, Debug, Serialize, Deserialize)]
pub enum Principal {
Unauthenticated,
External(ExternalId),
System,
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn principal_exhaustive_classify() {
fn classify(p: &Principal) -> &'static str {
match p {
Principal::Unauthenticated => "unauth",
Principal::External(_) => "external",
Principal::System => "system",
}
}
assert_eq!(classify(&Principal::Unauthenticated), "unauth");
assert_eq!(classify(&Principal::External(ExternalId(7))), "external");
assert_eq!(classify(&Principal::System), "system");
}
#[test]
fn external_id_is_transparent_u64() {
let id = ExternalId(0xDEAD_BEEF);
assert_eq!(id.0, 0xDEAD_BEEF);
}
#[test]
fn external_id_is_total_ordered() {
assert!(ExternalId(1) < ExternalId(2));
}
#[test]
fn principal_equality() {
assert_eq!(Principal::Unauthenticated, Principal::Unauthenticated);
assert_eq!(
Principal::External(ExternalId(3)),
Principal::External(ExternalId(3))
);
assert_ne!(
Principal::External(ExternalId(3)),
Principal::External(ExternalId(4))
);
assert_ne!(Principal::System, Principal::Unauthenticated);
}
}