javascript - 从 MongoDB 中的对象字段中删除数组

标签 javascript node.js mongodb

我试图通过通过数组元素中的 ObjectId 找到它来删除数组的元素。正在关注MongoDB opposite of $addToSet to '$removeFromSet' ,我应该能够做到:

db.collection.update(
  {name: 'nameOfNode'}, 
  {$pull: { activities: ["5e7d16e9736bb64bdd158c13"]}})

db.collection.update(
  {name: 'nameOfNode'}, 
  {$pull: { activities: ["5e7d16e9736bb64bdd158c13", "Materi"]}})

但是上面的这两个代码都不起作用,是否有另一种方法可以仅通过一个值删除它们,或者如果不可能,则使用两个值删除它们?

current data schema

Note: I have removed some confidential information from the screenshot, hence the supposed gaps between the letters are not spaces, but covered texts. The strings I've tried to use to refer to them are identical though, no difference.

最佳答案

我发现代码有两个问题: - 该值不是 activities 数组的成员,而是 activities 数组中包含的数组的成员 - 搜索像 activities: ["5e7d16e9736bb64bdd158c13"] 这样的字符串将不会匹配 ObjectId 类型的值。

我运行了一个匹配 ObjectId 的快速演示:

MongoDB Enterprise replset:PRIMARY> db.updtest.find()  
{ "_id" : ObjectId("5e7d354ccede22b56b5335bc"), "name" : "nameOfNode", "activities" : [ [ ObjectId("5e7d354ccede22b56b5335b9"), "Check-in" ], [ ObjectId("5e7d354ccede22b56b5335ba"), "Materi" ], [ ObjectId("5e7d354ccede22b56b5335bb"), "Materi" ] ] }

MongoDB Enterprise replset:PRIMARY> db.updtest.update({"name" : "nameOfNode"},{$pull:{"activities.0":ObjectId("5e7d354ccede22b56b5335b9")}})  
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })

MongoDB Enterprise replset:PRIMARY> db.updtest.find()  
{ "_id" : ObjectId("5e7d354ccede22b56b5335bc"), "name" : "nameOfNode", "activities" : [ [ "Check-in" ], [ ObjectId("5e7d354ccede22b56b5335ba"), "Materi" ], [ ObjectId("5e7d354ccede22b56b5335bb"), "Materi" ] ] }

请注意,虽然这成功删除了 ObjectId 值,但它并没有删除包含的数组,这正是我认为您想要的。

如果您使用的是 MongoDB 4.2,则可以使用 $filter 删除整个子元素,例如:

db.updtest.update(
      {"name" : "nameOfNode"},
      [ {$set:{
         activities:{
             $filter:{
                 input:"$activities",
                 cond:{$ne:["$this.0",ObjectId("5e7d16e9736bb64bdd158c13")]}
             }
          }
      }}]
)

如果您可以修改架构,请将事件作为对象而不是子数组插入。例如,如果每个事件的形式为 {id:... type: ...},您可以使用 $pull:

匹配特定 id
MongoDB Enterprise replset:PRIMARY> db.updtest.find()
{ "_id" : ObjectId("5e7d3939cede22b56b5335c4"), "name" : "nameOfNode", "activities" : [ { "id" : ObjectId("5e7d3939cede22b56b5335c1"), "type" : "Check-in" }, { "id" : ObjectId("5e7d3939cede22b56b5335c2"), "type" : "Materi" }, { "id" : ObjectId("5e7d3939cede22b56b5335c3"), "type" : "Materi" } ] }

MongoDB Enterprise replset:PRIMARY> db.updtest.update({"name" : "nameOfNode"},{$pull:{"activities":{id:ObjectId("5e7d3939cede22b56b5335c2")}}})
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })

MongoDB Enterprise replset:PRIMARY> db.updtest.find()
{ "_id" : ObjectId("5e7d3939cede22b56b5335c4"), "name" : "nameOfNode", "activities" : [ { "id" : ObjectId("5e7d3939cede22b56b5335c1"), "type" : "Check-in" }, { "id" : ObjectId("5e7d3939cede22b56b5335c3"), "type" : "Materi" } ] }

关于javascript - 从 MongoDB 中的对象字段中删除数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60876824/

相关文章:

javascript - AngularJS 的面向对象方法

javascript - 如何设置元素的不透明度?

javascript - 如何使用 JQuery 选中复选框

node.js - Socket.io + SSL + 自签名 CA 证书在连接时出错

javascript - 使用 AngularJS 解析 JSON

node.js - 在 Ubuntu 上使用 npm/node 停止 EACCES 错误?

node.js - 如何用 crypto.randomBytes() 代替 Math.random()

mongodb - Mongorestore 一直向我抛出 "(NotMaster) not master"错误

node.js - 如何让 Elasticsearch 与 MongoDb 和 node.js 一起玩?

mongodb - Mongodb collection.Find()返回过滤后的数据