noxu_db/
database_entry.rs1use bytes::Bytes;
5
6#[derive(Debug, Clone, PartialEq, Eq)]
17pub struct DatabaseEntry {
18 data: Option<Bytes>,
20 offset: usize,
22 size: usize,
24 partial: bool,
26 partial_offset: usize,
28 partial_length: usize,
30}
31
32impl DatabaseEntry {
33 pub fn new() -> Self {
35 Self {
36 data: None,
37 offset: 0,
38 size: 0,
39 partial: false,
40 partial_offset: 0,
41 partial_length: 0,
42 }
43 }
44
45 pub fn from_bytes(data: &[u8]) -> Self {
49 Self {
50 data: Some(Bytes::copy_from_slice(data)),
51 offset: 0,
52 size: data.len(),
53 partial: false,
54 partial_offset: 0,
55 partial_length: 0,
56 }
57 }
58
59 pub fn from_vec(data: Vec<u8>) -> Self {
61 let size = data.len();
62 Self {
63 data: Some(Bytes::from(data)),
64 offset: 0,
65 size,
66 partial: false,
67 partial_offset: 0,
68 partial_length: 0,
69 }
70 }
71
72 pub fn from_bytes_ref(data: Bytes) -> Self {
74 let size = data.len();
75 Self {
76 data: Some(data),
77 offset: 0,
78 size,
79 partial: false,
80 partial_offset: 0,
81 partial_length: 0,
82 }
83 }
84
85 pub fn data_opt(&self) -> Option<&[u8]> {
92 self.data.as_ref().map(|d| {
93 let start = self.offset.min(d.len());
94 let end = (self.offset + self.size).min(d.len());
95 &d[start..end]
96 })
97 }
98
99 pub fn set_data(&mut self, data: &[u8]) {
101 self.data = Some(Bytes::copy_from_slice(data));
102 self.offset = 0;
103 self.size = data.len();
104 }
105
106 pub fn set_data_vec(&mut self, data: Vec<u8>) {
108 self.size = data.len();
109 self.data = Some(Bytes::from(data));
110 self.offset = 0;
111 }
112
113 pub fn set_data_bytes(&mut self, data: Bytes) {
115 self.size = data.len();
116 self.data = Some(data);
117 self.offset = 0;
118 }
119
120 pub fn from_data(data: &[u8]) -> Self {
124 Self::from_bytes(data)
125 }
126
127 pub fn data(&self) -> &[u8] {
131 self.data_opt().unwrap_or(&[])
132 }
133
134 pub fn len(&self) -> usize {
136 self.size
137 }
138
139 pub fn set_offset(&mut self, offset: usize) {
141 self.offset = offset;
142 }
143
144 pub fn offset(&self) -> usize {
146 self.offset
147 }
148
149 pub fn set_size(&mut self, size: usize) {
151 self.size = size;
152 }
153
154 pub fn set_partial(&mut self, offset: usize, length: usize, partial: bool) {
158 self.partial = partial;
159 self.partial_offset = offset;
160 self.partial_length = length;
161 }
162
163 pub fn is_partial(&self) -> bool {
165 self.partial
166 }
167
168 pub fn partial_offset(&self) -> usize {
170 self.partial_offset
171 }
172
173 pub fn partial_length(&self) -> usize {
175 self.partial_length
176 }
177
178 pub fn clear(&mut self) {
180 self.data = None;
181 self.offset = 0;
182 self.size = 0;
183 self.partial = false;
184 self.partial_offset = 0;
185 self.partial_length = 0;
186 }
187
188 pub fn is_empty(&self) -> bool {
190 self.data.is_none() || self.size == 0
191 }
192}
193
194impl Default for DatabaseEntry {
195 fn default() -> Self {
196 Self::new()
197 }
198}
199
200impl From<Vec<u8>> for DatabaseEntry {
201 fn from(data: Vec<u8>) -> Self {
202 Self::from_vec(data)
203 }
204}
205
206impl From<Bytes> for DatabaseEntry {
207 fn from(data: Bytes) -> Self {
208 Self::from_bytes_ref(data)
209 }
210}
211
212impl From<&[u8]> for DatabaseEntry {
213 fn from(data: &[u8]) -> Self {
214 Self::from_bytes(data)
215 }
216}
217
218impl From<String> for DatabaseEntry {
219 fn from(s: String) -> Self {
220 Self::from_vec(s.into_bytes())
221 }
222}
223
224impl From<&str> for DatabaseEntry {
225 fn from(s: &str) -> Self {
226 Self::from_bytes(s.as_bytes())
227 }
228}
229
230impl AsRef<[u8]> for DatabaseEntry {
234 fn as_ref(&self) -> &[u8] {
235 self.data()
236 }
237}
238
239#[cfg(test)]
240mod tests {
241 use super::*;
242
243 #[test]
244 fn test_new_empty() {
245 let entry = DatabaseEntry::new();
246 assert!(entry.is_empty());
247 assert_eq!(entry.len(), 0);
248 assert_eq!(entry.data_opt(), None);
249 }
250
251 #[test]
252 fn test_from_bytes() {
253 let data = b"hello";
254 let entry = DatabaseEntry::from_bytes(data);
255 assert!(!entry.is_empty());
256 assert_eq!(entry.len(), 5);
257 assert_eq!(entry.data_opt(), Some(&data[..]));
258 }
259
260 #[test]
261 fn test_from_vec() {
262 let data = vec![1, 2, 3, 4, 5];
263 let entry = DatabaseEntry::from_vec(data.clone());
264 assert_eq!(entry.len(), 5);
265 assert_eq!(entry.data_opt(), Some(&data[..]));
266 }
267
268 #[test]
269 fn test_set_data() {
270 let mut entry = DatabaseEntry::new();
271 entry.set_data(b"test");
272 assert_eq!(entry.len(), 4);
273 assert_eq!(entry.data_opt(), Some(b"test".as_ref()));
274 }
275
276 #[test]
277 fn test_set_data_vec() {
278 let mut entry = DatabaseEntry::new();
279 let data = vec![10, 20, 30];
280 entry.set_data_vec(data.clone());
281 assert_eq!(entry.len(), 3);
282 assert_eq!(entry.data_opt(), Some(&data[..]));
283 }
284
285 #[test]
286 fn test_offset_and_size() {
287 let mut entry = DatabaseEntry::from_bytes(b"hello world");
288 entry.set_offset(6);
289 entry.set_size(5);
290 assert_eq!(entry.data_opt(), Some(b"world".as_ref()));
291 }
292
293 #[test]
294 fn test_partial_entry() {
295 let mut entry = DatabaseEntry::new();
296 assert!(!entry.is_partial());
297
298 entry.set_partial(10, 20, true);
299 assert!(entry.is_partial());
300 assert_eq!(entry.partial_offset(), 10);
301 assert_eq!(entry.partial_length(), 20);
302
303 entry.set_partial(0, 0, false);
304 assert!(!entry.is_partial());
305 }
306
307 #[test]
308 fn test_clear() {
309 let mut entry = DatabaseEntry::from_bytes(b"data");
310 assert!(!entry.is_empty());
311
312 entry.clear();
313 assert!(entry.is_empty());
314 assert_eq!(entry.len(), 0);
315 assert_eq!(entry.data_opt(), None);
316 }
317
318 #[test]
319 fn test_default() {
320 let entry = DatabaseEntry::default();
321 assert!(entry.is_empty());
322 assert_eq!(entry.len(), 0);
323 }
324
325 #[test]
326 fn test_from_string() {
327 let entry = DatabaseEntry::from(String::from("test"));
328 assert_eq!(entry.data_opt(), Some(b"test".as_ref()));
329 }
330
331 #[test]
332 fn test_from_str() {
333 let entry = DatabaseEntry::from("hello");
334 assert_eq!(entry.data_opt(), Some(b"hello".as_ref()));
335 }
336
337 #[test]
338 fn test_clone() {
339 let entry1 = DatabaseEntry::from_bytes(b"original");
340 let entry2 = entry1.clone();
341 assert_eq!(entry1.data_opt(), entry2.data_opt());
342 }
343
344 #[test]
345 fn test_equality() {
346 let entry1 = DatabaseEntry::from_bytes(b"data");
347 let entry2 = DatabaseEntry::from_bytes(b"data");
348 let entry3 = DatabaseEntry::from_bytes(b"other");
349 assert_eq!(entry1, entry2);
350 assert_ne!(entry1, entry3);
351 }
352
353 #[test]
354 fn test_empty_slice() {
355 let entry = DatabaseEntry::from_bytes(b"");
356 assert!(entry.is_empty());
357 assert_eq!(entry.len(), 0);
358 }
359
360 #[test]
361 fn test_offset_beyond_data() {
362 let mut entry = DatabaseEntry::from_bytes(b"short");
363 entry.set_offset(10);
364 entry.set_size(5);
365 assert_eq!(entry.data_opt(), Some(&[][..]));
367 }
368
369 #[test]
370 fn test_size_beyond_data() {
371 let mut entry = DatabaseEntry::from_bytes(b"test");
372 entry.set_size(100);
373 assert_eq!(entry.data_opt(), Some(b"test".as_ref()));
375 }
376}