Skip to main content

made_core/value_objects/
output_contract_id.rs

1use std::borrow::Borrow;
2use std::fmt;
3
4use serde::{Deserialize, Serialize};
5
6use crate::error::DomainError;
7
8const MAX_OUTPUT_CONTRACT_ID_LEN: usize = 128;
9
10/// Stable identity of a structured output contract.
11#[derive(Debug, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
12#[serde(transparent)]
13pub struct OutputContractId(String);
14
15impl OutputContractId {
16    pub fn new(raw: impl Into<String>) -> Result<Self, DomainError> {
17        let raw = raw.into();
18        let value = raw.trim();
19        if value.is_empty() {
20            return Err(DomainError::EmptyField {
21                field: "output_contract.contract_id",
22            });
23        }
24        if value.len() > MAX_OUTPUT_CONTRACT_ID_LEN {
25            return Err(DomainError::FieldTooLong {
26                field: "output_contract.contract_id",
27                actual: value.len(),
28                max: MAX_OUTPUT_CONTRACT_ID_LEN,
29            });
30        }
31        Ok(Self(value.to_owned()))
32    }
33
34    #[must_use]
35    pub fn as_str(&self) -> &str {
36        &self.0
37    }
38}
39
40impl Borrow<str> for OutputContractId {
41    fn borrow(&self) -> &str {
42        self.as_str()
43    }
44}
45
46impl fmt::Display for OutputContractId {
47    fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
48        formatter.write_str(self.as_str())
49    }
50}
51
52impl PartialEq<str> for OutputContractId {
53    fn eq(&self, other: &str) -> bool {
54        self.as_str() == other
55    }
56}
57
58impl PartialEq<&str> for OutputContractId {
59    fn eq(&self, other: &&str) -> bool {
60        self.as_str() == *other
61    }
62}
63
64#[cfg(test)]
65mod tests {
66    use super::*;
67
68    #[test]
69    fn trims_a_valid_identity() {
70        assert_eq!(OutputContractId::new(" report-v1 ").unwrap(), "report-v1");
71    }
72
73    #[test]
74    fn rejects_an_empty_identity() {
75        assert!(OutputContractId::new(" ").is_err());
76    }
77}