avalanche_types/choices/
status.rs1use crate::{errors, packer::Packer};
3use bytes::Bytes;
4use serde::{Deserialize, Serialize};
5
6#[derive(
10 Deserialize,
11 Serialize,
12 std::clone::Clone,
13 std::cmp::Eq,
14 std::cmp::Ord,
15 std::cmp::PartialEq,
16 std::cmp::PartialOrd,
17 std::fmt::Debug,
18 std::hash::Hash,
19)]
20pub enum Status {
21 Processing,
23
24 Rejected,
26
27 Accepted,
29
30 Unknown(String),
32}
33
34impl Default for Status {
35 fn default() -> Self {
36 Status::Unknown("default".to_owned())
37 }
38}
39
40impl std::convert::From<&str> for Status {
41 fn from(s: &str) -> Self {
42 match s {
43 "Processing" => Status::Processing,
44 "Rejected" => Status::Rejected,
45 "Accepted" => Status::Accepted,
46 other => Status::Unknown(other.to_owned()),
47 }
48 }
49}
50
51impl std::str::FromStr for Status {
52 type Err = std::convert::Infallible;
53
54 fn from_str(s: &str) -> std::result::Result<Self, Self::Err> {
55 Ok(Status::from(s))
56 }
57}
58
59impl std::fmt::Display for Status {
63 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
64 write!(f, "{}", self.as_str())
65 }
66}
67
68impl Status {
69 pub fn as_str(&self) -> &str {
70 match self {
71 Status::Processing => "Processing",
72 Status::Rejected => "Rejected",
73 Status::Accepted => "Accepted",
74 Status::Unknown(s) => s.as_ref(),
75 }
76 }
77
78 pub fn values() -> &'static [&'static str] {
80 &["Processing", "Rejected", "Accepted"]
81 }
82
83 pub fn decided(&self) -> bool {
85 matches!(self, Status::Rejected | Status::Accepted)
86 }
87
88 pub fn fetched(&self) -> bool {
90 match self {
91 Status::Processing => true,
92 _ => self.decided(),
93 }
94 }
95
96 pub fn bytes(&self) -> errors::Result<Bytes> {
98 let iota = match self {
99 Status::Processing => 1_u32,
100 Status::Rejected => 2_u32,
101 Status::Accepted => 3_u32,
102 Status::Unknown(_) => 0_u32,
103 };
104
105 let packer = Packer::new(4, 4);
106 packer.pack_u32(iota)?;
107 Ok(packer.take_bytes())
108 }
109
110 pub fn to_u32(&self) -> u32 {
112 match self {
113 Status::Processing => 1,
114 Status::Rejected => 2,
115 Status::Accepted => 3,
116 Status::Unknown(_) => 0,
117 }
118 }
119
120 pub fn to_i32(&self) -> i32 {
122 match self {
123 Status::Processing => 1,
124 Status::Rejected => 2,
125 Status::Accepted => 3,
126 Status::Unknown(_) => 0,
127 }
128 }
129
130 pub fn u32_from_slice(bytes: &[u8]) -> u32 {
132 assert!(bytes.len() <= 4);
133 let d: [u8; 4] = bytes.try_into().unwrap();
134 u32::from_ne_bytes(d)
135 }
136}
137
138impl AsRef<str> for Status {
139 fn as_ref(&self) -> &str {
140 self.as_str()
141 }
142}
143
144#[test]
146fn test_bytes() {
147 let sb = Status::Processing.bytes().unwrap().to_vec();
148 assert!(cmp_manager::eq_vectors(&sb, &[0x00, 0x00, 0x00, 0x01]));
149
150 let sb = Status::Rejected.bytes().unwrap().to_vec();
151 assert!(cmp_manager::eq_vectors(&sb, &[0x00, 0x00, 0x00, 0x02]));
152
153 let sb = Status::Accepted.bytes().unwrap().to_vec();
154 assert!(cmp_manager::eq_vectors(&sb, &[0x00, 0x00, 0x00, 0x03]));
155
156 let sb = Status::Unknown("()".to_string()).bytes().unwrap().to_vec();
157 assert!(cmp_manager::eq_vectors(&sb, &[0x00, 0x00, 0x00, 0x00]));
158}
159
160#[test]
162fn test_to_u32() {
163 assert_eq!(Status::Unknown("hello".to_string()).to_u32(), 0);
164 assert_eq!(Status::Processing.to_u32(), 1);
165 assert_eq!(Status::Rejected.to_u32(), 2);
166 assert_eq!(Status::Accepted.to_u32(), 3);
167}