基于非数组字段在mongo文档中投影数组值

时间:2019-03-13 05:54:03

标签: mongodb aggregation-framework projection

我数据库中的数据如下:

/* 1 */
{
      "name": "Severus",
      "u_name": "severussnape",
      "info": [
        {
          "value": "Severus",
          "source": "1",
          "infotag": "name"
        },
        {
          "value": "severussnape",
          "source": "2",
          "infotag": "name"
        }
      ]
}

/* 2 */
{
      "name": "Harry",
      "u_name": null,
      "info": [
        {
        "value": "Harry",
          "source": "1",
          "infotag": "name"
        }
      ]
}

我想对数据进行投影,以便根据name字段是否为空来更改结果中的info字段和u_name数组。我期望的结果看起来像这样:

/* 1 */
{
      "name": "severussnape",
      "info": [
        {
          "value": "severussnape",
          "source": "2",
          "infotag": "name"
        }
      ]
}

/* 2 */
{
      "name": "Harry",      
      "info": [
        {
          "value": "Harry",
          "source": "1",
          "infotag": "name"
        }
      ]
}

我设法使用投影正确投影了名称字段:

db.database.aggregate([{
    $project:{
        "name":{$cond:[{$eq:["$u_name",null]},"$name","$u_name"]}
    }
}])

但是我一直无法弄清楚如何从info中删除第一个文档中值为{Severus“的u_name数组元素。这可能吗?

3 个答案:

答案 0 :(得分:1)

您应该尝试使用此汇总查询,这样可以解决您的问题。

db.database.aggregate([
    {
        $project:{
            'name': {
                '$ifNull': ['$u_name', '$name']
            },
            'info': '$info'
        }
    },
    {
        $project: {
            'name': '$name',
            'info': {
                '$filter': {
                    'input': '$info',
                    'as': 'info',
                    'cond': {
                        '$eq':['$$info.value', '$name']
                    }
                }
            }
        }
    }
])

答案 1 :(得分:0)

您可以尝试以下操作:

db.database.aggregate([
    {
        $project:{
            "name":{ $cond: { if: { $eq:["$u_name",null] }, then: "$name", else: "$u_name" } },
        }
    },
])

答案 2 :(得分:0)

这有帮助吗?

如果有任何条件需要。你可以匹配它。

db.getCollection('TestQueries').aggregate([
{$unwind:{
 path:"$info",
 preserveNullAndEmptyArrays:true
}},
{$project:{
  name:"$info.value",
  info:1
}}
])