dory/src/mailbox/mod.rs

76 lines
2.2 KiB
Rust

//! A full representation of a Misfin mailbox, including display name
use crate::{mailuser::Mailuser, prelude::Host};
use std::{fmt, str::FromStr};
#[cfg(feature = "serde")]
use serde::{Deserialize, Serialize};
mod error;
pub use error::Error;
#[derive(Debug, Clone, PartialEq)]
#[cfg_attr(feature = "serde", derive(Deserialize, Serialize))]
pub struct Mailbox {
pub username: String,
pub host: Host,
pub blurb: Option<String>,
}
impl fmt::Display for Mailbox {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
if let Some(ref blurb) = self.blurb {
write!(f, "{}@{} {}", self.username, self.host, blurb,)
} else {
write!(f, "{}@{}", self.username, self.host,)
}
}
}
impl FromStr for Mailbox {
type Err = Error;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let mut blurb = None;
if let Some((username, mut host)) = s.split_once('@') {
if username.is_empty() {
Err(Error::EmptyUser)
} else if username.contains(char::is_whitespace) {
Err(Error::IllegalWhitespace)
} else {
let username = username.to_string();
if let Some((h, b)) = host.split_once(char::is_whitespace) {
if h.is_empty() {
return Err(Error::EmptyHost);
} else if h.contains(char::is_whitespace) {
return Err(Error::IllegalWhitespace);
}
host = h;
if !b.is_empty() {
if b.contains('\n') {
return Err(Error::IllegalWhitespace);
}
blurb = Some(b.to_string());
}
}
let host = host.parse()?;
Ok(Self {
username,
host,
blurb,
})
}
} else {
Err(Error::MissingSeparator)
}
}
}
impl From<Mailuser> for Mailbox {
fn from(value: Mailuser) -> Self {
Self {
username: value.username,
host: value.host,
blurb: None,
}
}
}