Skip to content

Commit 541806e

Browse files
authored
feat(text-index): Added support for text indexes (#23)
1 parent 4e50093 commit 541806e

File tree

3 files changed

+87
-19
lines changed

3 files changed

+87
-19
lines changed

src/index.rs

Lines changed: 70 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -26,12 +26,50 @@ impl From<SortOrder> for Bson {
2626
}
2727
}
2828

29+
#[derive(Clone, Debug)]
30+
enum IndexKey {
31+
SortIndex(SortIndexKey),
32+
TextIndex(TextIndexKey),
33+
}
34+
35+
impl IndexKey {
36+
fn get_key_name(&self) -> String {
37+
match self {
38+
IndexKey::SortIndex(s) => match s.direction {
39+
SortOrder::Ascending => format!("{}_1", s.name),
40+
SortOrder::Descending => format!("{}_-1", s.name),
41+
},
42+
43+
IndexKey::TextIndex(t) => format!("{}_text", t.name),
44+
}
45+
}
46+
47+
fn get_name(&self) -> String {
48+
match self {
49+
IndexKey::SortIndex(s) => s.name.to_string(),
50+
IndexKey::TextIndex(t) => t.name.to_string(),
51+
}
52+
}
53+
54+
fn get_value(&self) -> Bson {
55+
match self {
56+
IndexKey::SortIndex(s) => s.direction.into(),
57+
IndexKey::TextIndex(_) => "text".into(),
58+
}
59+
}
60+
}
61+
2962
#[derive(Debug, Clone)]
30-
struct IndexKey {
63+
struct SortIndexKey {
3164
name: Cow<'static, str>,
3265
direction: SortOrder,
3366
}
3467

68+
#[derive(Debug, Clone)]
69+
struct TextIndexKey {
70+
name: Cow<'static, str>,
71+
}
72+
3573
/// Specify field to be used for indexing and options.
3674
///
3775
/// [Mongo manual](https://docs.mongodb.com/manual/indexes/)
@@ -78,6 +116,15 @@ impl Index {
78116
index
79117
}
80118

119+
/// Make a new index for the given key with the text parameter.
120+
///
121+
/// [Mongo manual](https://docs.mongodb.com/manual/core/index-single/)
122+
pub fn new_with_text(key: impl Into<Cow<'static, str>>) -> Self {
123+
let mut index = Self::default();
124+
index.add_key_with_text(key);
125+
index
126+
}
127+
81128
/// Make this index compound adding the given key with ascending direction.
82129
///
83130
/// [Mongo manual](https://docs.mongodb.com/manual/core/index-compound/).
@@ -99,10 +146,18 @@ impl Index {
99146
key: impl Into<Cow<'static, str>>,
100147
direction: SortOrder,
101148
) {
102-
self.keys.push(IndexKey {
149+
self.keys.push(IndexKey::SortIndex(SortIndexKey {
103150
name: key.into(),
104151
direction,
105-
});
152+
}));
153+
}
154+
155+
/// Make this index compound adding the given key with text.
156+
///
157+
/// [Mongo manual](https://docs.mongodb.com/manual/core/index-compound/).
158+
pub fn add_key_with_text(&mut self, key: impl Into<Cow<'static, str>>) {
159+
self.keys
160+
.push(IndexKey::TextIndex(TextIndexKey { name: key.into() }));
106161
}
107162

108163
/// Builder style method for `add_key_with_direction`.
@@ -140,13 +195,8 @@ impl Index {
140195
let mut names = Vec::with_capacity(self.keys.len());
141196
let mut keys_doc = Document::new();
142197
for key in self.keys {
143-
let key_name = match key.direction {
144-
SortOrder::Ascending => format!("{}_1", key.name),
145-
SortOrder::Descending => format!("{}_-1", key.name),
146-
};
147-
names.push(key_name);
148-
149-
keys_doc.insert(key.name, key.direction);
198+
names.push(key.get_key_name());
199+
keys_doc.insert(key.get_name(), key.get_value());
150200
}
151201

152202
let mut index_doc = doc! { "key": keys_doc };
@@ -232,6 +282,8 @@ pub enum IndexOption {
232282
StorageEngine(Document),
233283
/// Specifies the collation
234284
Collation(Document),
285+
/// Specifies the weights for text indexes
286+
Weights(Vec<(String, i32)>),
235287
/// Specify a custom index option. This is present to provide forwards compatibility.
236288
Custom { name: String, value: Bson },
237289
}
@@ -247,6 +299,7 @@ impl IndexOption {
247299
IndexOption::ExpireAfterSeconds(..) => "expireAfterSeconds",
248300
IndexOption::StorageEngine(..) => "storageEngine",
249301
IndexOption::Collation(..) => "collation",
302+
IndexOption::Weights(..) => "weights",
250303
IndexOption::Custom { name, .. } => name.as_str(),
251304
}
252305
}
@@ -261,6 +314,13 @@ impl IndexOption {
261314
IndexOption::PartialFilterExpression(doc)
262315
| IndexOption::StorageEngine(doc)
263316
| IndexOption::Collation(doc) => Bson::Document(doc),
317+
IndexOption::Weights(w) => {
318+
let mut doc = Document::new();
319+
w.into_iter().for_each(|(k, v)| {
320+
doc.insert(k, Bson::from(v));
321+
});
322+
Bson::Document(doc)
323+
}
264324
IndexOption::Custom { value, .. } => value,
265325
}
266326
}

