如何在MongoDB中修改嵌套对象数组中的字段名/键?

10 浏览
0 Comments

如何在MongoDB中修改嵌套对象数组中的字段名/键?

我有一个包含多个对象的MongoDB集合,格式如下:

{

"_id" : "1234",

"type" : "automatic",

"subtypes" : [

{

"_id" : "dfgd",

"name" : "test subtype",

"subjetRequired" : true,

},

{

"_id" : "dfgd",

"name" : "test subtype2",

"subjetRequired" : false,

}

],

"anotherField" : "some value"

}

如你所见,"subtypes"数组中的一个键的拼写错误 - "subjetRequired"而不是"subjectRequired"。

我想要更正这个键的名称。我该如何做呢?

首先,我想说明一下,我之前没有在MongoDB中做过太多的工作。

经过大量研究,我能想到的最好的解决方案如下(但并不起作用):

function remap(doc) {
     subtypes = doc.subtypes;
     var count = 0;
     subtypes.forEach(function(subtype){
         db.taskType.update({"_id": subtype._id}, {
             $set: {"subtypes.subjectRequired" : subtype.subjetRequired},
             $unset: {"subtypes.subjetRequired": 1}
         });
     }
     )
}
db.taskType.find({"subtypes.subjetRequired":{$ne:null}}).forEach(remap);

这个方法不起作用。

我知道循环是正确的,因为如果我用print语句替换其他逻辑,我可以访问并打印我想要修改的字段。

我在这里做错了什么?

0
0 Comments

在MongoDB中,如果我们想要修改嵌套数组对象中的字段名/键,可以使用以下的更新操作来实现,而且这种方法非常稳定,可以多次执行而不用担心出错。

db.collection.updateMany(
  {
    "subtypes.subjetRequired": { $exists: true }
  },
  [
    {
      $set: {
        subtypes: {
          $map: {
            input: "$subtypes",
            in: {
              $mergeObjects: [
                "$$this",
                {
                  subjectRequired: "$$this.subjetRequired"
                }
              ]
            }
          }
        }
      }
    },
    {
      $unset: "subtypes.subjetRequired"
    }
  ]
)

这段代码中,我们使用了`updateMany()`方法来更新集合中的多个文档。首先,我们使用了查询条件`{"subtypes.subjetRequired": { $exists: true }}`来找到包含需要修改字段的文档。

然后,在更新操作中,我们使用了`$set`运算符来设置新的`subtypes`字段。在这里,我们使用`$map`运算符来遍历`subtypes`数组,并使用`$mergeObjects`运算符将原始文档和新的字段合并起来,形成一个新的对象。

最后,我们使用`$unset`运算符来删除原始字段`subjetRequired`。

通过这种方式,我们可以修改嵌套数组对象中的字段名/键,并且可以多次执行该操作而不用担心出错。

你可以在Mongo Playground中查看示例并进行测试。

0
0 Comments

问题出现的原因是作者需要修改嵌套数组中对象的字段名/键名称,但是作者现有的解决方法只适用于小型对象,而实际上作者处理的对象可能有数百个字段。

为了解决这个问题,可以使用以下方法:

function remap(doc) {
  correctSubtypes = doc.subtypes.map(({ subjetRequired, ...rest }) => ({
    ...rest,
    subjectRequired: subjetRequired,
  }));
  var count = 0;
  db.taskType.findByIdAndUpdate(doc._id, {
    $set: {
      subtypes: correctSubtypes,
    },
  });
}

0