1use core::fmt;
8use core::str::FromStr;
9
10#[repr(u8)]
16#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, PartialOrd, Ord)]
17#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
18#[cfg_attr(feature = "serde", serde(rename_all = "snake_case"))]
19pub enum SubstrateKind {
20 Note = 0,
21 Entity = 1,
22 Event = 2,
23}
24
25pub const SUBSTRATE_COUNT: usize = 3;
27
28impl SubstrateKind {
29 pub const ALL: [SubstrateKind; SUBSTRATE_COUNT] = [
31 SubstrateKind::Note,
32 SubstrateKind::Entity,
33 SubstrateKind::Event,
34 ];
35
36 #[inline]
38 pub const fn name(self) -> &'static str {
39 match self {
40 Self::Note => "note",
41 Self::Entity => "entity",
42 Self::Event => "event",
43 }
44 }
45
46 #[inline]
48 pub const fn from_u8(v: u8) -> Option<Self> {
49 match v {
50 0 => Some(Self::Note),
51 1 => Some(Self::Entity),
52 2 => Some(Self::Event),
53 _ => None,
54 }
55 }
56}
57
58impl fmt::Display for SubstrateKind {
59 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
60 f.write_str(self.name())
61 }
62}
63
64const SUBSTRATE_KIND_VALID: &[&str] = &["note", "entity", "event"];
65
66impl FromStr for SubstrateKind {
67 type Err = crate::error::UnknownVariant;
68
69 fn from_str(s: &str) -> Result<Self, Self::Err> {
70 match s {
71 "note" | "Note" => Ok(Self::Note),
72 "entity" | "Entity" => Ok(Self::Entity),
73 "event" | "Event" => Ok(Self::Event),
74 other => Err(crate::error::UnknownVariant::new(
75 "substrate_kind",
76 other,
77 SUBSTRATE_KIND_VALID,
78 )),
79 }
80 }
81}
82
83#[cfg(test)]
84mod tests {
85 use super::*;
86
87 #[test]
88 fn all_variants() {
89 assert_eq!(SubstrateKind::ALL.len(), SUBSTRATE_COUNT);
90 for (i, &kind) in SubstrateKind::ALL.iter().enumerate() {
91 assert_eq!(kind as u8, i as u8);
92 assert_eq!(SubstrateKind::from_u8(i as u8), Some(kind));
93 }
94 }
95
96 #[test]
97 fn parse_roundtrip() {
98 for kind in SubstrateKind::ALL {
99 let parsed: SubstrateKind = kind.name().parse().unwrap();
100 assert_eq!(parsed, kind);
101 }
102 }
103
104 #[test]
105 fn out_of_range() {
106 assert_eq!(SubstrateKind::from_u8(3), None);
107 assert_eq!(SubstrateKind::from_u8(255), None);
108 }
109}