如何平滑升级 MongoDB 副本集版本不停机服务

文章导读
MongoDB 副本集平滑升级不停机的核心方法是滚动升级(Rolling Upgrade),即逐节点重启并替换二进制文件,期间保持副本集多数派可用。此方案适用于生产环境副本集架构,主要风险在于功能兼容性版本(FCV)设置时机错误可能导致节点拒绝同步或选举失败。
📋 目录
  1. 命令速用版
  2. 为什么会这样
  3. 分步处理
  4. 怎么验证是否生效
  5. 常见坑
  6. 常见问题
  7. 参考来源
A A

MongoDB 副本集平滑升级不停机的核心方法是滚动升级(Rolling Upgrade),即逐节点重启并替换二进制文件,期间保持副本集多数派可用。此方案适用于生产环境副本集架构,主要风险在于功能兼容性版本(FCV)设置时机错误可能导致节点拒绝同步或选举失败。

先说结论:必须逐节点滚动升级,先升级所有 Secondary 节点,最后升级 Primary 节点,所有节点二进制版本一致后再统一提升 FCV。

  • 适合场景:生产环境 MongoDB 副本集架构,要求业务写入不中断。
  • 先看准备:完成全量数据备份,确认当前副本集状态健康无 ROLLBACK 节点。
  • 建议操作:升级过程中严禁提前执行 setFeatureCompatibilityVersion,直到所有节点版本一致。

命令速用版

# 查看副本集状态
rs.status()

# 主节点主动降级(参数单位秒)
rs.stepDown(60)

# 升级完成后提升功能兼容性版本
db.adminCommand({ setFeatureCompatibilityVersion: "6.0" })

# 验证 FCV 版本
db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 })

为什么会这样

滚动升级能不停机是因为副本集依赖多数派选举机制,只要多数节点存活,集群仍可读写。二进制升级与 FCV 提升分离是为了防止版本不一致导致同步失败,旧版本节点无法解析新版本 oplog 会崩溃退出。若全量停机再启动,所有节点同时重启会触发多数节点失联判定,可能因 FCV 不一致或 electionId 冲突导致长期无法选出主节点。

分步处理

第一步:升级前检查与备份
使用 mongodump 进行逻辑备份或物理备份,执行 rs.status() 确认所有成员 stateStr 为 PRIMARY、SECONDARY 或 ARBITER,无 STARTUP、RECOVERING 状态。检查隐藏节点和延迟节点,升级前需手动暂停同步以防意外 stepDown。

第二步:滚动升级 Secondary 节点
选择一个 Secondary 节点,执行 sudo systemctl stop mongod 停止服务。替换二进制文件(如 Ubuntu 上运行 sudo apt-get install -y mongodb-org=6.0.15)。启动服务 sudo systemctl start mongod,等待 rs.status() 中该节点状态恢复为 SECONDARY。重复此步骤直到所有 Secondary 节点升级完成。

如何平滑升级 MongoDB 副本集版本不停机服务

第三步:升级 Primary 节点
连接当前 Primary,执行 rs.stepDown(60) 主动降级,等待新主选出(通常 10–30 秒)。确认原 Primary 状态变为 SECONDARY 后,按 Secondary 节点流程停止服务、替换二进制、启动服务。等待其同步完成并恢复为 SECONDARY 状态。

第四步:提升功能兼容性版本
确认所有节点二进制版本一致且 rs.status() 无异常后,在当前 Primary 上执行 db.adminCommand({ setFeatureCompatibilityVersion: "6.0" })。该命令幂等,但若返回 node not master 说明连接到了从节点。

怎么验证是否生效

执行 db.version() 查看当前版本是否为目标版本。运行 db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 }) 确认 version 字段已更新。在应用层发一条带 w: "majority" 的测试写入,验证写操作能成功返回。检查日志 /var/log/mongodb/mongod.log 确认无版本兼容性报错。

如何平滑升级 MongoDB 副本集版本不停机服务

常见坑

FCV 提升过早:在所有节点完成二进制升级前执行 setFeatureCompatibilityVersion 会导致未升级节点崩溃退出。
StepDown 等待不足:rs.stepDown() 后未等待新主稳定就升级原主节点,可能导致写入丢失或 NotPrimaryNoSecondaryOk 错误。
隐藏节点干扰:隐藏节点若未暂停同步,可能在升级完成后突然追上并触发意外选举。
分片集群遗漏:若是分片集群,必须先升级 mongos,再升级 config server,最后升级 shard,顺序错误会导致协议不兼容。

常见问题

升级过程中业务会中断吗?

正常滚动升级业务不会中断,但主节点切换瞬间可能有秒级写入抖动,客户端驱动需配置重试机制。

FCV 升级失败怎么办?

若返回错误,检查是否所有节点二进制版本已一致,确认当前连接的是主节点,该命令支持失败重试。

升级后能回滚版本吗?

一旦提升 FCV 到新版本,通常无法直接回滚到低版本二进制,需通过恢复备份方式回退。

参考来源

  • MongoDB 5.0 副本集如何平滑升级到 6.0 版本_按照官方滚动升级指南依次更替节点
  • 如何在 MongoDB 副本集升级时做到零停机_滚动升级策略与 StepDown
  • 如何实现 MongoDB 分片集群的平滑版本升级_采用滚动升级策略先更新 Mongos 再到 Shard
  • Mongodb 副本集版本升级
  • 升级到 MongoDB Enterprise(副本集)