elasticsearch_dsl/search/queries/compound/boosting_query.rs
1use crate::search::*;
2use crate::util::*;
3
4/// Returns documents matching a `positive` query while reducing the
5/// [relevance score](https://www.elastic.co/guide/en/elasticsearch/reference/current/query-filter-context.html#relevance-scores)
6/// of documents that also match a `negative` query.
7///
8/// You can use the `boosting` query to demote certain documents without excluding them from the search results.
9///
10/// To create boosting query:
11/// ```
12/// # use elasticsearch_dsl::queries::*;
13/// # use elasticsearch_dsl::queries::params::*;
14/// # let query =
15/// Query::boosting(Query::term("test1", 123), Query::term("test2", 456), 0.2)
16/// .boost(3)
17/// .name("test");
18/// ```
19/// <https://www.elastic.co/guide/en/elasticsearch/reference/current/query-dsl-boosting-query.html>
20#[derive(Debug, Clone, PartialEq, Serialize)]
21#[serde(remote = "Self")]
22pub struct BoostingQuery {
23 positive: Box<Query>,
24
25 negative: Box<Query>,
26
27 negative_boost: NegativeBoost,
28
29 #[serde(skip_serializing_if = "ShouldSkip::should_skip")]
30 boost: Option<f32>,
31
32 #[serde(skip_serializing_if = "ShouldSkip::should_skip")]
33 _name: Option<String>,
34}
35
36impl Query {
37 /// Creates an instance of [`BoostingQuery`]
38 ///
39 /// - `positive` - Query you wish to run. Any returned documents must match this query.
40 /// - `negative` - Query used to decrease the
41 /// [relevance score](https://www.elastic.co/guide/en/elasticsearch/reference/current/query-filter-context.html#relevance-scores)
42 /// of matching documents.<br/>
43 /// If a returned document matches the `positive` query and this query, the `boosting` query
44 /// calculates the final
45 /// [relevance score](https://www.elastic.co/guide/en/elasticsearch/reference/current/query-filter-context.html#relevance-scores)
46 /// for the document as follows:
47 /// 1. Take the original relevance score from the `positive` query.
48 /// 2. Multiply the score by the `negative_boost` value.
49 /// - `negative_boost` - Floating point number between `0` and `1.0` used to decrease the
50 /// [relevance scores](https://www.elastic.co/guide/en/elasticsearch/reference/current/query-filter-context.html#relevance-scores)
51 /// of documents matching the `negative` query.
52 pub fn boosting<Q, B>(positive: Q, negative: Q, negative_boost: B) -> BoostingQuery
53 where
54 Q: Into<Query>,
55 B: Into<NegativeBoost>,
56 {
57 BoostingQuery {
58 positive: Box::new(positive.into()),
59 negative: Box::new(negative.into()),
60 negative_boost: negative_boost.into(),
61 boost: None,
62 _name: None,
63 }
64 }
65}
66
67impl BoostingQuery {
68 add_boost_and_name!();
69}
70
71impl ShouldSkip for BoostingQuery {
72 fn should_skip(&self) -> bool {
73 self.positive.should_skip() || self.negative.should_skip()
74 }
75}
76
77serialize_with_root!("boosting": BoostingQuery);
78
79#[cfg(test)]
80mod tests {
81 use super::*;
82
83 #[test]
84 fn serialization() {
85 assert_serialize_query(
86 Query::boosting(Query::term("test1", 123), Query::term("test2", 456), 0.2),
87 json!({
88 "boosting": {
89 "positive": {
90 "term": {
91 "test1": {
92 "value": 123
93 }
94 }
95 },
96 "negative": {
97 "term": {
98 "test2": {
99 "value": 456
100 }
101 }
102 },
103 "negative_boost": 0.2
104 }
105 }),
106 );
107
108 assert_serialize_query(
109 Query::boosting(Query::term("test1", 123), Query::term("test2", 456), 0.2)
110 .boost(3)
111 .name("test"),
112 json!({
113 "boosting": {
114 "positive": {
115 "term": {
116 "test1": {
117 "value": 123
118 }
119 }
120 },
121 "negative": {
122 "term": {
123 "test2": {
124 "value": 456
125 }
126 }
127 },
128 "negative_boost": 0.2,
129 "boost": 3.0,
130 "_name": "test"
131 }
132 }),
133 );
134 }
135}