runCommand vs aggregate方法进行聚合

时间:2018-05-03 11:23:26

标签: mongodb aggregation-framework runcommand

要运行聚合查询,可以使用以下任一方法:

db.collectionName.aggregate(query1);

OR

db.runCommand(query2)

但是今天早上我注意到了一些奇怪的事情。虽然这个:

db.runCommand(

{
   "aggregate":"collectionName",
    allowDiskUse: true,
   "pipeline":[
      {
         "$match":{
            "field":param


         }
      }

   ]
});

失败并显示错误:

{
    "ok" : 0.0,
    "errmsg" : "aggregation result exceeds maximum document size (16MB)",
    "code" : 16389,
    "codeName" : "Location16389"
}

这:

db.collectionName.aggregate([

{
  $match: {
           field: param
   }
}

]) 

正在运行(给出预期的聚合结果)。

这怎么可能?

1 个答案:

答案 0 :(得分:5)

当然,区别在于.aggregate()方法会返回"cursor",而您提供给runCommand()的选项则不是。这实际上是遗留形式,它将响应作为单个BSON文档返回,并且所有it's limitations。另一方面,游标没有限制。

当然,您可以使用runCommand()方法在shell中“制作自己的游标”,因为后来这正是.aggregate()方法正在做的“幕后”。所有驱动程序都是如此,它基本上为所有内容调用数据库命令。

使用shell,您可以像这样转换您的请求:

var cmdRes = db.runReadCommand({
   "aggregate": "collectionName",
   "allowDiskUse": true,
   "pipeline":[
      {
         "$match":{
            "field":param
         }
      }
   ],
   "cursor": { "batchSize": 25 }
});

var cursor = new DBCommandCursor(db, cmdRes);

cursor.next();   // will actually iterate the cursor

如果你真的想深入研究它,那么输入db.collectionName.aggregate而没有括号(),所以你实际上打印了函数定义。这将向您展示一些其他函数调用,您可以进一步深入研究它们,并最终看到上面显示的有效线条,以及许多其他内容。

但是你运行它的方式,它是一个“单个BSON文档”响应。按照此处显示的方式运行它,您将获得相同的“光标”响应。