MongoDB Secondary 延时高(同步锁)问题分析

本文涉及的产品
云原生多模数据库 Lindorm,多引擎 多规格 0-4节点
云数据库 Redis 版,社区版 2GB
推荐场景:
搭建游戏排行榜
云数据库 MongoDB,通用型 2核4GB
简介: 背景介绍 MongoDB 复制集里 Secondary 不断从主上批量拉取 oplog,然后在本地重放,以保证数据与 Primary 一致。同步原理参考MongoDB复制集同步原理解析 Secondary 拉取到一批 oplog 后,在重放这批 oplog 时,会加一个特殊的 Lock::ParallelBatchWriterMode 的锁,这个锁会阻塞所有的读请求,直到这批 oplog 重放完成。

背景介绍

  • MongoDB 复制集里 Secondary 不断从主上批量拉取 oplog,然后在本地重放,以保证数据与 Primary 一致。同步原理参考MongoDB复制集同步原理解析
  • Secondary 拉取到一批 oplog 后,在重放这批 oplog 时,会加一个特殊的 Lock::ParallelBatchWriterMode 的锁,这个锁会阻塞所有的读请求,直到这批 oplog 重放完成。这么做的原因有2个

    • 尽量避免脏读,等一批 oplog 重放完后,这批数据才允许用户读到。
    • 尽量保证同步性能,设想一下,如果重放 oplog 时,使用普通的锁,那么 oplog 的重放就需要跟正常的读写竞争锁资源,如果 Secondary 上有大量的读,那么势必会造成备同步逐步跟不上。参考 SERVER-18190

案例分析

基于上述问题,某些用户在读取备节点时,可能遇到因为 Secondary 重放 oplog 占用特殊锁时间较长,导致读取的延时变长。

问题1:单个请求耗时长

一个长达1小时的『前台创建索引』请求,在 Secondary 节点上重放时,一直占用 ParallelBatchWriterMode 锁,导致 Secondary 上所有请求阻塞长达1小时,这个案例我在Secondary节点为何阻塞请求近一个小时? 里已经分析过,这里不再赘述,解决方案是尽量后台建索引。

上述场景除了会影响 Secondary 上的读请求,如果 Priamry 上写请求指定了 writeConcern 来写多个节点({w: 2+}),而 Secondary 又一直阻塞在创建索引上,导致其后的oplog 重放都要等待创建索引结束,从而主上的写入也阻塞。

问题2:多个请求加起来耗时长

当主上写入并发很大时,Secondary 每次能拉到很多条 oplog,然后并发重放,重放一条的耗时可能很小,但累计起来一次重放上百、上千条 oplog,耗时就会高很多,而重放过程中,Secondary 上读请求都是要阻塞等待的,所以总体看上去,「Secondary 上平均延时,可能比 Primary 上更长点」(这就是为什么很多用户在写入比较多时,会发现读secondary 比 读praimry 更慢),但只要延时在可接受范围内,这个问题并无影响,而且根据云上用户使用的经验,绝大部分用户都是感受不到这个差异的。

但有一种情况值要注意

update

从上面的例子可以看到,一条 update 操作,指定了 {multi: true} 选项,更新了2个匹配的文档,针对每个文档都产生了一条 oplog(主要为了保证 oplog 幂等性),如果匹配的文档有成千上万条,就会产生对应数量的 oplog,然后 Secondary 拉取这些 oplog 并重放;这个场景下,update 的开销在Secondary 上被放大多倍,此时Secondary 的读延时可能会受比较大的影响。

如何评估重放 oplog 时锁的影响有多大?

从上述的例子可以看出,Secondary 在某些场景下会出现读延时很高的情况,那么当实际遇到问题时,如何判断问题就是 Secondary 重放 oplog 占用锁时间太长导致呢?

我们的做法是增加审计日志,把『Secondary 节点重放每一批 oplog 的时间开销记录到审计日志』里,这样就能很方便的看出影响到底有多大,如下是一个『简化版本的加日志的patch』,有需要的可以应用到 MongoDB 3.2上。

