mongoose 使用mongodb在nodejs中通过锁定/事务读取和插入文档

k2arahey  于 2022-11-13  发布在  Go
关注(0)|答案(3)|浏览(316)

在预订系统中,只有5个不同的用户可以创建预订。如果100个用户同时调用预订API,那么如何处理带锁的并发。我正在使用mongodb的nodejs。我在mongodb中浏览了mongo并发article和事务,但没有找到任何带锁的示例编码解决方案。
我已经实现了乐观并发控制的解决方案(当资源的竞争很低时-这可以很容易地使用versionNumber或timeStamp字段实现)。
提前感谢您为我建议的解决方案与锁定。
现在的算法是:

步骤1:从userSettings集合中获取userAllowedNumber。

//Query
db.getCollection('userSettings').find({})

//Response Data
{ "userAllowedNumber": 5 }

步骤2,从bookings集合中获取当前bookedCount

//Query
db.getCollection('bookings').count({ })

//Response Data
2

第3步,如果bookedCount <= userAllowedNumber,则插入预订。

//Query
db.getCollection('bookings').create({ user_id: "usr_1" })
k7fdbhmy

k7fdbhmy1#

我在mongodb社区中对事务加锁进行了深入的讨论,在结论中,我了解并发现了事务的局限性,对于这个任务,我们没有可以用来处理并发请求的锁。
您可以在此链接https://www.mongodb.com/community/forums/t/implementing-locking-in-transaction-for-read-and-write/127845上查看Mongodb社区的完整对话
Github演示代码和Jmeter测试显示了限制,无法处理此任务的并发请求。https://github.com/naisargparmar/concurrencyMongo
欢迎提出新建议

bvn4nwqk

bvn4nwqk2#

要解决您的问题,您还可以尝试使用Redlock(https://redis.com/redis-best-practices/communication-patterns/redlock/)进行分布式锁定,或使用Mutex锁进行示例锁定。

ee7vknir

ee7vknir3#

对于transaction的一个简单示例,首先需要让一个客户机连接到MongoDB。

const client = new MongoClient(uri);
await client.connect();

拥有客户端后,可以创建一个会话,从中可以进行事务处理:

const session = await client.startSession();
const transactionResults = await session.withTransaction( async () => {
     await client.db().collection("example").insertOne(example);
}, transactionOptions);

其中transactionOptions为:

const transactionOptions = {
   readPreference: 'primary',
   readConcern: { level: 'majority' },
   writeConcern: { w: 'majority' }
};

在MongoDb文档中查找有关读/写的问题。根据您的使用情况,您也可以考虑findAndModify,它在更改时锁定文档。

相关问题