use crate::StringTyped;
#[must_use]
pub fn is_name_valid(name: &str) -> bool {
name.trim() == name && name.as_bytes().first() != Some(&b'/')
}
#[must_use]
pub fn is_name_empty(name: &str) -> bool {
debug_assert!(is_name_valid(name));
name.is_empty()
}
pub trait Name: StringTyped + Default + PartialEq {
#[must_use]
fn is_valid(&self) -> bool {
is_name_valid(self.as_ref())
}
#[must_use]
fn is_empty(&self) -> bool {
is_name_empty(self.as_ref())
}
}
impl<T> Name for T where T: StringTyped + Default + PartialEq {}
pub trait Value: StringTyped + Default + PartialEq {}
impl<T> Value for T where T: StringTyped + Default + PartialEq {}
#[derive(Debug, Clone, Default, PartialEq, Eq)]
pub struct Property<N, V> {
pub name: N,
pub value: V,
}
impl<N, V> Property<N, V>
where
N: Name,
{
#[must_use]
pub fn has_name(&self) -> bool {
!self.name.is_empty()
}
#[must_use]
pub fn name(&self) -> &N {
debug_assert!(self.name.is_valid());
&self.name
}
#[must_use]
pub const fn value(&self) -> &V {
&self.value
}
#[must_use]
pub fn is_valid(&self) -> bool {
self.has_name()
}
}