sift_core/search/emit/
stats.rs1use std::sync::atomic::{AtomicU64, AtomicUsize, Ordering};
2use std::time::Duration;
3
4use grep_printer::Stats as JsonStats;
5
6#[derive(Debug, Clone, Copy, Default, PartialEq, Eq)]
7pub struct SearchStats {
8 pub matches: usize,
9 pub files_with_matches: usize,
10 pub files_searched: usize,
11 pub bytes_printed: u64,
12 pub bytes_searched: u64,
13 pub elapsed: Duration,
14}
15
16impl SearchStats {
17 pub(crate) fn fill_from_json(
18 &mut self,
19 merged: &JsonStats,
20 candidates_len: usize,
21 bytes_searched_sum: u64,
22 elapsed: Duration,
23 summary_line_bytes: u64,
24 ) {
25 use std::convert::TryFrom;
26 self.matches = usize::try_from(merged.matches()).unwrap_or(usize::MAX);
27 self.files_with_matches =
28 usize::try_from(merged.searches_with_match()).unwrap_or(usize::MAX);
29 self.files_searched = candidates_len;
30 self.bytes_printed = merged.bytes_printed() + summary_line_bytes;
31 self.bytes_searched = bytes_searched_sum;
32 self.elapsed = elapsed;
33 }
34}
35
36#[derive(Debug)]
37pub struct TextStatsCounters {
38 primary: AtomicUsize,
39 files_with_matches: AtomicUsize,
40 bytes_printed: AtomicU64,
41 collect_stats: bool,
42}
43
44impl TextStatsCounters {
45 pub const fn new(collect_stats: bool) -> Self {
46 Self {
47 primary: AtomicUsize::new(0),
48 files_with_matches: AtomicUsize::new(0),
49 bytes_printed: AtomicU64::new(0),
50 collect_stats,
51 }
52 }
53
54 pub fn primary(&self) -> Option<&AtomicUsize> {
55 self.collect_stats.then_some(&self.primary)
56 }
57
58 pub fn files_with_matches(&self) -> Option<&AtomicUsize> {
59 self.collect_stats.then_some(&self.files_with_matches)
60 }
61
62 pub fn bytes_printed(&self) -> Option<&AtomicU64> {
63 self.collect_stats.then_some(&self.bytes_printed)
64 }
65
66 pub fn finish(
67 self,
68 candidates_len: usize,
69 bytes_searched: u64,
70 elapsed: Duration,
71 ) -> Option<SearchStats> {
72 if !self.collect_stats {
73 return None;
74 }
75 Some(SearchStats {
76 matches: self.primary.load(Ordering::Relaxed),
77 files_with_matches: self.files_with_matches.load(Ordering::Relaxed),
78 files_searched: candidates_len,
79 bytes_printed: self.bytes_printed.load(Ordering::Relaxed),
80 bytes_searched,
81 elapsed,
82 })
83 }
84}