我有一个可以在MongoDB Shell中运行的查询,但它会抛出一个"聚合结果超过最大文档大小(16MB)"当我增加要返回的文档数时,使用Spring Data MongoDB的异常。
以下是无错误返回的shell查询:
db.myCollection.aggregate([{"$skip":0},{"$limit":10000},{"$match":{"_id"="550b2552e4b03562d6329a39"}}], {"allowDiskUse":true})
以下是Spring Data片段:
List<AggregrationOperation> ops = new ArrayList<AggregationOperation>();
ops.add(new SkipOperation(0));
ops.add(new LimitOperation(10000));
ops.add(new MatchOperation(Criteria.where("_id").is("550b2552e4b03562d6329a39")));
TypeAggregation<MyCollection> aggregation = Aggregation.newAggregation(MyCollection.class, ops).withOptions(Aggregation.newAggregationOptions().allowDiskUse(true).build());
AggregationResults<MyCollection> result = mongoTemplate.aggregate(aggregation, MyCollection.class);
List<MyCollection> myResults = result.getMappedResults()
当我限制说100或1000条记录时,一切正常。当我增加到10,000时,我得到&#34;聚合结果超过最大文档大小(16MB)&#34;异常。
此处参考我正在使用的版本:
MongoDB = 3.0.0
Mongo Java Driver = 2.13.0
Spring Data MongoDB = 1.6.0
Spring Data Commons = 1.9.0
更新:
背景:我来到了聚合解决方案,因为在使用find()时我超过了32MB的排序限制。我知道添加索引可以解决这个问题。不幸的是,这种解决方案并没有扩展。我希望对列表网格中的所有列进行排序,这意味着要索引10列以上。当然,从UI我可以限制排序到特定的列,但我再次尝试避免该解决方案,因此我尝试聚合的原因。
看来使用光标是我唯一的解决方案。任何人都可以确认Spring Data MongoDB不提供直接游标支持,这意味着我必须使用MongoDB的API吗?
答案 0 :(得分:2)
我使用RoboMongo(mongo客户端)遇到了同样的问题。
尝试使用db.runCommand()
代替.aggregate()
。
似乎在某些客户端上使用聚合方法会向查询添加一些数据,并且将忽略allowDiskUse。
当我使用ranCommand时,它工作正常:
db.runCommand(
{ aggregate: "collection_name",
pipeline: [
{$group: ...},
{$match: ...},
{$group: ...}
],
allowDiskUse: true
}
答案 1 :(得分:1)
默认情况下,您可以使用 outputMode(AggregationOptions.OutputMode.CURSOR)作为输出选项,而不是有限的16MB文档。请参阅Aggregation Cursor Usage。
Aggregation.newAggregationOptions().outputMode(AggregationOptions.OutputMode.CURSOR).allowDiskUse(true).build()