use alloc::string::{String, ToString};
use core::fmt;
use core::str::FromStr;
#[derive(Debug, PartialEq, Eq)]
pub enum Error {
InvalidIdentity,
}
#[cfg(feature = "std")]
impl std::error::Error for Error {}
impl fmt::Display for Error {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
match self {
Self::InvalidIdentity => f.write_str("Invalid identity tag"),
}
}
}
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub enum ExternalIdentity {
GitHub,
Twitter,
Mastodon,
Telegram,
}
impl fmt::Display for ExternalIdentity {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
f.write_str(self.as_str())
}
}
impl ExternalIdentity {
pub fn as_str(&self) -> &str {
match self {
Self::GitHub => "github",
Self::Twitter => "twitter",
Self::Mastodon => "mastodon",
Self::Telegram => "telegram",
}
}
}
impl FromStr for ExternalIdentity {
type Err = Error;
fn from_str(identity: &str) -> Result<Self, Self::Err> {
match identity {
"github" => Ok(Self::GitHub),
"twitter" => Ok(Self::Twitter),
"mastodon" => Ok(Self::Mastodon),
"telegram" => Ok(Self::Telegram),
_ => Err(Error::InvalidIdentity),
}
}
}
#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
pub struct Identity {
pub platform: ExternalIdentity,
pub ident: String,
pub proof: String,
}
impl Identity {
pub fn new<S1, S2>(platform_iden: S1, proof: S2) -> Result<Self, Error>
where
S1: AsRef<str>,
S2: Into<String>,
{
let i: &str = platform_iden.as_ref();
let (platform, ident) = i.rsplit_once(':').ok_or(Error::InvalidIdentity)?;
Ok(Self {
platform: ExternalIdentity::from_str(platform)?,
ident: ident.to_string(),
proof: proof.into(),
})
}
#[inline]
pub(crate) fn tag_platform_identity(&self) -> String {
format!("{}:{}", self.platform, self.ident)
}
}