MongoDB:锁机制 (Concurrency)

今天了解了 MongoDB 的锁机制,与传统 RDMBS MVCC 机制相差较大,它在一些方面的特性比较特殊,下面简单介绍下:

1 MongoDB 使用的锁

MongoDB 使用的是“readers-writer”锁,可以支持并发但有很大的局限性,当一个读锁存在,许多读操作可以使用这把锁,然而, 当一个写锁的存在,一个单一的写操作会 exclusively 持有该锁,同时其它读,写操作不能使用共享这个锁;举个例子,假设一个集合里有 10 个文档,多个 update 操作不能并发在这个集合上,即使是更新不同的文档。

2 锁的粒度

在 2.2 版本以前,mongod 只有全局锁;在 2.2 版本开始,大部分读写操作只锁一个库,相对之前版本这个粒度已经下降,例如如果一个 mongod 实例上有 5 个库,如果只对一个库中的一个集合执行写操作,那么在写操作过程中,这个库被锁;而其它 5 个库不影响。相比 RDBMS 来说,这个粒度已经算很大了!

3 如何查看锁的状态

1
2
3
4
5
db.serverStatus()  
db.currentOp()
mongotop
mongostat
the MongoDB Monitoring Service (MMS)

4 哪些操作会对数据库产生锁?

下表列出了常见数据库操作产生的锁。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
Operation
Lock Type
Issue a query
Read lock
Get more data from a[cursor](http://docs.mongodb.org/manual/reference/glossary/#term-cursor)
Read lock
Insert data
Write lock
Remove data
Write lock
Update data
Write lock
[Map-reduce](http://docs.mongodb.org/manual/reference/glossary/#term-map-reduce)
Read lock and write lock, unless operations are specified as non-atomic. Portions of map-reduce jobs can run concurrently.
Create an index
Building an index in the foreground, which is the default, locks the database for extended periods of time.
[db.eval()](http://docs.mongodb.org/manual/reference/method/db.eval/#db.eval "db.eval")
Write lock.[db.eval()](http://docs.mongodb.org/manual/reference/method/db.eval/#db.eval "db.eval")blocks all other JavaScript processes.
[eval](http://docs.mongodb.org/manual/reference/commands/#eval "eval")
Write lock. If used with thenolocklock option, the[eval](http://docs.mongodb.org/manual/reference/commands/#eval "eval")option does not take a write lock and cannot write data to the database.
[aggregate()](http://docs.mongodb.org/manual/reference/method/db.collection.aggregate/#db.collection.aggregate "db.collection.aggregate")
Read lock

5 哪些数据库管理操作会锁数据库?

某些数据库管理操作会 exclusively 锁住数据库,以下命令需要申请 exclusively 锁,并锁定一段时间

1
2
3
4
5
6
7
db.collection.ensureIndex(),  
reIndex,
compact,
db.repairDatabase(),
db.createCollection(), when creating a very large (i.e. many gigabytes) capped collection,
db.collection.validate(),
db.copyDatabase().This operation may lock all databases

以下命令需要申请 exclusively 锁,但锁定很短时间。

1
2
3
4
5
6
7
db.collection.dropIndex(),  
db.collection.getLastError(),
db.isMaster(),
rs.status() (i.e. replSetGetStatus,)
db.serverStatus(),
db.auth(), and
db.addUser().

备注:可见,一些查看命令也会锁库,在比较繁忙的生产库中,也会有影响的。

6 锁住多个库的操作

以下数据库操作会锁定多个库。

1
2
3
4
5
6
db.copyDatabase() must lock the entire mongod instance at once.  
Journeying, which is an internal operation, locks all databases for short intervals.
All databases share a single journal.
User authentication locks the admin database as well as the database the user is accessing.
All writes to a replica set’s primary lock both the database receiving the writes and the
local database. The lock for the local database allows the mongod to write to the primary’s oplog.

7 参考

http://docs.mongodb.org/manual/faq/concurrency/
http://blog.163.com/dazuiba_008/blog/static/36334981201211112221314/

原创文章,作者:bd101bd101,如若转载,请注明出处:https://blog.ytso.com/237932.html

(0)
上一篇 2022年1月29日
下一篇 2022年1月29日

相关推荐

发表回复

登录后才能评论