pub struct SearchEngine<P> { /* private fields */ }
Expand description
A SearchEngine is a wrapper around a collection of search indices that can process complex queries involving multiple indices.
It can also create queries from strings that are tailored to the existing indices.
§Example
A complete example can be found on the front page of this crate.
Implementations§
Source§impl<P: Eq + Hash + Clone> SearchEngine<P>
impl<P: Eq + Hash + Clone> SearchEngine<P>
Sourcepub fn new() -> Self
pub fn new() -> Self
Creates a new SearchEngine
.
§Example
use attribute_search_engine::SearchEngine;
let engine = SearchEngine::<usize>::new();
Sourcepub fn add_index<T: SearchIndex<P> + 'static>(&mut self, name: &str, index: T)
pub fn add_index<T: SearchIndex<P> + 'static>(&mut self, name: &str, index: T)
Add a new index to this search engine.
§Example
use attribute_search_engine::{SearchEngine, SearchIndexHashMap};
let mut index = SearchIndexHashMap::<_, String>::new();
// Fill index here...
let mut engine = SearchEngine::<usize>::new();
engine.add_index("attribute", index);
Sourcepub fn search(&self, query: &Query) -> Result<HashSet<P>>
pub fn search(&self, query: &Query) -> Result<HashSet<P>>
Run a query on the search engine.
The result is a HashSet of all row ids / primary ids with rows that matched the query.
Sourcepub fn query_from_str<'a>(
&self,
query_str: &'a str,
) -> Result<(Query, Vec<&'a str>)>
pub fn query_from_str<'a>( &self, query_str: &'a str, ) -> Result<(Query, Vec<&'a str>)>
Build a Query from a string slice.
This function can return an error if an unknown index is referenced. On success this function returns a fully owned Query and a vector of string slices into the input query, that contains all parts of the query, that are not following the query syntax. They are called “Freetext”. They will never contain whitespace.
§Basic Syntax
The following text is an example for a query:
+attr1:foo,bar +attr2:=baz +attr3:<42,>84 -attr4:69-121
As a boolean expression it will mean something like this:
(attr1==foo || attr1==bar)
&& (attr2==baz)
&& (attr3 <= 42 || attr3 >= 84)
&& !(69 <= attr4 <= 121)
§In-depth Syntax description
A string query consists of multiple whitespace seperated attribute selectors.
Each of them starts with a +
or -
sign, indicating if the rows matching this
selector should be included or excluded from the result. This is followed by the
name of the attribute/index and a single :
char. Next comes a list of comma seperated
values that describe the basic queries that are used to select rows. There are
special operator symbols that can change the meaning of a value if the index
supports the matching query type. For example, if the Index supports Maximum queries,
the following value will return a Maximum query instead of an Exact query: <123
.
The following operator symbols are currently used if the index supports it:
>val
- forces a Minimum query<val
- forces a Maximum query=val
- forces a Exact queryminval-maxval
- forces a InRange query
If no operator symbol is found, a Prefix query will be used if it is supported by the index. Otherwise a Exact query is used, even if the index may not support it (all official indices currently implement them).
All non-whitespace substrings in the query, that are not valid attribute selectors are considered “Freetext”. All of these are returned on success and can be used or ignored by the caller. For example they can be used to filter the results further.
§Limits
- OutRange queries don’t have an operator symbol and are currently not supported.
But it is possible to build a functionally equivalent query if the index supports
Minimum and Maximum queries:
+attr:<10,>20
- InRange does not support negative values because only one
-
char is allowed. - There is no way to force a Prefix query. It will be automatically used if no operator symbol is found and the index supports them.
§Example
use attribute_search_engine::{SearchEngine, SearchIndexHashMap, Query};
let mut index = SearchIndexHashMap::<_, String>::new();
// Fill index here...
let mut engine = SearchEngine::<usize>::new();
engine.add_index("attribute", index);
let (q, freetext) = engine.query_from_str("+attribute:foo bar").expect("no error");
assert_eq!(q, Query::And(vec![Query::Exact("attribute".into(), "foo".into())]));
assert_eq!(freetext, vec!["bar"]);