一、升级前的准备工作
1.1 为什么需要升级MongoDB
MongoDB定期升级可以带来以下好处:
| 收益类型 | 具体内容 | 说明 |
|---|---|---|
| 安全修复 | 修复已知漏洞 | 防止被攻击 |
| 性能提升 | 查询优化、新算法 | 提升响应速度 |
| 新功能 | 新增运算符、聚合阶段 | 扩展能力 |
| 兼容性 | 适配新驱动、新系统 | 保持生态兼容 |
| 稳定性 | 修复Bug | 减少崩溃风险 |
1.2 版本兼容性检查
MongoDB大版本之间存在不兼容变更,升级需要按顺序进行:
## 版本升级路径规则
### 升级顺序要求
MongoDB 4.4 → 5.0 → 6.0 → 7.0
### 不能跨越大版本升级
❌ 4.4 → 6.0(必须经过5.0)
✅ 4.4 → 5.0 → 6.0
### LTS版本
- MongoDB 6.0:LTS版本(长期支持)
- MongoDB 7.0:最新稳定版
### 版本生命周期
- 社区版支持:通常24个月
- 企业版支持:通常36个月+
1.3 数据备份(必须)
# ===== 全量备份 =====
# 1. 使用mongodump备份所有数据库
mongodump --host 127.0.0.1 --port 27017 \
--out /backup/mongodb_$(date +%Y%m%d_%H%M%S)
# 2. 压缩备份文件
tar -czvf /backup/mongodb_$(date +%Y%m%d).tar.gz \
/backup/mongodb_$(date +%Y%m%d_%H%M%S)
# 3. 备份用户信息
mongosh --quiet --eval '
db.adminCommand({ usersInfo: 1 }).users.forEach(function(u) {
print("用户: " + u.user + ", 数据库: " + u.db);
print("角色: " + JSON.stringify(u.roles));
});
' > /backup/mongodb_users_$(date +%Y%m%d).txt
# 4. 备份配置文件
cp /etc/mongod.conf /backup/mongod.conf.backup
# 5. 验证备份完整性
ls -lh /backup/mongodb_*.tar.gz
1.4 停机窗口规划
## 升级停机时间估算
| 数据量 | 备份时间 | 升级时间 | 恢复时间 | 总计 |
|--------|----------|----------|----------|------|
| < 10GB | 5-10分钟 | 10-20分钟 | 5-10分钟 | 20-40分钟 |
| 10-100GB | 30-60分钟 | 20-40分钟 | 30-60分钟 | 1.5-2.5小时 |
| 100GB-1TB | 2-4小时 | 40-80分钟 | 2-4小时 | 5-9小时 |
| > 1TB | 需要专业评估 | - | - | - |
## 建议
- 生产环境选择业务低峰期
- 提前通知用户
- 准备好回滚方案
二、CentOS 7升级MongoDB
2.1 从MongoDB 4.4升级到5.0
准备工作
# 1. 检查当前版本
mongosh --quiet --eval "db.version()"
# 2. 检查存储引擎
mongosh --quiet --eval "db.adminCommand({ serverStatus: 1 }).storageEngine.name"
# 3. 检查Feature Compatibility Version (FCV)
mongosh admin --quiet --eval "db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 }).featureCompatibilityVersion"
# 4. 确保FCV为当前版本
# MongoDB 4.4应返回 "4.4"
升级步骤
# 1. 停止MongoDB服务
sudo systemctl stop mongod
# 2. 添加MongoDB 5.0官方源
sudo cat > /etc/yum.repos.d/mongodb.repo << 'EOF'
[mongodb-org-5.0]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/7/mongodb-org/5.0/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-5.0.asc
EOF
# 3. 升级MongoDB
sudo yum clean all
sudo yum install -y mongodb-org
# 4. 修改存储引擎(如使用WiredTiger可跳过)
# MongoDB 5.0推荐WiredTiger
# 5. 启动MongoDB
sudo systemctl start mongod
# 6. 验证版本
mongosh --quiet --eval "db.version()"
设置Feature Compatibility Version
# 连接到MongoDB
mongosh admin
# 设置FCV为5.0
db.adminCommand({ setFeatureCompatibilityVersion: "5.0" })
# 验证设置
db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 })
# 退出
exit
2.2 从MongoDB 5.0升级到6.0
# 1. 确保MongoDB 5.0 FCV已设置为5.0
mongosh admin --quiet --eval "db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 }).featureCompatibilityVersion"
# 2. 停止MongoDB
sudo systemctl stop mongod
# 3. 更新yum源为6.0
sudo cat > /etc/yum.repos.d/mongodb.repo << 'EOF'
[mongodb-org-6.0]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/7/mongodb-org/6.0/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-6.0.asc
EOF
# 4. 升级
sudo yum clean all
sudo yum install -y mongodb-org
# 5. 启动MongoDB
sudo systemctl start mongod
# 6. 设置FCV为6.0
mongosh admin --quiet --eval "db.adminCommand({ setFeatureCompatibilityVersion: '6.0' })"
# 7. 验证
mongosh --quiet --eval "db.version()"
2.3 从MongoDB 6.0升级到7.0
# 1. 确保FCV为6.0
mongosh admin --quiet --eval "db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 }).featureCompatibilityVersion"
# 2. 停止服务
sudo systemctl stop mongod
# 3. 更新yum源
sudo cat > /etc/yum.repos.d/mongodb.repo << 'EOF'
[mongodb-org-7.0]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/7/mongodb-org/7.0/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-7.0.asc
EOF
# 4. 升级
sudo yum clean all
sudo yum install -y mongodb-org
# 5. 启动
sudo systemctl start mongod
# 6. 设置FCV为7.0
mongosh admin --quiet --eval "db.adminCommand({ setFeatureCompatibilityVersion: '7.0' })"
# 7. 验证
mongosh --quiet --eval "db.version()"
三、CentOS Stream 8/9升级MongoDB
3.1 源配置差异
# CentOS Stream 8 使用不同的路径
sudo cat > /etc/yum.repos.d/mongodb.repo << 'EOF'
[mongodb-org-7.0]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/8/mongodb-org/7.0/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-7.0.asc
EOF
# CentOS Stream 9
sudo cat > /etc/yum.repos.d/mongodb.repo << 'EOF'
[mongodb-org-7.0]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/9/mongodb-org/7.0/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-7.0.asc
EOF
3.2 升级脚本模板
#!/bin/bash
# MongoDB升级脚本(CentOS 8/9)
set -e
CURRENT_VERSION=$1
TARGET_VERSION=$2
BACKUP_DIR="/backup/mongodb_upgrade_$(date +%Y%m%d)"
echo "===== MongoDB升级脚本 ====="
echo "当前版本: $CURRENT_VERSION"
echo "目标版本: $TARGET_VERSION"
echo "备份目录: $BACKUP_DIR"
# 1. 备份
echo "步骤1: 数据备份..."
mkdir -p $BACKUP_DIR
mongodump --host 127.0.0.1 --port 27017 --out $BACKUP_DIR
echo "备份完成!"
# 2. 停止服务
echo "步骤2: 停止MongoDB..."
sudo systemctl stop mongod
# 3. 更新源
echo "步骤3: 更新软件源..."
sudo cat > /etc/yum.repos.d/mongodb.repo << EOF
[mongodb-org-$TARGET_VERSION]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/8/mongodb-org/$TARGET_VERSION/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-$TARGET_VERSION.asc
EOF
# 4. 升级
echo "步骤4: 升级MongoDB..."
sudo yum clean all
sudo yum install -y mongodb-org-$TARGET_VERSION mongodb-org-server-$TARGET_VERSION
# 5. 启动
echo "步骤5: 启动MongoDB..."
sudo systemctl start mongod
# 6. 验证
echo "步骤6: 验证版本..."
NEW_VERSION=$(mongosh --quiet --eval "db.version()")
echo "新版本: $NEW_VERSION"
# 7. 设置FCV
echo "步骤7: 设置FCV..."
mongosh admin --quiet --eval "db.adminCommand({ setFeatureCompatibilityVersion: '$TARGET_VERSION' })"
echo "===== 升级完成 ====="
四、Replica Set升级
4.1 滚动升级流程
对于Replica Set,可以采用滚动升级方式减少停机时间:
## 滚动升级原理
Primary → Secondary → Secondary → Primary(新版本)
↓
按顺序升级每个节点,始终保持多数节点可用
## 升级顺序
1. 先升级Secondary节点(可多个同时)
2. 等待同步完成
3. 触发Primary降级(选举)
4. 升级原Primary节点
4.2 滚动升级执行
#!/bin/bash
# Replica Set滚动升级脚本
TARGET_VERSION="7.0.4"
echo "===== Replica Set滚动升级 ====="
# 1. 查看当前状态
echo "当前RS状态:"
mongosh --quiet --eval "rs.status().members.forEach(m => print(m.name + ': ' + m.stateStr))"
# 2. 禁止Balancer(如果是分片集群)
# sh.stopBalancer()
# 3. 升级Secondary节点
echo "升级Secondary节点..."
# 在每个Secondary上:
# sudo systemctl stop mongod
# sudo yum install -y mongodb-org-$TARGET_VERSION
# sudo systemctl start mongod
# 4. 等待同步
echo "等待Secondary同步..."
mongosh --quiet --eval "while(!db.adminCommand({ replSetGetStatus: 1 }).members.every(m => m.stateStr === 'SECONDARY' || m.stateStr === 'PRIMARY')) { print('等待中...'); sleep(1000); }"
# 5. 触发Primary降级
echo "触发Primary降级..."
mongosh --quiet --eval "rs.stepDown(300)"
# 6. 升级原Primary
echo "升级原Primary节点..."
# sudo systemctl stop mongod
# sudo yum install -y mongodb-org-$TARGET_VERSION
# sudo systemctl start mongod
# 7. 验证RS状态
echo "验证RS状态:"
mongosh --quiet --eval "rs.status().members.forEach(m => print(m.name + ': ' + m.stateStr))"
# 8. 设置FCV
echo "设置FCV..."
mongosh admin --quiet --eval "db.adminCommand({ setFeatureCompatibilityVersion: '$TARGET_VERSION' })"
echo "===== 滚动升级完成 ====="
4.3 滚动升级检查清单
## 滚动升级前检查
### 系统检查
- [ ] 所有节点磁盘空间充足(>20%剩余)
- [ ] 所有节点CPU/内存正常
- [ ] 网络连接正常
### 数据检查
- [ ] 所有节点数据同步正常
- [ ] 无数据不一致警告
- [ ] oplog足够大
### 应用检查
- [ ] 驱动版本兼容新MongoDB
- [ ] 应用已测试兼容性
- [ ] 监控告警已配置
### 回滚准备
- [ ] 备份完整且可恢复
- [ ] 回滚脚本已测试
- [ ] 停机窗口已确认
五、升级后验证
5.1 基本验证
# 1. 检查MongoDB版本
mongosh --quiet --eval "db.version()"
# 2. 检查FCV版本
mongosh admin --quiet --eval "db.adminCommand({ getParameter: 1, featureCompatibilityVersion: 1 }).featureCompatibilityVersion"
# 3. 检查连接状态
mongosh --quiet --eval "db.adminCommand({ ping: 1 })"
# 4. 检查Replica Set状态
mongosh --quiet --eval "rs.status().ok"
# 5. 检查各节点状态
mongosh --quiet --eval "rs.status().members.forEach(m => print(m.name + ': ' + m.stateStr))"
# 6. 检查数据库列表
mongosh --quiet --eval "db.adminCommand({ listDatabases: 1 }).databases.map(d => d.name)"
# 7. 检查索引
mongosh myapp --quiet --eval "db.getCollectionNames().forEach(c => print(c + ': ' + db[c].getIndexes().length + ' indexes'))"
5.2 功能验证
# 1. CRUD操作测试
mongosh testdb --quiet --eval "
db.users.insertOne({ name: '测试', created: new Date() });
db.users.findOne({ name: '测试' });
db.users.updateOne({ name: '测试' }, { \$set: { updated: true } });
db.users.deleteOne({ name: '测试' });
print('CRUD测试通过!');
"
# 2. 聚合操作测试
mongosh testdb --quiet --eval "
db.orders.aggregate([{ \$match: {} }, { \$group: { _id: null, count: { \$sum: 1 } } }]);
print('聚合测试通过!');
"
# 3. 副本集同步测试
mongosh admin --quiet --eval "
var status = rs.status();
var primary = status.members.find(m => m.stateStr === 'PRIMARY');
var secondaries = status.members.filter(m => m.stateStr === 'SECONDARY');
print('Primary: ' + primary.name);
print('Secondaries: ' + secondaries.length);
"
5.3 性能验证
# 1. 慢查询检查
mongosh --quiet --eval "
db.getSiblingDB('admin').getCollection('system.profile').find().sort({ ts: -1 }).limit(10).forEach(d => {
print('耗时: ' + d.millis + 'ms, 操作: ' + d.op + ', 集合: ' + d.ns);
});
"
# 2. 连接数检查
mongosh --quiet --eval "db.adminCommand({ connectionStatus: 1 }).info"
# 3. 内存使用检查
mongosh --quiet --eval "
var mem = db.adminCommand({ serverStatus: 1 }).mem;
print('常驻内存: ' + mem.resident + 'MB');
print('虚拟内存: ' + mem.virtual + 'MB');
"
# 4. 存储检查
mongosh --quiet --eval "
var storage = db.adminCommand({ serverStatus: 1 }).wiredTiger.cache;
print('缓存使用: ' + storage['bytes currently in the cache']);
print('缓存大小: ' + storage['maximum bytes configured']);
print('命中率: ' + (1 - storage['pages read from disk'] / storage['pages requested from cache']) * 100 + '%');
"
六、回滚方案
6.1 回滚触发条件
## 需要回滚的情况
- [ ] MongoDB无法启动
- [ ] 数据丢失或损坏
- [ ] 性能严重下降(>50%)
- [ ] 应用无法连接
- [ ] 核心功能不可用
- [ ] Replica Set无法选举Primary
6.2 回滚步骤
# ===== 单节点回滚 =====
# 1. 停止MongoDB
sudo systemctl stop mongod
# 2. 卸载新版MongoDB
sudo yum remove -y mongodb-org-7.0
# 3. 安装旧版MongoDB
sudo yum install -y mongodb-org-6.0
# 4. 清理数据目录(重要!)
sudo rm -rf /var/lib/mongo/*
sudo rm -rf /data/db/*
# 5. 恢复备份
mongorestore --host 127.0.0.1 --port 27017 /backup/mongodb_*/
# 6. 启动MongoDB
sudo systemctl start mongod
# 7. 验证
mongosh --quiet --eval "db.version()"
6.3 从备份恢复
# ===== 使用mongorestore恢复 =====
# 1. 查看备份内容
mongorestore --listBackups /backup/mongodb_*/
# 2. 完全恢复
mongorestore --host 127.0.0.1 --port 27017 \
--drop \ # 先删除现有数据
/backup/mongodb_*/
# 3. 恢复单个数据库
mongorestore --host 127.0.0.1 --port 27017 \
--nsInclude="myapp.*" \
/backup/mongodb_*/
# 4. 恢复单个集合
mongorestore --host 127.0.0.1 --port 27017 \
--nsInclude="myapp.users" \
/backup/mongodb_*/
# 5. 恢复用户信息
mongosh admin < /backup/mongodb_users_*.txt
七、生产环境最佳实践
7.1 升级检查清单
## 升级前必检项目
### 版本兼容性
- [ ] 检查当前MongoDB版本
- [ ] 确认支持的目标版本
- [ ] 了解版本间不兼容变更
- [ ] 确认驱动兼容性
### 数据安全
- [ ] 完整数据备份
- [ ] 用户配置备份
- [ ] 配置文件备份
- [ ] 备份可恢复性验证
### 系统准备
- [ ] 磁盘空间检查(>20%剩余)
- [ ] 内存充足
- [ ] 网络连接正常
- [ ] 防火墙规则正确
### 应用准备
- [ ] 应用代码已兼容
- [ ] 驱动版本已更新
- [ ] 功能测试已完成
- [ ] 监控告警已配置
### 人员准备
- [ ] 升级窗口已确定
- [ ] 值班人员已安排
- [ ] 回滚人员已就绪
- [ ] 沟通通知已发送
7.2 升级后必检项目
## 升级后必检项目
### 服务状态
- [ ] MongoDB进程运行正常
- [ ] 端口正常监听
- [ ] Replica Set健康
- [ ] 分片集群正常
### 数据完整性
- [ ] 数据库可访问
- [ ] 集合数据完整
- [ ] 索引正常
- [ ] 用户可正常认证
### 功能验证
- [ ] 应用连接正常
- [ ] CRUD操作正常
- [ ] 聚合查询正常
- [ ] 备份恢复流程正常
### 性能基线
- [ ] 查询响应时间正常
- [ ] 连接数正常
- [ ] 内存使用正常
- [ ] 无异常慢查询
八、总结
MongoDB升级流程关键要点:
- 充分备份:升级前务必完整备份数据和配置
- 按序升级:不能跨越大版本,必须依次升级
- 测试环境验证:生产升级前先在测试环境验证
- 滚动升级:Replica Set优先采用滚动升级方案
- 设置FCV:升级后及时设置Feature Compatibility Version
- 验证完整性:升级后全面验证功能和数据完整性
- 准备回滚:始终准备回滚方案并确保可用
# 快速升级命令模板(CentOS 7, 4.4 → 7.0)
sudo systemctl stop mongod
sudo rm /etc/yum.repos.d/mongodb.repo
sudo cat > /etc/yum.repos.d/mongodb.repo << 'EOF'
[mongodb-org-7.0]
name=MongoDB Repository
baseurl=https://repo.mongodb.org/yum/redhat/7/mongodb-org/7.0/x86_64/
gpgcheck=1
enabled=1
gpgkey=https://www.mongodb.org/static/pgp/server-7.0.asc
EOF
sudo yum clean all && sudo yum install -y mongodb-org
sudo systemctl start mongod
mongosh admin --quiet --eval "db.adminCommand({ setFeatureCompatibilityVersion: '7.0' })"
注:本文基于MongoDB 7.0和CentOS 7编写,具体步骤可能因版本和系统版本而异。