1use nodedb_types::Surrogate;
9
10#[derive(
15 serde::Serialize,
16 serde::Deserialize,
17 zerompk::ToMessagePack,
18 zerompk::FromMessagePack,
19 Clone,
20 Debug,
21)]
22pub struct Posting {
23 pub doc_id: Surrogate,
24 pub term_freq: u32,
25 pub positions: Vec<u32>,
26}
27
28#[derive(Debug, Clone, Copy, Default, PartialEq, Eq)]
30#[non_exhaustive]
31pub enum QueryMode {
32 #[default]
34 And,
35 Or,
37}
38
39#[derive(Debug, Clone)]
41pub struct TextSearchResult {
42 pub doc_id: Surrogate,
43 pub score: f32,
44 pub fuzzy: bool,
46}
47
48#[derive(Debug, Clone, PartialEq, Eq)]
50pub struct MatchOffset {
51 pub start: usize,
52 pub end: usize,
53 pub term: String,
54}
55
56#[derive(Debug, Clone, Copy)]
58pub struct Bm25Params {
59 pub k1: f32,
61 pub b: f32,
63}
64
65impl Default for Bm25Params {
66 fn default() -> Self {
67 Self { k1: 1.2, b: 0.75 }
68 }
69}
70
71#[cfg(test)]
72mod tests {
73 use super::*;
74
75 #[test]
76 fn default_query_mode_is_and() {
77 assert_eq!(QueryMode::default(), QueryMode::And);
78 }
79
80 #[test]
81 fn default_bm25_params() {
82 let p = Bm25Params::default();
83 assert!((p.k1 - 1.2).abs() < f32::EPSILON);
84 assert!((p.b - 0.75).abs() < f32::EPSILON);
85 }
86
87 #[test]
88 fn posting_fields() {
89 let posting = Posting {
90 doc_id: Surrogate(1),
91 term_freq: 3,
92 positions: vec![0, 5, 12],
93 };
94 assert_eq!(posting.doc_id, Surrogate(1));
95 assert_eq!(posting.term_freq, 3);
96 assert_eq!(posting.positions, vec![0, 5, 12]);
97 }
98}