MongoDB,具有增量属性的对象的数组字段

时间:2017-03-11 08:16:09

标签: mongodb mongodb-query

我理解这个问题有点令人困惑。忍受我,

假设我有一个Class文档,其中包含Students属性作为数组。现在这些学生应该有一个增量Id但我不知道如果有并发插入推送查询到文档,该怎么做。

示例:

假设class是我在db中的文档。

var class = {
   'students':[{
      'name': 'Bob'
       'id' :1
   }]
}

现在,如果我要插入,请将学生Sally({'name': 'Sally'})推送到class.students我希望她能获得2作为身份。

我可以查询获取db中的最新id并将其递增1并将其用作Sally的id。

但是,我不知道当两个不同的请求同时发生时会发生什么,其中一个尝试插入推送Sally和另一个Jack。我怎样才能确保Sally和Jack没有得到同样的身份?

一张纸条;我不想依赖id字段的数组索引。

1 个答案:

答案 0 :(得分:1)

您可以在计数器收集的帮助下完成此操作

1.插入计数器集合,即studentId的初始值:

db.counters.insert(
   {
      _id: "studentId",
      seq: 0
   }
) 

2。创建一个接受序列名称的getNextSequence函数。该函数使用findAndModify()方法原子增加seq值并返回此新值

function getNextSequence(name) {
   var ret = db.counters.findAndModify(
          {
            query: { _id: name },
            update: { $inc: { seq: 1 } },
            new: true
          }
   );

   return ret.seq;
}

由于findAndModify是原子操作,getNextSequence()将始终返回下一个值,即使是并发请求。

3.在插入/推送

期间使用此getNextSequence()函数
//let's assume you already have a 'student' variable that represents a student doc
student['id'] = getNextSequence("studentId");
db.classes.update(
   { _id: 1 },
   { $addToSet: { students: student  } }
)

有关自动递增序列字段的更多详细信息,请参阅MongoDb网站上的corresponding tutorial