使用$ addToSet时MongoDB数组的最大大小

时间:2015-01-14 15:00:24

标签: javascript node.js mongodb mongoose mongodb-query

使用:

 db.collection('users').update(
     { "_id": user._id},
     { "$addToSet": { "keywords.RFD": keywords } },
     function(err, result) {
         if (err) {
             console.log(
               'failed to add keyword "%s" for user: %s', keywords, user.email);
                    throw err;
          }
          else {
              console.log('Keyword added: ' + keywords );
              res.end('{"success" : "Updated Successfully.", "status" : 200}');
          }
   }
);

我想将关键字的数量限制为50,如果关键字超过50则抛出错误。无论如何,如果数据库中已有50个,我可以查看MongoDB吗?

3 个答案:

答案 0 :(得分:1)

告诉你什么。您没有正确阅读文档。所以keywords是一个用词不当"这里因为在这种情况下它只能是单个字符串或其他对象。当然不是阵列。

MongoDB有办法解决这个问题。就像我给出指针一样,你需要阅读$each文档以及other modifiers

db.collection('users').update(
  { "_id": user._id},
  { 
    "$addToSet": { 
      "keywords.RFD": {
         "$each": [keywords],
      }
  }
)

然后,您实际上可以通过空白调用$slice来调用单独的更新语句来调用$each。哪个有趣可笑完美。

db.collection('users').update(
  { "_id": user._id},
  { 
    "$push": { 
      "keywords.RFD": {
         "push": {"$each": [] },
      },
      "$slice": -50
  }
)

这里的主键修饰符是$slice,它是"限制"的形式。数组的大小。

请注意,您需要MongoDB 2.6或更高版本作为服务器版本,以使这些运算符在更新时有效。如果您需要这种互动,这是升级的一个令人信服的理由。

P.S。正如我之前所说,"关键字的背景"在你的例子中是一个用词不当"因为它是一个"标量"值。在$each修饰符下,这确实可以是一个数组。因此:

db.collection('users').update(
  { "_id": user._id},
  { 
    "$addToSet": { 
      "keywords.RFD": {
         "$each": { "$each: keywords },
      }
  }
)
db.collection('users').update(
  { "_id": user._id},
  { 
    "$push": { 
      "keywords.RFD": {
         "push": [],
      },
      "$slice": -50
  }
)

不是原子的。但是尽可能接近,尤其是在使用批量API时。

答案 1 :(得分:0)

我想也许有一种方法可以使用像封顶数组这样的MongoDB为数组本身添加一个严格的限制,但我认为这是不可能的。我最后只使用逻辑。

if (user.settings.max_keywords <= result.keywords.RFD.length){
        res.end('{"error" : "Too many keywords.", "status" : 401}');
      }

答案 2 :(得分:0)

const MAX_KEYWORDS = 50;
const maxArrayPath = `keywords.RFD.${MAX_KEYWORDS - 1}`;

db.collection('users').updateOne(
  { _id: user._id,
    [maxArrayPath]: { $exists: false }
  },
  { 
    $addToSet: { 
      "keywords.RFD": keywords,
    }
  }
);