use std::collections::BTreeSet;
use derive_more::From;
use itertools::Itertools;
use reqwest::Url;
use super::core::Subdomain;
#[derive(Clone, Debug, From)]
#[from(&str)]
pub struct SearchQueryParam(String);
#[allow(clippy::to_string_trait_impl)]
impl ToString for SearchQueryParam {
fn to_string(&self) -> String {
self.0.clone()
}
}
impl SearchQueryParam {
pub fn to_search_query(&self, domain: &str, prefix: &str) -> SearchQuery {
SearchQuery::new(self.clone(), prefix, domain)
}
}
#[derive(Debug)]
pub struct SearchQuery {
pub param: SearchQueryParam,
pub prefix: String,
pub domain: String,
pub state: BTreeSet<String>,
}
impl SearchQuery {
pub fn new(param: SearchQueryParam, prefix: &str, domain: &str) -> Self {
Self {
param,
prefix: prefix.to_string(),
domain: domain.to_string(),
state: BTreeSet::new(),
}
}
pub fn update(&mut self, sub: Subdomain) -> bool {
let formatted = format!(".{}", self.domain);
if let Some(stripped) = sub.strip_suffix(&formatted) {
self.state.insert(format!("-{}", stripped.trim()))
} else {
false
}
}
pub fn update_many(&mut self, subs: BTreeSet<Subdomain>) -> bool {
let filter_stmt = |item: &&String| self.update(item.to_string());
subs.iter().filter(filter_stmt).count() > 0
}
pub fn as_search_str(&mut self) -> String {
let suffix = self.state.iter().join(" ");
if suffix.is_empty() {
format!("{}{}", self.prefix, self.domain)
} else {
format!("{}{} {}", self.prefix, self.domain, suffix.trim())
}
}
pub fn as_url(&mut self, base_url: Url, extra_params: &[(String, String)]) -> Url {
let query_param = &[(self.param.to_string(), self.as_search_str())];
let params = [extra_params, query_param].concat();
Url::parse_with_params(base_url.as_ref(), params).expect("URL parse error!")
}
}