【问题标题】:MongoDB Push With Positional Operator Not Working位置运算符不工作的 MongoDB 推送
【发布时间】:2015-01-25 10:18:06
【问题描述】:

我在“用户”集合中有以下文档

{
    "_id" : "388179687996974",
    "matches" : [ 
        {
            "userId" : "1495728740672094",
            "choice" : false,
            "dates" : [],
            "dateId" : null
        }, 
        {
            "userId" : "385516561596016",
            "choice" : true,
            "dates" : [],
            "dateId" : "2014-11-26_385516561596016_388179687996974"
        }, 
        {
            "userId" : "253752728167114",
            "choice" : false,
            "dates" : [],
            "dateId" : null
        }, 
        {
            "userId" : "365296866955687",
            "choice" : null,
            "dates" : [ 
                "2014-11-26"
            ],
            "dateId" : null
        }
    ],
    "playDates" : [ 
        "2014-11-26"
    ]       
}

我有以下问题

db.users.find({
  "_id":{"$ne":"385516561596016"},
  "playDates":{"$in":["2014-11-26"]},
  "matches":{"$elemMatch":{
        "userId":"385516561596016",
        "dates":{"$nin":["2014-11-26"]}}}})

它返回上面的文档。

我正在尝试使用位置运算符更新文档,如下所示:

db.users.update({
    "_id":{"$ne":"385516561596016"}, 
    "playDates":{"$in":["2014-11-26"]},
    "matches":{"$elemMatch":{"userId":"385516561596016",
          "dates":{"$nin":["2014-11-26"]}}}}, 
    {"$push":{"matches.$.dates":"2014-11-26"}})

它没有将 2014-11-26 放入用户 ID 385516561596016 的匹配项中,而是将其放入匹配项 [0] 中。

我做错了什么?

【问题讨论】:

    标签: node.js mongodb mongodb-query


    【解决方案1】:

    这闻起来像一个 mongodb 错误。我尝试了几种不同的变体。

    db.items.update({
    "_id":{"$ne":"385516561596016"},     
        //without the playDates $in clause
    "matches":{"$elemMatch":{"userId":"253752728167114"} } } , 
    {"$push":{"matches.$.dates":"test"} } )
    

    这按预期工作,将“测试”放入第三项。

    这不是 $push 运算符的错误,因为 $set 也搞砸了:

    db.items.update({
    "_id":{"$ne":"385516561596016"},     
    "playDates":{"$in":["2014-11-26"]},
    "matches":{"$elemMatch":{"userId":"253752728167114"} } } , 
    {"$set":{"matches.$.other":"bob"} } ) 
    //fails
    
    
    db.items.update({
    "_id":{"$ne":"385516561596016"},     
    "matches":{"$elemMatch":{"userId":"253752728167114"} } } , 
    {"$set":{"matches.$.other":"joe"} } )
    //success
    

    我认为你应该在 JIRA 上报告它。 https://jira.mongodb.org/secure/Dashboard.jspa(如果你幸运的话,他们可能会在一年内修复它。到目前为止,他们已经修复了我的 1/8 问题。)

    与此同时,也许您可​​以更改您的应用逻辑,以便不需要对 playDates 进行 $in 查询?

    【讨论】:

    • 使用玩具数据库的乐趣。您能想到任何潜在的解决方法吗?
    【解决方案2】:

    问题是您在一个查询中查询两个数组:playDatesmatches

    MongoDB 将您的数据放入 matches[0],因为您的查询匹配 playDates[0]{"$in":["2014-11-26"]},因此 MongoDB 将 $ 绑定到其索引 0。

    不幸的是,我不知道如何在不删除 "playDates":{"$in":["2014-11-26"]} 部分的情况下修复它。

    【讨论】:

      【解决方案3】:

      问题是您试图在单个查询文档中匹配来自两个不同数组的值-matchesplayDates-。 MongoDB 目前不支持此功能。

      根据dos

      查询文档应该只包含数组上的单个条件 被投影的场。多个条件可以相互覆盖 内部并导致未定义的行为。

      在这些要求下,以下查询不正确:

       db.collection.find( { <array>: <value>, <someOtherArray>: <value2> },
                          { "<array>.$": 1 } )
      

      由于使用$ 更新其中一个数组中的匹配子文档,导致undefined 行为,解决方法是触发两个查询,一个查找文档,另一个更新一次这些值在应用代码中进行了修改。

      【讨论】:

        猜你喜欢
        • 2021-09-18
        • 1970-01-01
        • 2012-01-17
        • 2021-07-26
        • 1970-01-01
        • 2015-01-12
        • 2014-06-27
        • 1970-01-01
        • 2017-01-15
        相关资源
        最近更新 更多