1use std::fmt::Display;
2
3use borsh::{BorshDeserialize, BorshSerialize};
4use serde::{Deserialize, Deserializer, Serialize, Serializer};
5
6#[derive(
7 Default,
8 Debug,
9 Clone,
10 Hash,
11 PartialEq,
12 Eq,
13 Ord,
14 PartialOrd,
15 BorshSerialize,
16 BorshDeserialize,
17)]
18pub enum SchemaType {
19 #[default]
20 Governance,
21 Type(String),
22 AllSchemas,
23}
24
25pub enum ReservedWords {
26 AllSchemas,
27 Governance,
28 Any,
29 Witnesses,
30 Owner,
31}
32
33impl Display for ReservedWords {
34 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
35 match self {
36 ReservedWords::AllSchemas => write!(f, "all_schemas"),
37 ReservedWords::Governance => write!(f, "governance"),
38 ReservedWords::Any => write!(f, "Any"),
39 ReservedWords::Witnesses => write!(f, "Witnesses"),
40 ReservedWords::Owner => write!(f, "Owner"),
41 }
42 }
43}
44
45impl std::str::FromStr for SchemaType {
46 type Err = String;
47
48 fn from_str(s: &str) -> Result<Self, Self::Err> {
49 if s.is_empty() {
51 return Err("Schema_id can not be empty".to_string());
52 }
53
54 match s {
55 "governance" => Ok(SchemaType::Governance),
56 "all_schemas" => Ok(SchemaType::AllSchemas),
57 _ => Ok(SchemaType::Type(s.to_string())),
58 }
59 }
60}
61
62impl SchemaType {
63 pub fn len(&self) -> usize {
64 match self {
65 SchemaType::Governance => "governance".len(),
66 SchemaType::Type(schema_id) => schema_id.len(),
67 SchemaType::AllSchemas => "all_schemas".len(),
68 }
69 }
70
71 pub fn is_empty(&self) -> bool {
72 match self {
73 SchemaType::Governance => false,
74 SchemaType::Type(schschema_id) => schschema_id.is_empty(),
75 SchemaType::AllSchemas => false,
76 }
77 }
78
79 pub fn is_valid(&self) -> bool {
80 match self {
81 SchemaType::Governance => true,
82 SchemaType::AllSchemas => true,
83 SchemaType::Type(schema_id) => {
84 !schema_id.is_empty()
85 && schema_id != &ReservedWords::Governance.to_string()
86 && schema_id != &ReservedWords::AllSchemas.to_string()
87 && schema_id.trim().len() == schema_id.len()
88 }
89 }
90 }
91}
92
93impl Display for SchemaType {
94 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
95 match self {
96 SchemaType::AllSchemas => write!(f, "all_schemas"),
97 SchemaType::Governance => write!(f, "governance"),
98 SchemaType::Type(schema_id) => write!(f, "{}", schema_id),
99 }
100 }
101}
102
103impl SchemaType {
104 pub fn is_gov(&self) -> bool {
105 matches!(self, SchemaType::Governance)
106 }
107}
108
109impl<'de> Deserialize<'de> for SchemaType {
110 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
111 where
112 D: Deserializer<'de>,
113 {
114 let s = <String as serde::Deserialize>::deserialize(deserializer)?;
115 if s.is_empty() {
116 return Err(serde::de::Error::custom(
117 "Schema can not be empty".to_string(),
118 ));
119 }
120
121 Ok(match s.as_str() {
122 "governance" => SchemaType::Governance,
123 "all_schemas" => SchemaType::AllSchemas,
124 _ => SchemaType::Type(s),
125 })
126 }
127}
128
129impl Serialize for SchemaType {
130 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
131 where
132 S: Serializer,
133 {
134 match self {
135 SchemaType::AllSchemas => serializer.serialize_str("all_schemas"),
136 SchemaType::Governance => serializer.serialize_str("governance"),
137 SchemaType::Type(schema) => serializer.serialize_str(schema),
138 }
139 }
140}