这是一个非常简单的项目,用于学习如何将 mongodb 与 Rust 结合使用。我在这里使用官方 mongodb 驱动程序:https://github.com/mongodb/mongo-rust-driver。问题是,如果我使用aggregate,我无法读取结果
// main.rs
use mongodb::bson::{doc, Bson};
use mongodb::{options::AggregateOptions, options::ClientOptions, Client};
use std::error::Error;
use tokio;
#[tokio::main]
async fn main() -> Result<(), Box<dyn Error>> {
// Load the MongoDB connection string:
let client_uri = "mongodb://127.0.0.1:27017";
// A Client is needed to connect to MongoDB:
let mut options = ClientOptions::parse(&client_uri).await?;
options.app_name = Some("testing".to_string());
let client = Client::with_options(options)?;
// get the collection here
let items = client.database("my_database").collection("inventory");
// aggregate options and pipeline
let pipeline = vec![doc! {"$match": {"name": "FOO"}}];
let options = AggregateOptions::builder().allow_disk_use(true).build();
// I'm using tokio for async-await library
let data = items
.aggregate(pipeline, options)
.await
.map_err(|e| println!("{}", e));
// data is a Result<mongodb::Cursor> type
match data {
Ok(cursor) => {
// I want to iterate the returned documents here
// this doesn't compiles
while let Some(doc) = cursor.next().await {
println!("{}", doc?)
}
},
Err(e) => println!("{:?}", e),
}
Run Code Online (Sandbox Code Playgroud)
上面的代码返回一个错误。它抱怨光标没有任何next()功能。
while let Some(doc) = cursor.next().await {
| ^^^^ method not found in `mongodb::Cursor`
Run Code Online (Sandbox Code Playgroud)
我在这里阅读了 mongodb::Cursor 的手册:https://docs.rs/mongodb/1.2.1/mongodb/struct.Cursor.html
和这里的聚合函数https://docs.rs/mongodb/1.2.1/mongodb/struct.Collection.html#method.aggregate
正如您所看到的,聚合方法应该返回Result<Cursor>。正如手册所述:
游标可以像任何其他流一样使用。最简单的方法就是迭代它生成的文档:
while let Some(doc) = cursor.next().await {
println!("{}", doc?)
}
Run Code Online (Sandbox Code Playgroud)
那么为什么它不起作用呢?
我的依赖项Cargo.toml:
[dependencies]
tokio = { version = "0.2", features = ["macros", "rt-threaded"] }
serde = { version = "1.0", features = ["derive"] }
mongodb = "1.2.0"
Run Code Online (Sandbox Code Playgroud)
如果我打印光标println!("{:?}", cursor);。它包含数据在里面。如何从这个游标中取出数据?
我找到了!只需添加use tokio::stream::StreamExt;到文件顶部,其余的就可以了。
...Stream 具有的所有其他方法也可在 Cursor 上使用。这包括 StreamExt 提供的所有功能,它提供与标准库 Iterator 特征类似的功能。
// main.rs
use mongodb::bson::{doc, Bson};
use mongodb::{options::AggregateOptions, options::ClientOptions, Client};
use std::error::Error;
use tokio;
// don't forget this!
use tokio::stream::StreamExt;
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
3010 次 |
| 最近记录: |