diff --git a/src/mongo/db/repl/sync_tail.cpp b/src/mongo/db/repl/sync_tail.cpp
index 50517c2..e7d58bc 100644
--- a/src/mongo/db/repl/sync_tail.cpp
+++ b/src/mongo/db/repl/sync_tail.cpp
@@ -550,6 +550,8 @@ OpTime SyncTail::multiApply(OperationContext* txn,
     // stop all readers until we're done
     Lock::ParallelBatchWriterMode pbwm(txn->lockState());

+    unsigned long long startTime = curTimeMicros64();
+
     if (inShutdownStrict()) {
         log() << "Cannot apply operations due to shutdown in progress";
         return OpTime();
@@ -585,6 +587,8 @@ OpTime SyncTail::multiApply(OperationContext* txn,
         setMinValid(txn, boundaries->end, DurableRequirement::None);  // Mark batch as complete.
     }

+    log() << "batch writer cost " << (curTimeMicros64() - startTime) << us;
+
     return lastOpTime;
 }

参考资料

相关实践学习
MongoDB数据库入门
MongoDB数据库入门实验。
快速掌握 MongoDB 数据库
本课程主要讲解MongoDB数据库的基本知识,包括MongoDB数据库的安装、配置、服务的启动、数据的CRUD操作函数使用、MongoDB索引的使用(唯一索引、地理索引、过期索引、全文索引等)、MapReduce操作实现、用户管理、Java对MongoDB的操作支持(基于2.x驱动与3.x驱动的完全讲解)。 通过学习此课程,读者将具备MongoDB数据库的开发能力,并且能够使用MongoDB进行项目开发。 &nbsp; 相关的阿里云产品:云数据库 MongoDB版 云数据库MongoDB版支持ReplicaSet和Sharding两种部署架构,具备安全审计,时间点备份等多项企业能力。在互联网、物联网、游戏、金融等领域被广泛采用。 云数据库MongoDB版(ApsaraDB for MongoDB)完全兼容MongoDB协议,基于飞天分布式系统和高可靠存储引擎,提供多节点高可用架构、弹性扩容、容灾、备份回滚、性能优化等解决方案。 产品详情: https://www.aliyun.com/product/mongodb
相关文章
|
存储 JSON NoSQL
插入大量数据至MongoDB数据库的速度问题分析
插入大量数据至MongoDB数据库的速度问题分析
|
NoSQL 数据库
MongoDB副本集--Secondary节点恢复实例
MongoDB副本集中有一台Secondary节点出现RECOVERING的状态 点击(此处)折叠或打开 arps:RECOVERING> rs.
1740 0
|
NoSQL
Mongodb 通过一致性备份搭建SECONDARY.
该方法应用面比较窄, 适用于 : 一主 一备 一投票节点,数据库较大,oplog 比较小,备库需要修复而且主库不能停机的情况.
3519 0
|
存储 NoSQL
MongoDB Secondary同步慢问题分析(续)
在MongoDB Scondary同步慢问题分析文中介绍了因Primary上写入qps过大,导致Secondary节点的同步无法追上的问题,本文再分享一个case,因oplog的写入被放大,导致同步追不上的问题。 MongoDB用于同步的oplog具有一个重要的『幂等』特性,也就是说,一条oplo
|
存储 NoSQL MongoDB
MongoDB Secondary同步慢问题分析
MongoDB Scondary同步慢问题分析 问题背景 最近生产环境出现多次Primary写入QPS太高,导致Seconary的同步无法跟上的问题(Secondary上的最新oplog时间戳比Primary上最旧oplog时间戳小),使得Secondary变成RECOVERING状态,这时需要
|
1月前
|
存储 NoSQL MongoDB
MongoDB如何创建数据库
MongoDB如何创建数据库
|
3天前
|
存储 NoSQL 关系型数据库
MongoDB非关系型数据库实战
【5月更文挑战第6天】MongoDB,流行的NoSQL数据库,以其灵活的数据模型和高性能备受青睐。本文介绍了MongoDB的基础,包括文档型数据库特性、安装配置、数据操作。通过电商订单管理的实战案例,展示了MongoDB在处理复杂数据结构和大规模数据时的优势,适用于电商、游戏、视频直播等场景。MongoDB的索引、全文搜索和地理空间功能进一步增强了其实用性。注意性能优化和扩展性以确保系统稳定性和可靠性。
|
10天前
|
弹性计算 NoSQL Shell
一键安装 MongoDB 数据库脚本
【4月更文挑战第29天】
16 4
|
16天前
|
NoSQL MongoDB 数据库
MongoDB数据恢复—MongoDB数据库文件被破坏的数据恢复案例
服务器数据恢复环境: 一台Windows Server操作系统服务器,服务器上部署MongoDB数据库。 MongoDB数据库故障&检测: 工作人员在未关闭MongoDB数据库服务的情况下,将数据库文件拷贝到其他分区。拷贝完成后将原MongoDB数据库所在分区进行了格式化操作,然后将数据库文件拷回原分区,重新启动MongoDB服务,服务无法启动。

相关产品

  • 云数据库 MongoDB 版