gix_odb/store_impls/loose/
iter.rs1use gix_features::fs;
2
3use crate::store_impls::loose;
4
5pub type Error = gix_features::fs::walkdir::Error;
7
8impl loose::Iter {
9 fn path_to_id(
10 &self,
11 res: Result<fs::walkdir::DirEntry, fs::walkdir::Error>,
12 ) -> Option<Result<gix_hash::ObjectId, Error>> {
13 use std::path::Component::Normal;
14
15 match res {
16 Ok(e) => {
17 let p = e.path();
18 let mut ci = p.components();
19 let (c2, c1) = (ci.next_back(), ci.next_back());
20 if let (Some(Normal(c1)), Some(Normal(c2))) = (c1, c2) {
21 if c1.len() == 2 && c2.len() == self.hash_hex_len - 2 {
22 if let (Some(c1), Some(c2)) = (c1.to_str(), c2.to_str()) {
23 let mut buf = gix_hash::Kind::hex_buf();
24 {
25 let (first_byte, rest) = buf[..self.hash_hex_len].split_at_mut(2);
26 first_byte.copy_from_slice(c1.as_bytes());
27 rest.copy_from_slice(c2.as_bytes());
28 }
29 if let Ok(b) = gix_hash::ObjectId::from_hex(&buf[..self.hash_hex_len]) {
30 return Some(Ok(b));
31 }
32 }
33 }
34 }
35 }
36 Err(err) => return Some(Err(err)),
37 };
38 None
39 }
40}
41
42impl Iterator for loose::Iter {
43 type Item = Result<gix_hash::ObjectId, Error>;
44
45 fn next(&mut self) -> Option<Self::Item> {
46 while let Some(res) = self.inner.next() {
47 if let Some(res) = self.path_to_id(res) {
48 return Some(res);
49 }
50 }
51 None
52 }
53}
54
55impl loose::Store {
57 pub fn iter(&self) -> loose::Iter {
67 loose::Iter {
68 inner: fs::walkdir_new(
69 &self.path,
70 fs::walkdir::Parallelism::ThreadPoolPerTraversal {
71 thread_name: "gix_odb::loose::Store::iter: fs-walk",
72 },
73 false,
74 )
75 .min_depth(2)
76 .max_depth(3)
77 .follow_links(false)
78 .into_iter(),
79 hash_hex_len: self.object_hash.len_in_hex(),
80 }
81 }
82}