【问题标题】:Accessing external parameters and document in mongodb group aggregation在 mongodb 组聚合中访问外部参数和文档
【发布时间】:2017-10-07 04:07:25
【问题描述】:

在具有以下一般结构的集合中:

{_id: 'id1', clientId: 'cid1', clientName:'Jon', item: 'item1', dateOfPurchase: '...'},
{_id: 'id2', clientId: 'cid1', clientName:'Jon', item: 'item2', dateOfPurchase: '...'},
{_id: 'id3', clientId: 'cid2', clientName:'Doe', item: 'itemX', dateOfPurchase: '...'}
... etc

目标是按clientId 创建一个分组来计算一些简单的统计数据,例如每个 clientId 的总出现次数。

使用 Node.js MongoDB 驱动程序 API Collection.group method 实现此目的的一种方法是:

db.collection.group(
    'clientId',
    {},
    { count: 0 },
    function(obj, prev) {
        prev.count++;
    },
    true
}

上面示例数据的输出类似于:

{clientId: 'cid1', count: 2}
{clientId: 'cid2', count: 1}

问题 1: 将一些外部值传递给 reducer 函数的最佳方法是什么?例如,我可能想要计算在特定日期之前/之后进行的购买的不同计数,并希望将此日期作为参数传递。我知道使用mapReduce 我可以为此目的使用scope 选项。我想知道是否有办法使用 group 函数来做到这一点。我可以使用迭代器对象,但感觉很hacky。

问题 2: 有没有办法从 finalize 函数内部访问原始文档,以便在结果中包含一些额外的数据?即从原始文档中投影额外的字段,例如clientName

{clientId: 'cid1', count: 2, clientName: 'Jon'}
{clientId: 'cid2', count: 1, clientName: 'Doe'}

对问题 2 的说明, a) 我可以在 reducer 函数中添加额外的字段,但是包含不应该在每次迭代中运行的代码感觉是多余的。 b)我可以使用聚合管道来实现这样的事情,但我想知道我是否可以在这里使用Collection.group 来做到这一点

【问题讨论】:

    标签: node.js mongodb mongodb-query


    【解决方案1】:

    在挖掘文档时,我找到了 问题 1 的答案,即使用 Code class 进行减速器功能。 Code 构造函数采用第二个参数,其功能与 mapReduce 中的 scope 完全相同,例如:

    const myFunction = function(obj, prev) {
        if (prev.count < myLimit) // myLimit is available here because it is defined in the Code initialization below
            prev.count++;
    }
    
    Code = require('mongodb').Code;
    db.collection.group(
        'clientId',
        {},
        { count: 0 },
        new Code(myFunction, { myLimit: 5 }),
        true
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2016-12-19
      • 1970-01-01
      • 2017-04-25
      • 2015-05-08
      • 2019-05-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多