nvrim/diagnostics/filters/
buffer.rs1use crate::diagnostics::filters::BufferWithPath;
8
9pub trait BufferFilter {
14 fn blacklisted_buf_paths(&self) -> &[&str];
19
20 fn blacklisted_buf_types(&self) -> &[&str];
25
26 fn skip_diagnostic(&self, buffer_with_path: &BufferWithPath) -> nvim_oxi::Result<bool> {
31 if self
32 .blacklisted_buf_paths()
33 .iter()
34 .any(|bp| buffer_with_path.path.contains(bp))
35 {
36 return Ok(true);
37 }
38 let Some(buf_type) = buffer_with_path.buffer.get_buf_type() else {
39 return Ok(false);
40 };
41 Ok(self.blacklisted_buf_types().contains(&buf_type.as_str()))
42 }
43}
44
45pub struct BufferFilterImpl;
46
47impl BufferFilter for BufferFilterImpl {
48 fn blacklisted_buf_paths(&self) -> &[&str] {
49 &[".cargo"]
50 }
51
52 fn blacklisted_buf_types(&self) -> &[&str] {
53 &["nofile", "grug-far"]
54 }
55}
56
57#[cfg(test)]
58mod tests {
59 use rstest::rstest;
60 use ytil_noxi::buffer::mock::MockBuffer;
61
62 use super::*;
63
64 #[rstest]
65 #[case::path_contains_blacklisted_substring(
66 &[".cargo"],
67 &[],
68 "/home/user/.cargo/registry/src/index.crates.io/crate.tar.gz",
69 "",
70 true
71 )]
72 #[case::path_not_blacklisted_and_buf_type_not_blacklisted(
73 &[".cargo"],
74 &["nofile"],
75 "/home/user/src/main.rs",
76 "",
77 false
78 )]
79 #[case::path_not_blacklisted_but_buf_type_is_blacklisted(
80 &[".cargo"],
81 &["nofile"],
82 "/home/user/src/main.rs",
83 "nofile",
84 true
85 )]
86 #[case::multiple_blacklisted_paths_and_types(
87 &[".cargo", "target"],
88 &["nofile", "grug-far"],
89 "/home/user/target/debug/main",
90 "",
91 true
92 )]
93 #[case::no_blacklists_configured(
94 &[],
95 &[],
96 "/home/user/src/main.rs",
97 "normal",
98 false
99 )]
100 #[case::path_exactly_matches_blacklisted_substring(
101 &[".cargo"],
102 &[],
103 ".cargo",
104 "",
105 true
106 )]
107 #[case::path_contains_multiple_occurrences_of_blacklisted_substring(
108 &["target"],
109 &[],
110 "/target/debug/target/release/target",
111 "",
112 true
113 )]
114 #[case::empty_path(
115 &[".cargo"],
116 &["nofile"],
117 "",
118 "",
119 false
120 )]
121 #[case::unicode_path_containing_blacklisted_substring(
122 &[".cargo"],
123 &[],
124 "/home/user/📁/.cargo/registry/🚀.tar.gz",
125 "",
126 true
127 )]
128 #[case::both_path_and_buffer_type_are_blacklisted(
129 &[".cargo"],
130 &["nofile"],
131 "/home/user/.cargo/main.rs",
132 "nofile",
133 true
134 )]
135 fn skip_diagnostic_works_as_expected(
136 #[case] blacklisted_paths: &[&str],
137 #[case] blacklisted_types: &[&str],
138 #[case] buffer_path: &str,
139 #[case] buffer_type: &str,
140 #[case] expected: bool,
141 ) {
142 let filter = TestBufferFilter::new(blacklisted_paths, blacklisted_types);
143 let buffer_with_path = create_buffer_with_path(buffer_path, buffer_type);
144
145 assert2::let_assert!(Ok(result) = filter.skip_diagnostic(&buffer_with_path));
146 pretty_assertions::assert_eq!(result, expected);
147 }
148
149 struct TestBufferFilter<'a> {
151 blacklisted_paths: &'a [&'a str],
152 blacklisted_types: &'a [&'a str],
153 }
154
155 impl<'a> TestBufferFilter<'a> {
156 fn new(blacklisted_paths: &'a [&'a str], blacklisted_types: &'a [&'a str]) -> Self {
157 Self {
158 blacklisted_paths,
159 blacklisted_types,
160 }
161 }
162 }
163
164 impl BufferFilter for TestBufferFilter<'_> {
165 fn blacklisted_buf_paths(&self) -> &[&str] {
166 self.blacklisted_paths
167 }
168
169 fn blacklisted_buf_types(&self) -> &[&str] {
170 self.blacklisted_types
171 }
172 }
173
174 fn create_buffer_with_path(path: &str, buf_type: &str) -> BufferWithPath {
175 BufferWithPath {
176 buffer: Box::new(MockBuffer::with_buf_type(vec![], buf_type)),
177 path: path.to_string(),
178 }
179 }
180}