1use bytes::Bytes;
2
3#[derive(Debug, Clone, Copy, Eq, PartialEq, Hash)]
5pub enum Op {
6 Get,
7 Gets,
8 Gat,
9 Gats,
10 Set,
11 Add,
12 Replace,
13 Append,
14 Prepend,
15 Cas,
16 Delete,
17 Incr,
18 Decr,
19 Touch,
20 Stats,
21 Version,
22 Quit,
23 MetaGet,
24 MetaSet,
25 MetaDelete,
26 MetaArithmetic,
27 MetaDebug,
28 MetaNoop,
29 Noop,
30 Unknown,
31}
32
33#[derive(Debug, Clone, Copy, Eq, PartialEq)]
35pub enum Protocol {
36 Ascii,
37 Meta,
38 Binary,
39}
40
41#[derive(Debug, Clone, Copy, Eq, PartialEq)]
43pub enum ReplyMode {
44 Always,
46 SuppressSuccess,
48 SuppressMiss,
50 QuietBuffered,
52}
53
54#[derive(Debug, Clone)]
56pub struct Request {
57 pub op: Op,
58 pub key: Option<Bytes>,
59 pub keys: Vec<Bytes>,
60 pub value: Option<Bytes>,
61 pub flags: Option<u32>,
62 pub exptime: Option<i64>,
63 pub cas: Option<u64>,
64 pub delta: Option<u64>,
65 pub initial: Option<u64>,
66 pub meta: Option<MetaFlags>,
67}
68
69impl Request {
70 pub fn new(op: Op) -> Self {
71 Self {
72 op,
73 key: None,
74 keys: Vec::new(),
75 value: None,
76 flags: None,
77 exptime: None,
78 cas: None,
79 delta: None,
80 initial: None,
81 meta: None,
82 }
83 }
84}
85
86#[derive(Debug, Clone, Copy)]
88pub struct RequestMeta {
89 pub protocol: Protocol,
90 pub reply: ReplyMode,
91 pub opaque: Option<u32>,
92 pub return_key: bool,
93 pub opcode: u8,
94}
95
96impl RequestMeta {
97 pub fn ascii() -> Self {
98 Self {
99 protocol: Protocol::Ascii,
100 reply: ReplyMode::Always,
101 opaque: None,
102 return_key: false,
103 opcode: 0,
104 }
105 }
106}
107
108#[derive(Debug, Clone)]
110pub struct MetaFlags {
111 pub ordered: Vec<MetaFlag>,
112 pub mask: u64,
113}
114
115impl MetaFlags {
116 pub fn new(ordered: Vec<MetaFlag>) -> Self {
117 let mut mask = 0u64;
118 for flag in &ordered {
119 if let Some(bit) = flag_bit(flag.code) {
120 mask |= 1u64 << bit;
121 }
122 }
123 Self { ordered, mask }
124 }
125
126 pub fn has(&self, code: u8) -> bool {
127 if let Some(bit) = flag_bit(code)
128 && (self.mask & (1u64 << bit)) != 0
129 {
130 return true;
131 }
132 self.ordered.iter().any(|flag| flag.code == code)
133 }
134
135 pub fn token(&self, code: u8) -> Option<&Bytes> {
136 self.ordered
137 .iter()
138 .find(|flag| flag.code == code)
139 .and_then(|flag| flag.token.as_ref())
140 }
141}
142
143fn flag_bit(code: u8) -> Option<u64> {
144 match code {
145 b'a'..=b'z' => Some((code - b'a') as u64),
146 b'A'..=b'Z' => Some((26 + (code - b'A')) as u64),
147 b'0'..=b'9' => Some((52 + (code - b'0')) as u64),
148 _ => None,
149 }
150}
151
152#[derive(Debug, Clone)]
154pub struct MetaFlag {
155 pub code: u8,
156 pub token: Option<Bytes>,
157}
158
159#[derive(Debug, Clone, Copy, Eq, PartialEq)]
161pub enum MetaCode {
162 Hd,
163 Va,
164 En,
165 Ns,
166 Ex,
167 Nf,
168}
169
170impl MetaCode {
171 pub fn as_bytes(self) -> &'static [u8] {
172 match self {
173 MetaCode::Hd => b"HD",
174 MetaCode::Va => b"VA",
175 MetaCode::En => b"EN",
176 MetaCode::Ns => b"NS",
177 MetaCode::Ex => b"EX",
178 MetaCode::Nf => b"NF",
179 }
180 }
181
182 pub fn is_success(self) -> bool {
183 matches!(self, MetaCode::Hd | MetaCode::Va)
184 }
185
186 pub fn is_miss(self) -> bool {
187 matches!(self, MetaCode::En)
188 }
189}
190
191#[derive(Debug, Clone)]
193pub struct MetaResponse {
194 pub code: MetaCode,
195 pub value: Option<Bytes>,
196 pub cas: Option<u64>,
197 pub flags: Option<u32>,
198 pub ttl: Option<i64>,
199 pub size: Option<usize>,
200 pub hit: Option<bool>,
201 pub last_access: Option<u64>,
202 pub extra: MetaExtra,
203}
204
205impl MetaResponse {
206 pub fn new(code: MetaCode) -> Self {
207 Self {
208 code,
209 value: None,
210 cas: None,
211 flags: None,
212 ttl: None,
213 size: None,
214 hit: None,
215 last_access: None,
216 extra: MetaExtra::default(),
217 }
218 }
219}
220
221#[derive(Debug, Clone, Default)]
223pub struct MetaExtra {
224 pub won: Option<WinState>,
225 pub stale: bool,
226}
227
228#[derive(Debug, Clone, Copy, Eq, PartialEq)]
229pub enum WinState {
230 Won,
231 AlreadyWon,
232}
233
234#[derive(Debug, Clone)]
236pub struct ValueEntry {
237 pub key: Bytes,
238 pub value: Bytes,
239 pub flags: u32,
240 pub cas: Option<u64>,
241}
242
243#[derive(Debug, Clone)]
245pub struct StatLine {
246 pub key: Bytes,
247 pub value: Bytes,
248}
249
250pub trait ValuesStream {
252 fn next(&mut self) -> Option<ValueEntry>;
253}
254
255pub trait StatsStream {
257 fn next(&mut self) -> Option<StatLine>;
258}