paginator_utils/
search.rs1use serde::{Deserialize, Serialize};
2
3#[derive(Clone, Debug, Serialize, Deserialize, PartialEq)]
4pub struct SearchParams {
5 pub query: String,
6 pub fields: Vec<String>,
7 #[serde(default)]
8 pub case_sensitive: bool,
9 #[serde(default)]
10 pub exact_match: bool,
11}
12
13impl SearchParams {
14 pub fn new(query: impl Into<String>, fields: Vec<String>) -> Self {
15 Self {
16 query: query.into(),
17 fields,
18 case_sensitive: false,
19 exact_match: false,
20 }
21 }
22
23 pub fn with_case_sensitive(mut self, sensitive: bool) -> Self {
24 self.case_sensitive = sensitive;
25 self
26 }
27
28 pub fn with_exact_match(mut self, exact: bool) -> Self {
29 self.exact_match = exact;
30 self
31 }
32
33 pub fn to_sql_where(&self) -> String {
34 let pattern = if self.exact_match {
35 format!("'{}'", self.query.replace('\'', "''"))
36 } else {
37 format!("'%{}%'", self.query.replace('\'', "''"))
38 };
39
40 let operator = if self.case_sensitive { "LIKE" } else { "ILIKE" };
41
42 let conditions: Vec<String> = self
43 .fields
44 .iter()
45 .map(|field| {
46 if self.case_sensitive || operator == "ILIKE" {
47 format!("{} {} {}", field, operator, pattern)
48 } else {
49 format!("LOWER({}) LIKE LOWER({})", field, pattern)
50 }
51 })
52 .collect();
53
54 format!("({})", conditions.join(" OR "))
55 }
56}