深入解析MongoDB中的锁机制

news2024/11/15 10:35:34

目录

一、MongoDB简介

二、MongoDB锁机制

三、锁的实践影响

        3.1 高并发写入导致的写锁案例


一、MongoDB简介

       MongoDB 作为一种非关系型文档数据库,在现代应用中扮演着极其重要的角色,尤其在处理大规模、高并发、灵活数据模型的场景下。MongoDB 具有如下特点:

  • MongoDB 拥有丰富的数据模型,而且文档没有固定的模式,这为扩展性提供了便利
  • 高可扩展性:MongoDB 设计之初就考虑到了扩展性,支持分片(sharding),可以轻松跨越多台服务器分配数据和处理请求,从而实现水平扩展。这对于处理海量数据等场景只管重要。
  • 高性能:MongoDB 支持各种索引,能够加锁数据的查询;采用异步非阻塞 I/O 模型,避免了线程的同步等待,从而实现高效的读写性能;水平扩展能力也能提高性能,通过添加分片可来分散负载,保持高性能;采用预分配数据机制来提高性能,当要写入新数据时,不会等到写入时才去请求磁盘空间,而是提前预留一定空间;同时还支持批量操作,减少交互来提升性能。
  • 高可用性:使用副本集来对数据进行冗余保存,当主节点故障时,数据也不会丢失。

        MongoDB 作为一个多用户、多线程的 NoSQL 数据库,确保其在高并发访问下数据的一致性和完整性至关重要。如果没有有效的并发控制机制,可能会产生如脏读、不接重复度、幻读等一系列问题。

        那如何确保 MongoDB 在并发环境下能够保障数据一致性和完整性呢?那就是 MongoDB 的锁机制。

二、MongoDB锁机制

        MongoDB 锁机制是其并发控制的重要组成部分,目的是为了确保多线程多用户访问下数据的完整性和一致性,主要分类两大类:MMAPv1 引擎的锁机制和 WiredTiger 引擎的锁机制。

        在使用 MMAPv1 存储引擎的 MongoDB 版本中,全局锁时其主要的并发控制手段。全局锁有两种模式:

  • 读锁:允许多个读操作共享,但组织任何写操作
  • 写锁:独占锁,一旦获取将组织其他读写操作,直至锁释放

        WiredTiger 引擎使用了更细粒度的锁机制,主要为:

  • 文档锁:锁定单个文档,允许多个并发读操作,但写操作会互斥。这大大减少了锁竞争,提高了并发写入能力,从而使得在高并发场景下也能保持较好的性能。
  • 多版本并发控制(MVCC):WiredTiger 实现了一种 MVCC 机制,为每个事务创建数据的多个版本。这样,读操作可以不受写操作的影响,看到事务开始时的一致性视图,而写操作则在新版本上进行,直到事务提交后才会对外可见。这增强了系统的并发能力,同时保证了事务的隔离性。
  • 范围锁:在某些情况下,为了保持数据一致性,WiredTiger可能会锁定一个文档范围,防止其他操作修改该范围内的数据。
  • 乐观锁:除了传统的锁机制,WiredTiger还采用了乐观锁策略,尤其在处理读写操作时。乐观锁依赖于文档版本控制,每个文档都有一个内部版本号。写操作前先读取版本号,写入时检查版本号是否改变,若未变则成功,否则重试。这种方式减少了锁的使用,提高了并发效率

三、锁的实践影响

        WiredTiger 提供文档级锁,减少了写操作之间的锁竞争,提高了并发性能。支持压缩,能够减少存储空间需求和I/O操作,进而提升读写速度。使用多版本并发控制(MVCC),允许读操作不阻塞写操作,提升了读取性能。支持事务,增强了数据一致性。

        但是有更高的内存需求,因为其缓存策略会占用较多内存。在极端并发写入场景下,虽然概率较低,但仍有可能遇到锁竞争导致的性能瓶颈。

        MongoDB 使用 WiredTiger 存储引擎时,具备一定的死锁检测和处理能力,旨在减少乃至避免死锁对系统的影响。

        WiredTiger 存储引擎具有内置的死锁检测机制。当事务等待资源超过一定时间阈值,引擎会尝试检测是否存在死锁情况。如果检测到死锁,WiredTiger 会选择一个或多个事务进行回滚,通常是那些影响较小或者等待时间较长的事务,从而解除死锁状态。

        可以通过以下方式避免死锁

  • 尽可能缩短事务运行时间,减少对锁的持有时间,可以降低与其他事务冲突的概率。使用原子操作和批量操作可以减少单独锁的次数和持续时间。
  • 设计事务时,尽量按照一致的顺序访问资源,减少循环等待的可能性。例如,如果多个事务总是按照相同的资源访问顺序执行,那么死锁就不会发生。
  • 在应用层面实施适当的并发控制策略,如乐观锁或悲观锁的合理使用,以及合理的重试逻辑,可以在遇到锁冲突时优雅地处理,避免直接导致死锁。

        3.1 高并发写入导致的写锁案例

        在使用MongoDB 时,由于有高并发的写入,突然出现了大量获取链接的报错,具体报错信息如下:

