使用$操作符多条件更新MongoDB数组子元素问题求助
解决MongoDB数组元素更新失败的问题
你的问题出在数组元素的匹配条件写法上,默认情况下,当你用{"services.service":"service1", "services.instanceId":1}作为查询条件时,MongoDB会理解为:文档的services数组中存在至少一个元素的service是service1,并且存在至少一个元素的instanceId是1(这两个元素可以不是同一个)。这时候$操作符只会匹配第一个满足services.service="service1"的元素(也就是instanceId=0的那个),所以你的更新操作实际上修改的是第一个元素,而不是你目标的instanceId=1的元素。
正确的解决方案:使用$elemMatch匹配数组内的多条件元素
你需要用$elemMatch来明确指定:要匹配的是services数组中同时满足service="service1"和instanceId=1的那个元素。修正后的更新语句如下:
db.device.update( {"services": {"$elemMatch": {"service": "service1", "instanceId": 1}}}, {"$set": {"services.$.attributes.attr.value": "val3"}}, {} )
验证结果
执行完上述语句后,你可以用db.device.findOne()查看文档,会发现instanceId=1的元素的attr.value已经被更新为val3:
{ "services": [ { "service": "service1", "instanceId": 0, "attributes": { "attr": { "value": "val1" } } }, { "service": "service1", "instanceId": 1, "attributes": { "attr": { "value": "val3" } } } ] }
补充:MongoDB 3.2+的另一种写法(数组过滤操作符)
如果你使用的是MongoDB 3.2及以上版本,也可以使用数组过滤操作符$[<identifier>]来更灵活地定位元素,写法如下:
db.device.update( {}, {"$set": {"services.$[elem].attributes.attr.value": "val3"}}, { "arrayFilters": [{"elem.service": "service1", "elem.instanceId": 1}] } )
这种写法的好处是可以一次性更新多个符合条件的数组元素,而$elemMatch配合$操作符只能更新第一个匹配的元素。
内容的提问来源于stack exchange,提问作者Sachin Gupta
相关产品推荐
相关产品推荐

