use crate::Error;
use serde::{Deserialize, Serialize};
use std::fmt;
use std::str::FromStr;
#[derive(Debug, Clone, Copy, Eq, PartialEq, Serialize, Deserialize)]
pub struct RestrictModCalledStrand(bool);
impl Default for RestrictModCalledStrand {
fn default() -> Self {
RestrictModCalledStrand(true)
}
}
impl FromStr for RestrictModCalledStrand {
type Err = Error;
fn from_str(val_str: &str) -> Result<Self, Self::Err> {
match val_str {
"bc" => Ok(RestrictModCalledStrand(true)),
"bc_comp" => Ok(RestrictModCalledStrand(false)),
_ => Err(Error::InvalidState(
"Please specify bc or bc_comp for mod-called strand!".to_string(),
)),
}
}
}
impl fmt::Display for RestrictModCalledStrand {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
write!(f, "{}", char::from(*self))
}
}
impl From<RestrictModCalledStrand> for char {
fn from(val: RestrictModCalledStrand) -> char {
match val {
RestrictModCalledStrand(true) => '+',
RestrictModCalledStrand(false) => '-',
}
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn restrict_mod_called_strand_basic() {
let bc = RestrictModCalledStrand::from_str("bc").expect("should parse");
assert_eq!(format!("{bc}"), "+");
assert_eq!(char::from(bc), '+');
let bc_comp = RestrictModCalledStrand::from_str("bc_comp").expect("should parse");
assert_eq!(format!("{bc_comp}"), "-");
assert_eq!(char::from(bc_comp), '-');
}
#[test]
fn restrict_mod_called_strand_errors() {
assert!(matches!(
RestrictModCalledStrand::from_str("invalid"),
Err(Error::InvalidState(_))
));
assert!(matches!(
RestrictModCalledStrand::from_str(""),
Err(Error::InvalidState(_))
));
assert!(matches!(
RestrictModCalledStrand::from_str("+"),
Err(Error::InvalidState(_))
)); }
#[test]
fn restrict_mod_called_strand_default() {
let default_strand = RestrictModCalledStrand::default();
assert_eq!(char::from(default_strand), '+');
}
}