org.springframework.data.mongodb.UncategorizedMongoDbException: Too many operations are already waiting for a connection. Max number of operations (maxWaitQueueSize) of 500 has been exceeded.; nested exception is com.mongodb.MongoWaitQueueFullException: Too many operations are already waiting for a connection. Max number of operations (maxWaitQueueSize) of 500 has been exceeded.
	at org.springframework.data.mongodb.core.MongoExceptionTranslator.translateExceptionIfPossible(MongoExceptionTranslator.java:138)
	at org.springframework.data.mongodb.core.MongoTemplate.potentiallyConvertRuntimeException(MongoTemplate.java:2902)
	at org.springframework.data.mongodb.core.MongoTemplate.execute(MongoTemplate.java:587)
	at org.springframework.data.mongodb.core.MongoTemplate.doUpdate(MongoTemplate.java:1636)
	at org.springframework.data.mongodb.core.MongoTemplate.upsert(MongoTemplate.java:1570)

        通过监控发现是高并发写入引起了写锁,导致某些操作长时间占用写锁,最终获取不到连接导致出现上面的问题。下面来分析下原因。

        并发写入操作频繁且锁等待时间较长时,连接可能会被长时间占用,无法及时归还到连接池,导致可用连接耗尽。那如何来解决呢?

        我们最后如何处理的呢?其实也很简单,可以采用批量写入来减少锁竞争或锁等待时间,或者采用异步的方式来进行写入操作。

        还需要检查下设置的连接池是否合理,可以根据情况适当的调整连接池的大小。

往期经典推荐

Sentinel与Nacos强强联合,构建微服务稳定性基石的重要实践_sentinel和nacos-CSDN博客

云原生:Kubernetes下的Java应用部署实战详解_kubernetes部署java-CSDN博客

全面解读MongoDB高可用、高性能与高可扩展架构-CSDN博客

深入剖析MongoDB集群架构设计_mongodb 架构-CSDN博客

TiDB存储引擎TiKV揭秘-CSDN博客

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1801146.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

聆思CSK6大模型开发板英语评测类开源SDK详解

离线英文评测算法SDK 能力简介 CSK6 大模型开发套件可以对用户通过语音输入的英文单词进行精准识别,并对单词的发音、错读、漏读、多读等方面进行评估,进行音素级的识别,根据用户的发音给出相应的建议和纠正,帮助用户更好地掌握单…

【C++进阶】深入STL之list:模拟实现深入理解List与迭代器

📝个人主页🌹:Eternity._ ⏩收录专栏⏪:C “ 登神长阶 ” 🤡往期回顾🤡:初步了解 list 🌹🌹期待您的关注 🌹🌹 ❀STL之list 📒1. list…

最大乘法算式-第13届蓝桥杯选拔赛Python真题精选

[导读]:超平老师的Scratch蓝桥杯真题解读系列在推出之后,受到了广大老师和家长的好评,非常感谢各位的认可和厚爱。作为回馈,超平老师计划推出《Python蓝桥杯真题解析100讲》,这是解读系列的第80讲。 最大乘法算式&…

Vue CLI 环境变量使用指南

一、简介 Vue CLI 是一个强大的前端工程化工具,它提供了丰富的配置选项,包括环境变量的管理。环境变量允许开发者根据不同的运行环境(如开发、测试和生产)应用不同的配置,而无需更改代码。本文将详细介绍如何在 Vue C…

OlSoul系统调校程序v2024.06.05

软件介绍 OlSoul是一款能够适配用于Win各个系统的系统调校软件,OlSoul内置有众多调校功能可以直接使用,如有启用无线网络功能、启用打印机功能、系统快速休眠与休眠开关、快捷方式小箭头去除功能等,具体的调校功能多达几十项,可自…

Python的Pillow(图像处理库)的一些学习笔记

Python的Pillow库是一个非常强大的图像处理库。 安装Pillow库: 在终端或命令行中输入以下命令来安装Pillow: pip install pillow 升级库: pip install pillow --upgrade 一些基础的应用 1、图像文件方面的: 打开文件 …

植物大战僵尸杂交版破解C++实现

