MongoDB更新子阵列中的所有子元素

时间:2016-03-28 06:45:10

标签: mongodb

我有一个包含以下架构的集合:

{
    "_id" : ObjectId("52dfba46daf02aa4630cf529"),
    "hotelVenue" : {
        "rooms" : [ 
            {
                "clientId" : "ROOM_1",
                "roomName" : "Executive"
            }, 
            {
                "clientId" : "ROOM_2",
                "roomName" : "Premium"
            }
        ]
    }
},
{
    "_id" : ObjectId("52dfc2f9daf02aa2632bc8af"),
    "hotelVenue" : {
        "rooms" : [ 
            {
                "clientId" : "ROOM_1",
                "roomName" : "Studio Room"
            }, 
            {
                "clientId" : "ROOM_2",
                "roomName" : "Soho Suite"
            }, 
            {
                "clientId" : "ROOM_3",
                "roomName" : "Luxury Suite"
            }
        ]
    }
}

我需要为所有记录创建唯一ID - >子阵。 即,在示例中有房间,因此对于每种房型,我需要基本上使用ObjectId()给出一个唯一的ID。

输出应该如下所示,其中roomId正在生成。

{
    "_id" : ObjectId("52dfba46daf02aa4630cf529"),
    "hotelVenue" : {
        "rooms" : [ 
            {
                "clientId" : "ROOM_1",
                "roomName" : "Executive",
                "roomId" : "56f8cb3f0c658b4bc26172342"
            }, 
            {
                "clientId" : "ROOM_2",
                "roomName" : "Premium",
                "roomId" : "56f8cb3f0c658b4bc26176d4"
            }
        ]
    }
}

我写了这个脚本,它出现以下错误:错误:第9行:意外的令牌+

db.venues.find().forEach(function(data) 
{
    data.hotelVenue.rooms.forEach(function(roomItem) 
    {
        db.venues.update({_id:data._id,'data.hotelVenue.rooms.clientId' : roomItem.clientId},
        {
            $set:
            {
                'hotelVenue.rooms.'+roomItem.clientId+'.roomId' : ObjectId()
            }
        }); 
    });
})

1 个答案:

答案 0 :(得分:1)

编辑:这应该通过仅保存每个文档一次以更有效的方式进行;

db.venues.
  find({"hotelVenue.rooms": { $elemMatch: {roomId: {$exists: 0}}}}).
  forEach(function(doc) {
    doc.hotelVenue.rooms.forEach(function(room) {
      if(!room.roomId) {
        room.roomId = ObjectId();
      }
    }); 
    db.venues.save(doc);
  });

find仅筛选出需要更新的文档。之后,只需根据需要更新文档并调用save

当然,在根据您的生产数据集从Internet上的随机用户运行可能具有破坏性的查询之前,备份是有序的。