我正在尝试聚合大型数据集,因此我将游标与聚合一起使用。但是,我找不到如何在不使用额外延迟的情况下实现此目的的文档。我觉得必须有一种方法可以将aggregate().cursor().each()
与聚合完成后解析的promise相结合。有谁知道怎么做?
此代码有效且基于http://mongoosejs.com/docs/api.html#aggregate_Aggregate-cursor 我试图在没有额外承诺的情况下找到一种方法。
aggregation = MyModel.aggregate().group({
_id: '$name'
});
deferred = Q.defer();
aggregation.cursor({
batchSize: 1000
}).exec().each(function(err, doc) {
if (err) {
return deferred.reject(err);
}
if (!doc) {
return deferred.resolve(); // done
}
// do stuff with doc
});
return deferred.promise;
答案 0 :(得分:4)
我发现这个SO正在寻找使用聚合游标和promises的一般帮助。经过大量的试验和错误,如果有其他人偶然发现这一点,我发现游标对象有一个next()方法返回一个promise,就像其他游标一样。出于某种原因,我无法在没有async
标志的情况下获得对它的引用。所以如果你使用蓝鸟:
let bluebird = require("bluebird");
let aggregation = MyModel.aggregate().group({
_id: '$name'
});
aggregation.cursor({
batchSize: 1000,
async: true
}).exec().then(cursor => {
return bluebird.coroutine(function* () {
let doc;
while ((doc = yield cursor.next())) {
console.log(doc._id)
}
})()
}).then(() => { console.log("done with cursor"); })
exec()
调用不再返回一个promise,只返回游标本身,并且不再需要async: true
属性。
let aggregation = MyModel.aggregate().group({
_id: '$name'
});
(async function () {
let doc, cursor;
cursor = aggregation.cursor({batchSize: 1000}).exec();
while ((doc = await cursor.next())) {
console.log(doc._id)
}
})()
.then(() => console.log("done with cursor"); )