文章目录 前言准备工作:基地址与偏移UI界面设计和绑定项目模板总览图生成与实现信号处理1、阳光值更新:BTN12、三种钱币值更新:BTN2-BTN43、冷却刷新:BTN54、锁定阳光:check15、无冷却:check26、OnTimer()和OnClose&am…

数 据 类 型

概述 Java 是强类型语言。 每一种数据都定义了明确的数据类型,在内存中分配了不同大小的内存空间(字节)。 Java 中一共有 8 种基本类型(primitive type),包括 4 种整型、2 种浮点型、1 种字符类型&#…

【C语言】07.函数

一、概念 C语言的函数,有些翻译为:子程序,子程序这种翻译更加准确⼀些。 C语言中的函数就是⼀个完成某项特定的任务的⼀小段代码。这段代码是有特殊的写法和调用方法的。 C语言的程序其实是由无数个小的函数组合而成的,也可以说&…

什么是SIEM

SIEM 解决方案是一种企业级应用程序,可集中和自动化与网络安全相关的操作,该工具通过收集、分析和关联从组织 IT 基础设施中的各种实体聚合的网络事件来帮助应对网络威胁。 与帮助监控和评估组织物理空间中的危险的监视控制台相比,SIEM解决方…

【百万字详解Redis】主从复制

文章目录 一、主从复制概述1.1、单机问题1.1.1、机器宕机1.1.2、容器瓶颈1.1.3、QPS瓶颈 1.2、什么是主从复制1.3、主从复制形式1.3.1、一主一从1.3.2、一主多从 1.4、主从复制作用 二、单机主从2.1、复制redis.conf2.2、配置主机2.3、配置从机2.4、启动服务2.5、读写分离 三、…

[工具探索]富士mini90拍立得使用指南

文章目录 1. 基本功能介绍1.1 相机外观1.2 电池与胶片 2. 设置相机2.1 装入电池2.2 装入胶片 3. 拍摄模式3.1 标准模式3.2 儿童模式3.3 远景模式3.4 双重曝光模式3.5 Bulb(B)模式3.6 **派对模式**3.7 微距模式3.8 **亮度模式**3.9 **定时拍摄模式**3.10 …

php探针代码怎么写

创建php文件并输入代码,访问文件查看php版本、环境和系统配置信息,可使用ini_set()函数定制输出,但注意在生产环境中使用时要注重安全,因为它会泄露敏感信息。 PHP探针代码撰写指南 PHP探针代码是一种脚本,可提供关于…

基于Java Mq的数据交换平台实现_设计消息的格式和内容

基于Java Mq的数据交换平台实现 目录概述需求: 设计思路实现思路分析 参考资料和推荐阅读 Survive by day and develop by night. talk for import biz , show your perfect code,full busy,skip hardness,make a better result,wait for change,challen…

FileZilla:不安全的服务器,不支持 FTP over TLS 原因与解决方法

今天在用FileZilla Client连接某个主机的FTP的时候,主机地址、账号、密码、端口确定百分之百正确的情况下,结果报错如下: 状态: 正在解析 x.x.x 的地址 状态: 正在连接 x.x.x.x:21... 状态: 连接建立,等待欢迎消息... 状态: 不安全…

6.6SSH的运用

ssh远程管理 ssh是一种安全通道协议,用来实现字符界面的远程登录。远程复制,远程文本传输。 ssh对通信双方的数据进行了加密 用户名和密码登录 密钥对认证方式(可以实现免密登录) ssh 22 网络层 传输层 数据传输的过程中是加密的 …

Java Web学习笔记19——Ajax介绍

Ajax: 概念:Asynchronous JavaScript And XML 异步的JavaScript和XML。 作用: 1)数据交换:通过Ajax可以给服务器发送请求,并获得服务器的响应数据。 2)异步交互:可以在不重新加载页面的情况…

【NetTopologySuite类库】生成凸包

介绍 计算几何体的凸包。凸包是最小的凸几何体,包含输入几何体中的所有点。使用Graham Scan算法。 API地址: https://nettopologysuite.github.io/NetTopologySuite/api/NetTopologySuite.Algorithm.ConvexHull.html 示意图 示例代码 需在NuGet中安装…

nomachine使用记录以及录包

录包命令: rosbag record 话题名字(可以是原相机话题和执行程序的话题)rosbag play 包名(可以离线播放包的数据) rqt_image_view 话题可视化

新买的移动硬盘无法识别

文章目录 背景解决方案 背景 同事新买的移动硬盘,插在电脑上识别不出来盘符,检查了一下,硬盘没问题应该,是ssk的硬盘盒M.2的SSD,硬盘驱动也是正常的,插拔了几次,都不识别,换了太电脑…