MongoDB - 带有聚合的$ nin无效运算符

时间:2017-01-06 18:55:07

标签: node.js mongodb mongoose database

我有一个函数,它应该返回按邀请和非邀请在给定时间段和组中创建的用户数。在$cond运算符上,我需要比较字段tkbSponsor是否不是null且不等于example@example.com。如果此条件为真,则会邀请用户。否则,他没被邀请。

var countByPeriod = function(req,res) {
    var initialDate = req.body.initialDate;
    var finalDate = req.body.finalDate;

    User.aggregate([
        {
            "$match": {
                "timeStamp": {
                    "$gte": new Date(initialDate),
                    "$lt": new Date(finalDate)
                }
            }
        },
        {
            "$group": {
                "_id": null,
                "total": { "$sum": 1 },
                "invited": {
                    "$sum": {
                        "$cond": [
                            { 
                                "tkbSponsor": {
                                    "$nin": ["example@example.com",null] 
                                }
                            },
                            1,
                            0
                        ]
                    }
                }
            }
        }
    ], (err,result) => {
        if (!err)  {
            if (result.length) res.send(result[0]);
            else res.send({"total": 0,"invited":0});
        } else {
            res.sendStatus(500);
            console.log(err);
        }

    });

};

顺便说一句,这个函数在执行时给我一个错误:

{ [MongoError: invalid operator '$nin']
  name: 'MongoError',
  message: 'invalid operator \'$nin\'',
  ok: 0,
  errmsg: 'invalid operator \'$nin\'',
  code: 15999 }

只是一个观察。我过去常常使用$cond运算符,因为我不需要与null进行比较:

"$cond": [
           { 
             "$ne": ["$tkbSponsor", "example@example.com"]
           },
           1,
           0
]

它有效。但是,现在我还要比较tkbSponsor是否为空且使用$nin,是否给了我这个错误。

1 个答案:

答案 0 :(得分:0)

$and $ifNull 结合使用更改为:

{
    "$cond": [
        { 
            "$and": [
                { "$ne": ["$tkbSponsor", "example@example.com"] },
                { 
                    "$ne": [
                        { "$ifNull": [ "$tkbSponsor", null ] },
                        null
                    ] 
                }
            ]
        }, 1, 0
    ]
}

或使用$or作为

{
    "$cond": [
        { 
            "$or": [
                { "$eq": ["$tkbSponsor", "example@example.com"] },
                { 
                    "$eq": [
                        { "$ifNull": [ "$tkbSponsor", null ] },
                        null
                    ] 
                }
            ]
        }, 0, 1
    ]
}

$ifNull 运营商的存在是通过替换"不存在&#34来充当 $exists 运营商34;或者具有null值的空字段用于评估。

运行此应返回正确的结果,因为之前的 revision 仅评估tkbSponsor字段exists AND的值为{{ 1}}或" example@example.com"。

$ifNull ,"不存在"当运算符为它们赋予空值时,也会对字段进行求值。