如何仅投影 MongoDB 中数组中存在的字段?

How to project only the fields present in an array in MongoDB?

有一个文档模式,它有一个名为 "updatedFields" 的数组字段,其中包含一些您可以在 "oldDocument" 中找到的字段名称,并且 "newDocument" 个对象。这是它的照片。

现在我只想投影 "newDocument""oldDocument""updatedFields" 数组中存在的那些字段,如下所示:

 $project : { 
    "oldDocument.Modified":1,
    "oldDocument.Status":1,
    "newDocument.Modified":1,
    "newDocument.Status":1
 } 

有谁知道如何根据数组中的字段名称构建项目子句?我需要一个 MongoDB 查询,而不是 js 代码。

您可以使用 $objectToArray 将键格式化为值,$filter 它们根据 updatedFields 数组,然后使用 $arrayToObject 再次使它们成为键.

编辑:根据评论中的要求,在过滤器中使用 $map 将日期转换为字符串。

像这样:

db.collection.aggregate([
  {
    $project: {
      oldDocumentArr: {$objectToArray: "$oldDocument"},
      newDocumentArr: {$objectToArray: "$newDocument"},
      updatedFields: 1
    }
  },
  {
    $project: {
      oldDocumentFilter: {
        $map: {
          input: {
            $filter: {
              input: "$oldDocumentArr",
              as: "item",
              cond: {$in: ["$$item.k", "$updatedFields"]
              }
            }
          },
          "as": "obj",
          "in": {
            "k": "$$obj.k",
            "v": {$toString: "$$obj.v"}
          }
        }
      },
      newDocumentFilter: {
        $map: {
          input: {
            $filter: {
              input: "$newDocumentArr",
              as: "item",
              cond: {$in: ["$$item.k", "$updatedFields"]
              }
            }
          },
          "as": "obj",
          "in": {
            "k": "$$obj.k",
            "v": {$toString: "$$obj.v"}
          }
        }
      }
    }
  },
  {
    $project: {
      oldDocument: {$arrayToObject: "$oldDocumentFilter"},
      newDocument: {$arrayToObject: "$newDocumentFilter"},
      _id: 0
    }
  }
])

正如您在 playground

上看到的