Удалите объекты JSON с определенным типом поля из поля массива JSON в документе MongoDB.

Дана коллекция с документами, у которых есть поле массива, содержащее объекты JSON (пары ключ-значение), например:

{ ..., arr : [{key: val}, {key : NumberLong(100)}]}

После обновления тот же документ должен выглядеть так:

{ ..., arr : [{key: val}]}

Документ в поле arr:

{ключ: NumberLong(100)}

следует удалить.

Можно ли это сделать с операторами MongoDB $? Я пытался использовать следующий код безрезультатно:

 db.coll.find({}).forEach( function(doc) {
     var objs = doc.arr;
     for(var i = objs.length; i--;){
         if (typeof(objs[i].ts) == NumberLong)
             objs.splice(i,1);
     }
     db.coll.save(doc);
})

person rok    schedule 21.03.2014    source источник


Ответы (1)


Я полагаю, вы хотите удалить данные из массива следующим образом:

{ 
    "field" : "aaa", 
    "list" : [  "aaa",  NumberLong(123),  "bbb",  NumberLong(456) ] 
}

Вы можете сделать это, используя $pull, так как он принимает выражение запроса, поскольку оно аргумент

 db.collection.update({ },{ "$pull": { "list": {"$type": 18 } } })

Редактировать

Поскольку вопрос изменился, он по-прежнему мало что меняет в ответе:

{ 
    "list" : [
        { "key" : "val" }, 
        { "key" : NumberLong(100) },
        { "key" : NumberLong(123) } 
    ] 
}

И в основном с тем же запросом:

 db.list.update({ }, { "$pull": { "list": { "key": {"$type": 18  } } } })

Затем все типы NumberLong() удаляются.


Добавьте { "multi": true } там, где вы хотите, чтобы это происходило в нескольких документах.

Таким образом, используется $type для сопоставления элементов "NumberLong", которые являются 64-битными целыми числами. Значения для каждого «типа» указаны на странице руководства.

Оператор positional $ здесь не подходит, так как:

  1. Это не допустимый аргумент для чего-либо, что можно использовать для удаления элементов.

  2. Даже при использовании с $set и последующей "установке" значения false, вам будет соответствовать только первый элемент, соответствующий массиву. В любом случае вы не удаляете элемент, и вам все равно нужно будет использовать pull.

Кроме того, в вашем методе JavaScript typeof(), который вы ищете, не вернет ничего, кроме object, что и является реализацией JavaScript. Вам придется проверить по-другому.

Но не надо. наилучшим способом является использование собственных методов обновления.

person Neil Lunn    schedule 22.03.2014
comment
Спасибо. Извините, я ошибся в своем вопросе. Массив содержит объекты JSON. - person rok; 22.03.2014
comment
@user1264304 user1264304 Это не имеет никакого значения для ответа. Я добавил ваш конкретный пример, чтобы показать вам, как это сделать. - person Neil Lunn; 23.03.2014