use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
#[serde(rename_all = "lowercase")]
pub enum FormalStatus {
Parsed,
Prose,
}
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
#[serde(deny_unknown_fields)]
pub struct Clause {
pub id: String,
pub statement: String,
#[serde(default, skip_serializing_if = "Option::is_none")]
pub formal: Option<String>,
pub formal_status: FormalStatus,
}
impl Clause {
#[must_use]
pub fn defect(&self) -> Option<String> {
if self.id.trim().is_empty() {
return Some("empty id".into());
}
let formal_empty = self.formal.as_deref().is_none_or(|f| f.trim().is_empty());
(self.formal_status == FormalStatus::Parsed && formal_empty)
.then(|| format!("{}: formal_status parsed with no formal", self.id))
}
#[must_use]
pub fn atom(&self) -> Option<String> {
match self.formal_status {
FormalStatus::Parsed => self
.formal
.as_deref()
.map(|f| f.split_whitespace().collect::<Vec<_>>().join(" ")),
FormalStatus::Prose => None,
}
}
}