1#[repr(u8)]
16#[derive(Debug, Clone, Copy, PartialEq, Eq)]
17pub enum Durability {
18 Sync = 0x01,
21 Batched = 0x02,
26 Buffered = 0x03,
28}
29
30impl From<Durability> for u8 {
31 fn from(d: Durability) -> u8 {
33 d as u8
34 }
35}
36
37impl std::fmt::Display for Durability {
38 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
39 let s = match self {
40 Durability::Sync => "sync",
41 Durability::Batched => "batched",
42 Durability::Buffered => "buffered",
43 };
44 write!(f, "{s}")
45 }
46}
47
48#[derive(Debug, Clone, Copy, PartialEq, Eq)]
51pub struct UnknownDurability(pub u8);
52
53impl std::fmt::Display for UnknownDurability {
54 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
55 write!(f, "unknown durability byte: {:#04x}", self.0)
56 }
57}
58
59impl std::error::Error for UnknownDurability {}
60
61impl TryFrom<u8> for Durability {
62 type Error = UnknownDurability;
63
64 fn try_from(value: u8) -> Result<Self, Self::Error> {
65 match value {
66 0x01 => Ok(Durability::Sync),
67 0x02 => Ok(Durability::Batched),
68 0x03 => Ok(Durability::Buffered),
69 v => Err(UnknownDurability(v)),
70 }
71 }
72}
73
74#[cfg(test)]
75mod tests {
76 use super::*;
77
78 #[test]
79 fn try_from_accepts_known_values() {
80 assert_eq!(Durability::try_from(0x01).unwrap(), Durability::Sync);
81 assert_eq!(Durability::try_from(0x02).unwrap(), Durability::Batched);
82 assert_eq!(Durability::try_from(0x03).unwrap(), Durability::Buffered);
83 }
84
85 #[test]
86 fn from_for_u8_round_trips_and_display() {
87 for d in [Durability::Sync, Durability::Batched, Durability::Buffered] {
88 assert_eq!(Durability::try_from(u8::from(d)).unwrap(), d);
89 }
90 assert_eq!(Durability::Sync.to_string(), "sync");
91 assert_eq!(Durability::Buffered.to_string(), "buffered");
92 }
93
94 #[test]
95 fn try_from_rejects_unknown_values() {
96 assert!(Durability::try_from(0x00).is_err());
97 assert!(Durability::try_from(0x04).is_err());
98 assert!(Durability::try_from(0xff).is_err());
99 }
100
101 #[test]
102 fn unknown_durability_preserves_byte() {
103 let err = Durability::try_from(0xab).unwrap_err();
104 assert_eq!(err.0, 0xab);
105 }
106
107 #[test]
108 fn repr_values_match_wire() {
109 assert_eq!(Durability::Sync as u8, 0x01);
110 assert_eq!(Durability::Batched as u8, 0x02);
111 assert_eq!(Durability::Buffered as u8, 0x03);
112 }
113}