这是我参与8月更文挑战的第2天,活动详情查看:8月更文挑战
MongoDB 的读操作事务主要关心两个特性:
- readPreference 数据从哪儿读
- readConcern 读什么样的数据
readPreference
readPreference 可以指定从哪一个节点读取数据,它的可选值包括:
primary只从主节点读取primaryPreferred优先选择主节点,主节点不可用的时候选择从节点secondary只选择从节点secondaryPreferred优先选择从节点,从节点不可用的时候选择主节点nearest选择最近的节点,节点的距离是根据 ping 的结果判断的
需要实效性的数据,建议选择 primary/primaryPreferred,因为从节点可能还没有复制到新的数据;但是对于比较旧的数据,建议选择 secondary/secondaryPreferred。
对于 primary/primaryPreferred 的场景,只要业务允许,都建议选择 primaryPreferred,如果选择 primary,一旦主节点故障,将没有节点可以读取数据。
对于生成报表之类的业务,对实效性要求低,并且不会影响主业务的功能,选择 secondary 即可。
对于针对全球用户的业务,对实效性要求不高的数据,推荐使用 nearest 从最近的节点读区数据。
配置方法:
- 通过 MongoDB 的连接串参数:
mongodb://host1:27107,host2:27107,host3:27017/?replicaSet=rs&readPreference=secondary - 通过 MongoDB 驱动程序 API:
MongoCollection.withReadPreference(ReadPreference readPref) - Mongo Shell:
db.collection.find().readPref("secondary")
readConcern
readConcern 用来指定节点上的哪些数据是可以读的,这里说的「哪些数据可以读」可以理解为关系型数据库中数据的隔离级别。
它的常用取值有:
available读取所有可用的数据local读取所有可用且属于当前分片的数据majority读取在大多数节点上提交完成的数据linearizable可线性化读取文档snapshot读取最近快照中的数据
local 和 available 有什么区别?在复制集中,两者是没有区别的,它们的区别体现在分片集群上。local 只会读取对应分片负责的数据,而 available 则是有什么就读什么。虽然表面上看,应该总是选择 local,但相较于 available 对需要更多的资源消耗,因此,在一些无关紧要的场景下,应该选择 available。
为什么需要 majority?majority 用于读取在大多数节点上提交完成的数据,这主要是为了读取的安全性,防止读取数据后,MongoDB 出现数据回滚。如果读取的数据是大多数节点都提交成功的数据,就不会出现会滚。
MongoDB 的回滚是如何出现的?在写操作到达大多数节点之前,一旦主节点崩溃,从节点还没有复制到该次操作,那么操作就会丢失。