MongoDB 内存管理配置指南
一 核心原则与内存构成
- 在 WiredTiger 引擎下,MongoDB 的内存占用主要由两部分组成:
- WiredTiger 缓存(可配置上限);
- 文件系统页缓存(由操作系统管理,存放数据/索引文件页)。
- WiredTiger 缓存的默认上限为:假定单实例部署时约为物理内存的 50%。当同一主机运行多个 mongod 实例或处于容器/cgroups 中时,需要按实际可用内存显式下调该上限,避免相互抢占。
- 注意:即使设置了 WiredTiger 缓存上限,进程 RSS 仍可能“超过”该值,因为文件系统页缓存与连接栈等也会占用内存;这属于正常现象。
二 配置 WiredTiger 缓存上限
- 在配置文件 mongod.conf 中设置 storage.wiredTiger.engineConfig.cacheSizeGB,建议预留充足内存给操作系统与其他进程(如日志、监控、驱动连接等)。
- 示例(单实例、主机内存 16GB,预留约 1–2GB 给系统):
storage:
engine: wiredTiger
wiredTiger:
engineConfig:
cacheSizeGB: 14
- 运行期可通过命令行参数覆盖:–wiredTigerCacheSizeGB 14。
- 多实例/容器场景:按“实例可用内存 × 安全系数(如 0.6–0.7)”设置,避免 OOM 或降速。
三 操作系统与容器层面的限制
- 使用 cgroups/容器内存限制(如 Docker 的 --memory、K8s memory limit)为 mongod 设置硬性上限,防止无界增长。
- Linux 内核参数建议:
- 降低 vm.swappiness(如设为 10),减少换页倾向;
- 设置 vm.overcommit_memory=2,更保守的内存过量使用策略;
- 是否开启 Swap:开启可在内存紧张时避免 OOM Killer 直接终止进程,但会带来不可控的变慢;不开启则在超限时可能被 OOM 终止。关键业务更推荐“规划足够内存 + 及时扩容”。
四 内存释放与脏页策略
- 调整 tcmalloc 行为(MongoDB 默认使用 tcmalloc):
- 更激进归还空闲内存:
- db.adminCommand({ setParameter: 1, tcmallocAggressiveMemoryDecommit: 1 })
- 调整归还速率(单位:千分之一;默认 0–10,资源紧张可更高):
- db.adminCommand({ setParameter: 1, tcmallocReleaseRate: 5 })
- 控制 WiredTiger 脏页缓存模式(部分版本支持):
- inMemory:缓存更多脏页,读性能更好,但内存占用更高;
- onDisk:脏页不长期驻留缓存,内存占用更低,读性能略降;
- 示例:
- storage.wiredTiger.engineConfig.cache_dirty_mode: onDisk
- 说明:上述参数名与取值范围可能随版本变化,请以所用版本的官方文档为准。
五 查询与索引层面的内存控制
- 限制排序/聚合等内存使用,避免将大量数据拉入内存:
- internalQueryExecMaxBlockingSortBytes:阻塞排序可用内存上限(如 100MB)
- internalQueryExecMaxMemoryUsageMB:查询执行可用内存上限(如 512MB)
- 示例:
- db.setParameter({ internalQueryExecMaxBlockingSortBytes: 104857600 })
- db.setParameter({ internalQueryExecMaxMemoryUsageMB: 512 })
- 设计与运维建议:
- 为高频查询建立合适索引,减少全表扫描与内存排序;
- 控制集合/索引数量,降低元数据内存开销与启动加载时间;
- 副本集从节点会维护 oplog 拉取缓冲(默认最大约 256MB),同步慢时会持续占用内存,需关注复制延迟。