summa_core/configs/
core.rs

1use std::collections::HashMap;
2use std::default::Default;
3
4use serde::{Deserialize, Serialize};
5use summa_proto::proto;
6use summa_proto::proto::IndexEngineConfig;
7
8use crate::errors::{BuilderError, SummaResult, ValidationError};
9
10fn return_1() -> usize {
11    1
12}
13fn return_100() -> usize {
14    100
15}
16
17#[derive(Clone, Debug, Serialize, Deserialize)]
18#[serde(rename_all = "snake_case")]
19pub enum WriterThreads {
20    SameThread,
21    N(u64),
22}
23
24impl WriterThreads {
25    pub fn threads(&self) -> u64 {
26        match self {
27            WriterThreads::SameThread => 0,
28            WriterThreads::N(n) => *n,
29        }
30    }
31}
32
33#[derive(Builder, Clone, Debug, Serialize, Deserialize)]
34#[builder(default, build_fn(error = "BuilderError"))]
35pub struct CollectorCacheConfig {
36    #[builder(default = "Some(120000)")]
37    pub ttl_interval_ms: Option<u64>,
38    #[builder(default = "128")]
39    pub size: usize,
40}
41
42impl Default for CollectorCacheConfig {
43    fn default() -> Self {
44        CollectorCacheConfig {
45            ttl_interval_ms: Some(120000),
46            size: 128,
47        }
48    }
49}
50
51#[derive(Builder, Clone, Debug, Serialize, Deserialize)]
52#[builder(default, build_fn(error = "BuilderError"))]
53pub struct Config {
54    #[serde(default = "HashMap::new")]
55    pub aliases: HashMap<String, String>,
56    #[builder(default = "None")]
57    pub autocommit_interval_ms: Option<u64>,
58    #[builder(default = "CollectorCacheConfig::default()")]
59    #[serde(default = "CollectorCacheConfig::default")]
60    pub collector_cache: CollectorCacheConfig,
61    #[builder(default = "1")]
62    #[serde(default = "return_1")]
63    pub doc_store_compress_threads: usize,
64    #[builder(default = "100")]
65    #[serde(default = "return_100")]
66    pub doc_store_cache_num_blocks: usize,
67    #[serde(default = "HashMap::new")]
68    pub indices: HashMap<String, IndexEngineConfig>,
69    #[builder(default = "1024 * 1024 * 1024")]
70    pub writer_heap_size_bytes: u64,
71    #[builder(default = "Some(WriterThreads::N(1))")]
72    pub writer_threads: Option<WriterThreads>,
73}
74
75impl Default for Config {
76    fn default() -> Self {
77        Config {
78            aliases: HashMap::new(),
79            autocommit_interval_ms: None,
80            collector_cache: CollectorCacheConfig::default(),
81            doc_store_compress_threads: 1,
82            indices: HashMap::new(),
83            writer_heap_size_bytes: 1024 * 1024 * 1024,
84            writer_threads: Some(WriterThreads::N(1)),
85            doc_store_cache_num_blocks: 100,
86        }
87    }
88}
89
90impl Config {
91    /// Copy aliases for the index
92    pub fn get_index_aliases_for_index(&self, index_name: &str) -> Vec<String> {
93        self.aliases
94            .iter()
95            .filter(|(_, v)| *v == index_name)
96            .map(|(k, _)| k.clone())
97            .collect::<Vec<String>>()
98    }
99
100    /// Find index by alias
101    pub fn resolve_index_alias(&self, alias: &str) -> Option<String> {
102        self.aliases.get(alias).cloned()
103    }
104
105    /// Set new alias for index
106    pub fn set_index_alias(&mut self, alias: &str, index_name: &str) -> SummaResult<Option<String>> {
107        if alias.is_empty() {
108            return Err(ValidationError::EmptyArgument("alias".to_owned()).into());
109        }
110        if index_name.is_empty() {
111            return Err(ValidationError::EmptyArgument("index_name".to_owned()).into());
112        }
113        if !self.indices.contains_key(index_name) {
114            return Err(ValidationError::MissingIndex(index_name.to_owned()).into());
115        }
116        Ok(self.aliases.insert(alias.to_owned(), index_name.to_owned()))
117    }
118
119    /// Delete all aliases listed in `index_aliases`
120    pub fn delete_index_aliases(&mut self, index_aliases: &Vec<String>) {
121        for alias in index_aliases {
122            self.aliases.remove(alias);
123        }
124    }
125}
126
127#[derive(Debug, Clone)]
128pub struct QueryParserConfig(pub proto::QueryParserConfig);
129impl QueryParserConfig {
130    pub fn from_default_fields(default_fields: Vec<String>) -> Self {
131        QueryParserConfig(proto::QueryParserConfig {
132            default_fields,
133            ..Default::default()
134        })
135    }
136    pub fn term_limit(&self) -> usize {
137        if self.0.term_limit > 0 {
138            self.0.term_limit as usize
139        } else {
140            16
141        }
142    }
143    pub fn merge(&mut self, other: Self) {
144        if !other.0.default_fields.is_empty() {
145            self.0.default_fields = other.0.default_fields;
146        }
147        self.0.field_aliases.extend(other.0.field_aliases);
148        self.0.term_field_mapper_configs.extend(other.0.term_field_mapper_configs);
149        self.0.field_boosts.extend(other.0.field_boosts);
150        self.0.morphology_configs.extend(other.0.morphology_configs);
151        if other.0.term_limit > 0 {
152            self.0.term_limit = other.0.term_limit;
153        }
154        if let Some(exact_matches_promoter) = other.0.exact_matches_promoter {
155            self.0.exact_matches_promoter = Some(exact_matches_promoter)
156        }
157        if let Some(default_mode) = other.0.default_mode {
158            self.0.default_mode = Some(default_mode)
159        }
160        if let Some(query_language) = other.0.query_language {
161            self.0.query_language = Some(query_language)
162        }
163    }
164}