src/lib.rs

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -89,14 +89,16 @@
8989
#[cfg(test)]
9090
extern crate pretty_assertions;
9191

92-
mod macros;
9392
mod index;
93+
mod macros;
9494
mod repository;
9595

9696
pub mod operator;
9797

9898
pub use index::{sync_indexes, Index, IndexOption, Indexes, SortOrder};
99-
pub use repository::{BulkUpdate, BulkUpdateResult, BulkUpdateUpsertResult, Repository, CollectionExt};
99+
pub use repository::{
100+
BulkUpdate, BulkUpdateResult, BulkUpdateUpsertResult, CollectionExt, Repository,
101+
};
100102

101103
// Re-export mongodb
102104
pub use mongodb as mongo;
@@ -223,9 +225,8 @@ pub mod prelude {
223225
#[doc(no_inline)]
224226
pub use crate::{
225227
f, field, operator::*, pipeline, sync_indexes, BulkUpdate, BulkUpdateResult,
226-
BulkUpdateUpsertResult, CollectionConfig, Index, IndexOption, Indexes, Model, Repository,
227-
SortOrder,
228-
CollectionExt as _, ToRepository as _,
228+
BulkUpdateUpsertResult, CollectionConfig, CollectionExt as _, Index, IndexOption, Indexes,
229+
Model, Repository, SortOrder, ToRepository as _,
229230
};
230231
#[doc(no_inline)]
231232
pub use futures_util::future::{BoxFuture, FutureExt};

src/repository.rs

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -285,7 +285,6 @@ impl<M: Model> Repository<M> {
285285
}
286286
}
287287

288-
289288
/// MongODM-provided utilities functions on `mongodb::Collection<M>`.
290289
#[async_trait]
291290
pub trait CollectionExt {
@@ -329,15 +328,23 @@ pub trait CollectionExt {
329328
/// assert_eq!(bulk_update_res.nb_modified, 2);
330329
/// # }
331330
/// ```
332-
async fn bulk_update<V, U>(&self, db: &mongodb::Database, updates: V) -> Result<BulkUpdateResult>
331+
async fn bulk_update<V, U>(
332+
&self,
333+
db: &mongodb::Database,
334+
updates: V,
335+
) -> Result<BulkUpdateResult>
333336
where
334337
V: 'async_trait + Send + Sync + Borrow<Vec<U>>,
335338
U: 'async_trait + Send + Sync + Borrow<BulkUpdate>;
336339
}
337340

338341
#[async_trait]
339342
impl<M: Send + Sync> CollectionExt for mongodb::Collection<M> {
340-
async fn bulk_update<V, U>(&self, db: &mongodb::Database, updates: V) -> Result<BulkUpdateResult>
343+
async fn bulk_update<V, U>(
344+
&self,
345+
db: &mongodb::Database,
346+
updates: V,
347+
) -> Result<BulkUpdateResult>
341348
where
342349
V: 'async_trait + Send + Sync + Borrow<Vec<U>>,
343350
U: 'async_trait + Send + Sync + Borrow<BulkUpdate>,
@@ -377,4 +384,4 @@ impl<M: Send + Sync> CollectionExt for mongodb::Collection<M> {
377384
let res = db.run_command(command, None).await?;
378385
Ok(from_document(res)?)
379386
}
380-
}
387+
}

0 commit comments

Comments
 (0)