记一次MongoDB性能问题(从MySQL迁移到MongoDB)
发布时间 - 2026-01-11 00:18:48 点击率:次公司为这个项目专门配备了几台高性能务器,清一色的双路四核超线程CPU,外加32G内存,运维人员安装好MongoDB后,就交我手里了,我习惯于在使用新服务器前先看看相关日志,了解一下基本情况,当我浏览MongoDB日志时,发现一些警告信息:

WARNING: You are running on a NUMA machine. We suggest launching mongod like this to avoid performance problems: numactl –interleave=all mongod [other options]
当时我并不太清楚NUMA是什么东西,所以没有处理,只是把问题反馈给了运维人员,后来知道运维人员也没有理会这茬儿,所以问题的序幕就这样拉开了。
迁移工作需要导入旧数据。MongoDB本身有一个mongoimport工具可供使用,不过它只接受json、csv等格式的源文件,不适合我的需求,所以我没用,而是用PHP写了一个脚本,平稳运行了一段时间后,我发现数据导入的速度下降了,同时PHP抛出异常:
cursor timed out (timeout: 30000, time left: 0:0, status: 0)
我一时判断不出问题所在,想想先在PHP脚本里加大Timeout的值应付一下:
<?php MongoCursor::$timeout = -1; ?>
可惜这样并没有解决问题,错误反倒变着花样的出现了:
max number of retries exhausted, couldn't send query, couldn't send query: Broken pipe
接着使用strace跟踪了一下PHP脚本,发现进程卡在了recvfrom操作上:
shell> strace -f -r -p <PID> recvfrom(<FD>,
通过如下命令查询recvfrom操作的含义:
shell> apropos recvfrom receive a message from a socket
或者按照下面的方式确认一下:
shell> lsof -p <PID> shell> ls -l /proc/<PID>/fd/<FD>
此时如果查询MongoDB的当前操作,会发现几乎每个操作会消耗大量的时间:
mongo> db.currentOp()
与此同时,运行mongostat的话,结果会显示很高的locked值。
…
我在网络上找到一篇:MongoDB Pre-Splitting for Faster Data Loading and Importing,看上去和我的问题很类似,不过他的问题实质是由于自动分片导致数据迁移所致,解决方法是使用手动分片,而我并没有使用自动分片,自然不是这个原因。
…
询问了几个朋友,有人反映曾遇到过类似的问题,在他的场景里,问题的主要原因是系统IO操作繁忙时,数据文件预分配堵塞了其它操作,从而导致雪崩效应。
为了验证这种可能,我搜索了一下MongoDB日志:
shell> grep FileAllocator /path/to/log [FileAllocator] allocating new datafile ... filling with zeroes... [FileAllocator] done allocating datafile ... took ... secs
我使用的文件系统是ext4(xfs也不错 ),创建数据文件非常快,所以不是这个原因,但如果有人使用ext3,可能会遇到这类问题,所以还是大概介绍一下如何解决:
MongoDB按需自动生成数据文件:先是<DB>.0,大小是64M,然后是<DB>.1,大小翻番到128M,到了<DB>.5,大小翻番到2G,其后的数据文件就保持在2G大小。为了避免可能出现的问题,可以采用事先手动创建数据文件的策略:
#!/bin/sh
DB_NAME=$1
cd /path/to/$DB_NAME
for INDEX_NUMBER in {5..50}; do
FILE_NAME=$DB_NAME.$INDEX_NUMBER
if [ ! -e $FILE_NAME ]; then
head -c 2146435072 /dev/zero > $FILE_NAME
fi
done
注:数值2146435072并不是标准的2G,这是INT整数范围决定的。
…
最后一个求助方式就是官方论坛了,那里的国际友人建议我检查一下是不是索引不佳所致,死马当活马医,我激活了Profiler记录慢操作:
mongo> use <DB> mongo> db.setProfilingLevel(1);
不过结果显示基本都是insert操作(因为我是导入数据为主),本身就不需要索引:
mongo> use <DB>
mongo> db.system.profile.find().sort({$natural:-1})
…
问题始终没有得到解决,求人不如求己,我又重复了几次迁移旧数据的过程,结果自然还是老样子,但我发现每当出问题的时候,总有一个名叫irqbalance的进程CPU占用率居高不下,搜索了一下,发现很多介绍irqbalance的文章中都提及了NUMA,让我一下子想起之前在日志中看到的警告信息,我勒个去,竟然绕了这么大一个圈圈!安下心来仔细翻阅文档,发现官方其实已经有了相关介绍,按如下设置搞定:
shell> echo 0 > /proc/sys/vm/zone_reclaim_mode shell> numactl --interleave=all mongod [options]
关于zone_reclaim_mode内核参数的说明,可以参考官方文档。
注:从MongoDB1.9.2开始:MongoDB会在启动时自动设置zone_reclaim_mode。
至于NUMA的含义,简单点说,在有多个物理CPU的架构下,NUMA把内存分为本地和远程,每个物理CPU都有属于自己的本地内存,访问本地内存速度快于访问远程内存,缺省情况下,每个物理CPU只能访问属于自己的本地内存。对于MongoDB这种需要大内存的服务来说就可能造成内存不足,NUMA的详细介绍,可以参考老外的文章。
理论上,MySQL、Redis、Memcached等等都可能会受到NUMA的影响,需要留意。
# MongoDB性能问题
# mongodb 数据块的迁移流程分析
# mongodb数据库迁移变更的解决方案
# 迁移sqlserver数据到MongoDb的方法
# Python中MySQL数据迁移到MongoDB脚本的方法
# MongoDB副本集迁移实操案例详解
# 自己的
# 分片
# 有一个
# 都是
# 这是
# 我是
# 死马当活马医
# 几个
# 文档
# 都有
# 我在
# 多个
# 不出
# 不太
# 就不
# 我一
# 几次
# 我又
# 但我
# 当我
相关栏目:
【
网站优化151355 】
【
网络推广146373 】
【
网络技术251813 】
【
AI营销90571 】
相关推荐:
Linux网络带宽限制_tc配置实践解析【教程】
Android使用GridView实现日历的简单功能
Laravel如何配置和使用队列处理异步任务_Laravel队列驱动与任务分发实例
Laravel怎么实现微信登录_Laravel Socialite第三方登录集成
Laravel如何实现多表关联模型定义_Laravel多对多关系及中间表数据存取【方法】
Laravel如何处理CORS跨域问题_Laravel项目CORS配置与解决方案
如何用VPS主机快速搭建个人网站?
html5的keygen标签为什么废弃_替代方案说明【解答】
Laravel如何处理JSON字段_Eloquent原生JSON字段类型操作教程
网站制作报价单模板图片,小松挖机官方网站报价?
Laravel如何实现API版本控制_Laravel API版本化路由设计策略
php嵌入式断网后怎么恢复_php检测网络重连并恢复硬件控制【操作】
标准网站视频模板制作软件,现在有哪个网站的视频编辑素材最齐全的,背景音乐、音效等?
JavaScript如何操作视频_媒体API怎么控制播放
PHP 实现电台节目表的智能时间匹配与今日/明日轮播逻辑
Android实现代码画虚线边框背景效果
EditPlus中的正则表达式 实战(2)
Laravel中Service Container是做什么的_Laravel服务容器与依赖注入核心概念解析
Laravel怎么实现验证码功能_Laravel集成验证码库防止机器人注册
Laravel路由怎么定义_Laravel核心路由系统完全入门指南
Laravel如何操作JSON类型的数据库字段?(Eloquent示例)
Android自定义listview布局实现上拉加载下拉刷新功能
如何快速登录WAP自助建站平台?
Python面向对象测试方法_mock解析【教程】
Laravel Eloquent访问器与修改器是什么_Laravel Accessors & Mutators数据处理技巧
在线制作视频网站免费,都有哪些好的动漫网站?
儿童网站界面设计图片,中国少年儿童教育网站-怎么去注册?
惠州网站建设制作推广,惠州市华视达文化传媒有限公司怎么样?
标题:Vue + Vuex + JWT 身份认证的正确实践与常见误区解析
Laravel如何实现模型的全局作用域?(Global Scope示例)
Laravel模型关联查询教程_Laravel Eloquent一对多关联写法
装修招标网站设计制作流程,装修招标流程?
如何快速查询网址的建站时间与历史轨迹?
网易LOFTER官网链接 老福特网页版登录地址
iOS中将个别页面强制横屏其他页面竖屏
Laravel如何升级到最新的版本_Laravel版本升级流程与兼容性处理
如何用wdcp快速搭建高效网站?
Laravel队列由Redis驱动怎么配置_Laravel Redis队列使用教程
Laravel怎么配置不同环境的数据库_Laravel本地测试与生产环境动态切换【方法】
Laravel怎么使用Blade模板引擎_Laravel模板继承与Component组件复用【手册】
Laravel用户认证怎么做_Laravel Breeze脚手架快速实现登录注册功能
详解jQuery停止动画——stop()方法的使用
个人网站制作流程图片大全,个人网站如何注销?
如何在阿里云ECS服务器部署织梦CMS网站?
Win11搜索栏无法输入_解决Win11开始菜单搜索没反应问题【技巧】
Bootstrap CSS布局之列表
Laravel如何从数据库删除数据_Laravel destroy和delete方法区别
微信小程序 require机制详解及实例代码
JavaScript中如何操作剪贴板_ClipboardAPI怎么用
百度浏览器如何管理插件 百度浏览器插件管理方法

