mirror of
https://github.com/meilisearch/meilisearch.git
synced 2024-11-23 10:37:41 +08:00
FacetCondition can be created from array of facets
This commit is contained in:
parent
a8e3269ad6
commit
cb5e57e2dd
@ -3,6 +3,7 @@ use std::fmt::Debug;
|
|||||||
use std::ops::Bound::{self, Included, Excluded};
|
use std::ops::Bound::{self, Included, Excluded};
|
||||||
use std::str::FromStr;
|
use std::str::FromStr;
|
||||||
|
|
||||||
|
use either::Either;
|
||||||
use heed::types::{ByteSlice, DecodeIgnore};
|
use heed::types::{ByteSlice, DecodeIgnore};
|
||||||
use log::debug;
|
use log::debug;
|
||||||
use num_traits::Bounded;
|
use num_traits::Bounded;
|
||||||
@ -141,6 +142,81 @@ where T: FromStr,
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl FacetCondition {
|
impl FacetCondition {
|
||||||
|
pub fn from_array<I, J, A, B>(
|
||||||
|
rtxn: &heed::RoTxn,
|
||||||
|
index: &Index,
|
||||||
|
array: I,
|
||||||
|
) -> anyhow::Result<Option<FacetCondition>>
|
||||||
|
where I: IntoIterator<Item=Either<J, B>>,
|
||||||
|
J: IntoIterator<Item=A>,
|
||||||
|
A: AsRef<str>,
|
||||||
|
B: AsRef<str>,
|
||||||
|
{
|
||||||
|
fn facet_condition(
|
||||||
|
fields_ids_map: &FieldsIdsMap,
|
||||||
|
faceted_fields: &HashMap<FieldId, FacetType>,
|
||||||
|
key: &str,
|
||||||
|
value: &str,
|
||||||
|
) -> anyhow::Result<FacetCondition>
|
||||||
|
{
|
||||||
|
let fid = fields_ids_map.id(key).unwrap();
|
||||||
|
let ftype = faceted_fields.get(&fid).copied().unwrap();
|
||||||
|
let (neg, value) = match value.strip_prefix('-') {
|
||||||
|
Some(value) => (true, value),
|
||||||
|
None => (false, value),
|
||||||
|
};
|
||||||
|
|
||||||
|
let operator = match ftype {
|
||||||
|
FacetType::String => OperatorString(fid, FacetStringOperator::equal(value)),
|
||||||
|
FacetType::Float => OperatorF64(fid, FacetNumberOperator::Equal(value.parse()?)),
|
||||||
|
FacetType::Integer => OperatorI64(fid, FacetNumberOperator::Equal(value.parse()?)),
|
||||||
|
};
|
||||||
|
|
||||||
|
if neg { Ok(operator.negate()) } else { Ok(operator) }
|
||||||
|
}
|
||||||
|
|
||||||
|
let fields_ids_map = index.fields_ids_map(rtxn)?;
|
||||||
|
let faceted_fields = index.faceted_fields(rtxn)?;
|
||||||
|
let mut ands = None;
|
||||||
|
|
||||||
|
for either in array {
|
||||||
|
match either {
|
||||||
|
Either::Left(array) => {
|
||||||
|
let mut ors = None;
|
||||||
|
for rule in array {
|
||||||
|
let mut iter = rule.as_ref().splitn(2, ':');
|
||||||
|
let key = iter.next().unwrap();
|
||||||
|
let value = iter.next().unwrap();
|
||||||
|
let condition = facet_condition(&fields_ids_map, &faceted_fields, key, value)?;
|
||||||
|
ors = match ors.take() {
|
||||||
|
Some(ors) => Some(Or(Box::new(ors), Box::new(condition))),
|
||||||
|
None => Some(condition),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
if let Some(rule) = ors {
|
||||||
|
ands = match ands.take() {
|
||||||
|
Some(ands) => Some(And(Box::new(ands), Box::new(rule))),
|
||||||
|
None => Some(rule),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
},
|
||||||
|
Either::Right(rule) => {
|
||||||
|
let mut iter = rule.as_ref().splitn(2, ':');
|
||||||
|
let key = iter.next().unwrap();
|
||||||
|
let value = iter.next().unwrap();
|
||||||
|
let condition = facet_condition(&fields_ids_map, &faceted_fields, key, value)?;
|
||||||
|
ands = match ands.take() {
|
||||||
|
Some(ands) => Some(And(Box::new(ands), Box::new(condition))),
|
||||||
|
None => Some(condition),
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(ands)
|
||||||
|
}
|
||||||
|
|
||||||
pub fn from_str(
|
pub fn from_str(
|
||||||
rtxn: &heed::RoTxn,
|
rtxn: &heed::RoTxn,
|
||||||
index: &Index,
|
index: &Index,
|
||||||
|
Loading…
Reference in New Issue
Block a user