Mongodb 对空数组使用$push

Mongodb 对空数组使用$push,mongodb,Mongodb,我有一个mongo文档,它有一个名为events的数组字段 此字段有时可以为空 我使用$push将元素添加到事件数组中。问题是,当events字段为null时,它无法工作 例如,如果在数据库中,它如下所示: { "_id" : ObjectId("4d2d8deff4e6c1d71fc29a07"), "user_id" : "714638ba-2e08-2168-2b99-00002f3d43c0", "

我有一个mongo文档,它有一个名为events的数组字段

此字段有时可以为空

我使用$push将元素添加到事件数组中。问题是,当events字段为null时,它无法工作

例如,如果在数据库中,它如下所示:

{
"_id" : ObjectId("4d2d8deff4e6c1d71fc29a07"),
"user_id" : "714638ba-2e08-2168-2b99-00002f3d43c0",
"events" : null
 }
我使用$push运行更新:

{ $push : { "events" : { "profile" : 10, "data" : "X"}}};
它将失败,因为事件为null

我可以通过查询数据库的两个步骤来解决这个问题。但是,我可以在1个查询中完成吗


如果数组字段不为null,我想将事件添加到数组中,但如果为null,则首先创建事件空数组,然后将事件添加到数组中。

不要为没有数据的字段写入null值。然后您将能够以预期的方式使用$push:

MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.insert({a:1})
WriteResult({ "nInserted" : 1 })
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.update({a:1},{$push:{b:[1]}})
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b481dd9c782d95389a1ce"), "a" : 1, "b" : [ [ 1 ] ] }
如果坚持将空值写入数据库,则可以使用聚合管道更新和$set、$ifNull、$concatarray和$merge:

MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.insert({a:2,b:null})
WriteResult({ "nInserted" : 1 })
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b4bfbd9c782d95389a1d2"), "a" : 2, "b" : null }
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.aggregate([{$match:{a:2}},{$set:{b:{$ifNull:[{$concatArrays:['$b',[4]]},[4]]}}},{$merge:'foo'}])
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b4bfbd9c782d95389a1d2"), "a" : 2, "b" : [ 4 ] }
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.aggregate([{$match:{a:2}},{$set:{b:{$ifNull:[{$concatArrays:['$b',[5]]},[5]]}}},{$merge:'foo'}])
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b4bfbd9c782d95389a1d2"), "a" : 2, "b" : [ 4, 5 ] }

不要为没有数据的字段写入空值。然后您将能够以预期的方式使用$push:

MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.insert({a:1})
WriteResult({ "nInserted" : 1 })
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.update({a:1},{$push:{b:[1]}})
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b481dd9c782d95389a1ce"), "a" : 1, "b" : [ [ 1 ] ] }
如果坚持将空值写入数据库,则可以使用聚合管道更新和$set、$ifNull、$concatarray和$merge:

MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.insert({a:2,b:null})
WriteResult({ "nInserted" : 1 })
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b4bfbd9c782d95389a1d2"), "a" : 2, "b" : null }
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.aggregate([{$match:{a:2}},{$set:{b:{$ifNull:[{$concatArrays:['$b',[4]]},[4]]}}},{$merge:'foo'}])
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b4bfbd9c782d95389a1d2"), "a" : 2, "b" : [ 4 ] }
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.aggregate([{$match:{a:2}},{$set:{b:{$ifNull:[{$concatArrays:['$b',[5]]},[5]]}}},{$merge:'foo'}])
MongoDB Enterprise ruby-driver-rs:PRIMARY> db.foo.find()
{ "_id" : ObjectId("5f0b4bfbd9c782d95389a1d2"), "a" : 2, "b" : [ 4, 5 ] }

你可以使用MogoDB 4.2。这允许作为单个操作执行更新

var OBJ_TO_ADD = { "profile": 10, "data": "X" }

db.test.updateOne(
  { "_id" : ObjectId("4d2d8deff4e6c1d71fc29a07") }, 
  [ 
      { 
          $set: { 
              events: { 
                  $ifNull: [ 
                      { $concatArrays: [ "$events", [ OBJ_TO_ADD ] ] }, 
                      [ OBJ_TO_ADD ] 
                  ] 
              }
          }
      } 
  ] 
)

你可以使用MogoDB 4.2。这允许作为单个操作执行更新

var OBJ_TO_ADD = { "profile": 10, "data": "X" }

db.test.updateOne(
  { "_id" : ObjectId("4d2d8deff4e6c1d71fc29a07") }, 
  [ 
      { 
          $set: { 
              events: { 
                  $ifNull: [ 
                      { $concatArrays: [ "$events", [ OBJ_TO_ADD ] ] }, 
                      [ OBJ_TO_ADD ] 
                  ] 
              }
          }
      } 
  ] 
)

事件不能是空数组而不是空数组吗?这应该更一致。问题是,我不知道events字段是否不存在,或者有时也可能为null:/这不是一个修正字段。。尽管我同意处理这个问题的最佳方法,但就是始终创建它,即使它是空的。你能不能用空数组代替空数组?这应该更一致。问题是,我不知道events字段是否不存在,或者有时也可能为null:/这不是一个修正字段。。尽管我同意处理这个问题的最好方法,就是总是创建它,即使它是空的