MongoDB 三节点高可用副本集部署与运维全手册

mongodb介绍

MongoDB 是由 MongoDB Inc. 开发的开源文档型 NoSQL 数据库,以灵活的文档模型、高可扩展性、高性能为核心特性,自 2009 年发布以来,已成为全球最流行的 NoSQL 数据库之一,广泛应用于互联网、金融、电商、物联网等领域。

高可用与高扩展
  • 副本集(Replica Set):多节点冗余存储,自动故障切换(主节点宕机后从节点秒级升主),保障数据不丢失、服务不中断;
  • 分片集群(Sharding):支持水平扩展,将数据分布到多个节点,突破单节点存储 / 性能瓶颈,适配 TB/PB 级数据;
  • 读写分离:读请求可分流到从节点,降低主节点压力。

本手册适配 MongoDB 6.0 LTS (兼容 4.4+/5.0+),基于10.10.11.45/46/47三节点环境,搭建一主两从全数据副本集(无仲裁节点),包含完整部署流程、日常运维、故障处理、性能优化,满足生产级高可用要求.

  • 部署核心 :三节点副本集需保证replSetNamekeyFile全节点一致,主节点优先级最高;
  • 运维重点:监控节点健康、同步延迟、资源使用率,定期备份,权限遵循最小原则;
  • 高可用保障:主节点宕机自动切换,从节点同步延迟需及时优化,定期演练故障恢复。

常见问题

  • 副本集初始化失败:检查 keyFile 权限 / 网络 / 配置文件;
  • 同步延迟高:扩容 OPLOG / 优化硬件 / 降低主节点写入压力;
  • 权限不足:确认认证库为 admin,用户具备对应角色。
  1. 集群架构规划
节点 IP 角色 端口 核心作用 硬件建议(生产)
10.10.11.45 Primary(主) 27017 处理所有写请求、选举优先级最高 8 核 16G/500G SSD(数据盘)
10.10.11.46 Secondary(从) 27017 同步主节点数据、故障时接替主节点 8 核 16G/500G SSD
10.10.11.47 Secondary(从) 27017 同步主节点数据、分担读请求 8 核 16G/500G SSD
  1. 前置环境准备(所有节点执行)
  • 系统基础配置

    1. 关闭防火墙(生产可精准放行27017端口)

    systemctl stop firewalld && systemctl disable firewalld

    生产环境放行端口(替代关闭防火墙)

    firewall-cmd --add-port=27017/tcp --permanent && firewall-cmd --reload

    2. 关闭SELinux

    setenforce 0
    sed -i 's/^SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config

    3. 时间同步(必做,避免副本集选举异常)

    yum install -y ntp ntpdate
    ntpdate ntp.aliyun.com
    systemctl start ntpd && systemctl enable ntpd

    4. 提升文件句柄限制(解决高并发连接问题)

    echo "* soft nofile 65535" >> /etc/security/limits.conf
    echo "* hard nofile 65535" >> /etc/security/limits.conf
    echo "mongodb soft nproc 65535" >> /etc/security/limits.conf
    echo "mongodb hard nproc 65535" >> /etc/security/limits.conf

    5. 重启系统使配置生效(可选,生产可分批重启)

    reboot

  • 创建用户和目录

    创建mongodb系统用户(无登录权限)

    useradd -r -s /sbin/nologin mongodb

    创建数据/日志/密钥目录(统一路径)

    mkdir -p /data/mongodb/{data,log,key}
    chown -R mongodb:mongodb /data/mongodb
    chmod 755 /data/mongodb
    chmod 700 /data/mongodb/key # 密钥目录严格权限

3.安装 MongoDB(所有节点)

复制代码
  # 安装稳定版
  yum install -y mongodb-org

  # 禁止自动更新(避免版本漂移)
  echo "exclude=mongodb-org*" >> /etc/yum.conf

  # 验证安装
  mongod --version  # 输出6.0.x版本即成功
  • 配置文件编写(所有节点

编辑 /etc/mongod.conf45/46/47 节点仅 bindIp 不同):

复制代码
# 系统日志配置
systemLog:
  destination: file
  path: /data/mongodb/log/mongod.log
  logAppend: true
  logRotate: reopen
  verbosity: 0  # 日志级别,生产设0(最低)

# 存储配置
storage:
  dbPath: /data/mongodb/data
  engine: wiredTiger  # 默认高性能引擎
  wiredTiger:
    engineConfig:
      cacheSizeGB: 8  # 按物理内存50%配置(16G内存设8,32G设16)
      journalCompressor: snappy  # 日志压缩
    collectionConfig:
      blockCompressor: snappy  # 数据压缩
  journal:
    enabled: true  # 必开,崩溃恢复核心
    commitIntervalMs: 100  # 日志刷盘间隔

# 网络配置
net:
  port: 27017
  bindIp: 10.10.11.45  # 45节点填45,46填46,47填47(生产禁止0.0.0.0)
  maxIncomingConnections: 2000  # 最大连接数
  wireObjectCheck: true  # 校验BSON对象完整性

# 副本集核心配置
replication:
  replSetName: rs0  # 所有节点必须一致
  oplogSizeMB: 40960  # OPLOG大小40G(生产建议磁盘10%)
  enableMajorityReadConcern: true  # 读一致性保障

# 进程管理
processManagement:
  fork: true
  pidFilePath: /var/run/mongodb/mongod.pid
  timeZoneInfo: /usr/share/zoneinfo  # 时区配置

# 安全配置(生产必开)
security:
  authorization: enabled  # 开启账号密码认证
  keyFile: /data/mongodb/key/keyfile  # 节点间认证密钥
  enableEncryption: false  # 如需加密,需配置KMIP

# 监控配置
operationProfiling:
  mode: slowOp  # 仅记录慢查询
  slowOpThresholdMs: 50  # 慢查询阈值(50ms)
  rateLimit: 100  # 每秒最多记录100条慢查询
  • 生成节点认证密钥(仅 45 节点执行)

    生成keyfile(节点间认证,所有节点必须一致)

    openssl rand -base64 756 > /data/mongodb/key/keyfile
    chmod 600 /data/mongodb/key/keyfile
    chown mongodb:mongodb /data/mongodb/key/keyfile

    同步到46/47节点

    scp /data/mongodb/key/keyfile root@10.10.11.46:/data/mongodb/key/
    scp /data/mongodb/key/keyfile root@10.10.11.47:/data/mongodb/key/

    46/47节点修改权限(执行以下命令)

    chmod 600 /data/mongodb/key/keyfile && chown mongodb:mongodb /data/mongodb/key/keyfile

  • 启动服务(所有节点)

    启动mongod

    systemctl start mongod

    设置开机自启

    systemctl enable mongod

    验证状态(active (running)为正常)

    systemctl status mongod

    验证端口监听

    ss -tulpn | grep 27017 # 输出10.10.11.xx:27017 LISTEN

4.初始化副本集(仅 45 节点执行)

  • 无认证连接主节点

    mongo --host 10.10.11.45 --port 27017

  • 初始化副本集配置

    // 定义副本集配置
    var rs_config = {
    _id: "rs0",
    members: [
    {_id: 0, host: "10.10.11.45:27017", priority: 10, votes: 1}, // 主节点(优先级最高)
    {_id: 1, host: "10.10.11.46:27017", priority: 1, votes: 1}, // 从节点1
    {_id: 2, host: "10.10.11.47:27017", priority: 1, votes: 1} // 从节点2
    ],
    settings: {
    chainingAllowed: true, // 允许从节点间同步
    heartbeatIntervalMillis: 2000, // 心跳检测间隔(2秒)
    electionTimeoutMillis: 10000, // 选举超时(10秒)
    catchUpTimeoutMillis: 20000 // 追平数据超时(20秒)
    }
    };

    // 初始化副本集(仅执行一次)
    rs.initiate(rs_config);

    // 等待10秒,让节点完成握手
    sleep(10000);

    // 验证副本集状态
    rs.status();

执行rs.status()后,需满足:

  • 所有节点health: 1(健康);
  • 45 节点stateStr: PRIMARY
  • 46/47 节点stateStr: SECONDARY
  • syncingTo字段:46/47 指向 45 节点;
  • lagSeconds(同步延迟)< 1 秒。

创建管理员账号(仅 45 节点)

复制代码
// 切换到admin库
use admin;

// 创建root超级管理员(生产需设置强密码)
db.createUser({
  user: "root",
  pwd: "MongoDB@Root123!",
  roles: [{role: "root", db: "admin"}]
});

// 创建监控用户(最小权限原则)
db.createUser({
  user: "monitor",
  pwd: "MongoDB@Monitor123!",
  roles: [{role: "clusterMonitor", db: "admin"}]
});

// 创建业务用户(示例)
db.createUser({
  user: "app_user",
  pwd: "MongoDB@app123!",
  roles: [{role: "readWriteAnyDatabase", db: "admin"}]
});

// 验证认证
db.auth("root", "MongoDB@Root123!");  // 返回1即成功


// 回收业务用户写权限
use admin;
db.revokeRolesFromUser("app_user", [{role: "readWriteAnyDatabase", db: "admin"}]);

// 授予只读权限
db.grantRolesToUser("app_user", [{role: "readAnyDatabase", db: "admin"}]);

// 查看用户权限
db.getUser("app_user");
  1. 日常运维操作

核心状态查询(认证后执行)

复制代码
# 登录集群(推荐用monitor用户)
mongo --host 10.10.11.45 --port 27017 -u monitor -p MongoDB@Monitor123! --authenticationDatabase admin


#登录后操作
// 1. 副本集完整状态
rs.status();

// 2. 简化节点状态输出
rs.status().members.forEach(m => {
  print(`节点: ${m.host}, 角色: ${m.stateStr}, 健康: ${m.health}, 延迟: ${m.lagSeconds || 0}s`);
});

// 3. 主从同步详情
rs.printSlaveReplicationInfo();

// 4. 数据库运行状态
db.serverStatus();

// 5. 慢查询(运行超50ms的操作)
db.currentOp({
  "secs_running": { "$gt": 0.05 },
  "op": { "$nin": ["idle", "getmore"] }
});

// 6. 连接数统计
db.serverStatus().connections;  // current(当前)/available(可用)

节点维护操作

复制代码
// 在当前主节点执行,降级并60秒内不参与选举
rs.stepDown(60);

// 验证新主节点
rs.status().members.forEach(m => {
  if (m.stateStr === "PRIMARY") print("新主节点:", m.host);
});

// 添加新从节点(如10.10.11.48)
rs.add("10.10.11.48:27017");

// 移除故障节点(如47节点)
rs.remove("10.10.11.47:27017");

// 修改节点优先级(提升47节点优先级)
var cfg = rs.conf();
cfg.members[2].priority = 5;
rs.reconfig(cfg);

#权限管理

// 回收业务用户写权限
use admin;
db.revokeRolesFromUser("app_user", [{role: "readWriteAnyDatabase", db: "admin"}]);

// 授予只读权限
db.grantRolesToUser("app_user", [{role: "readAnyDatabase", db: "admin"}]);

// 查看用户权限
db.getUser("app_user");

3.全量备份(主节点定时执行)

复制代码
# 创建备份脚本
cat > /usr/local/bin/mongodb_backup.sh << EOF
#!/bin/bash
BACKUP_DIR="/backup/mongodb/\$(date +%Y%m%d)"
mkdir -p \$BACKUP_DIR
mongodump -u root -p MongoDB@Root123! --authenticationDatabase admin -o \$BACKUP_DIR
# 保留7天备份
find /backup/mongodb -type d -mtime +7 -exec rm -rf {} \;
EOF

# 添加执行权限
chmod +x /usr/local/bin/mongodb_backup.sh

# 添加定时任务(每天凌晨2点)
crontab -e
# 新增一行
0 2 * * * /usr/local/bin/mongodb_backup.sh >> /var/log/mongodb_backup.log 2>&1

数据恢复(目标节点执行)

复制代码
# 全量恢复
mongorestore -u root -p MongoDB@Root123! --authenticationDatabase admin /backup/mongodb/20260312/

# 恢复指定库
mongorestore -u root -p MongoDB@Root123! --authenticationDatabase admin -d app_db /backup/mongodb/20260312/app_db/

6.日志管理

复制代码
cat > /etc/logrotate.d/mongod << EOF
/data/mongodb/log/mongod.log {
    daily
    rotate 7
    compress
    delaycompress
    missingok
    notifempty
    create 644 mongodb mongodb
    postrotate
        /bin/kill -SIGUSR1 \$(cat /var/run/mongodb/mongod.pid) > /dev/null 2>&1 || true
    endscript
}
EOF

# 手动触发轮转
logrotate -f /etc/logrotate.d/mongod

7.重置管理员密码(忘记密码)

复制代码
# 1. 45节点停止服务
systemctl stop mongod

# 2. 修改配置文件,注释认证配置
# security:
#   authorization: enabled
#   keyFile: /data/mongodb/key/keyfile

# 3. 启动服务
systemctl start mongod

# 4. 无认证登录重置密码
mongo --host 10.10.11.45 --port 27017
use admin;
db.changeUserPassword("root", "NewMongoDB@Root123!");

# 5. 恢复配置文件,重启服务
systemctl restart mongod

8.集群中节点异常(剔除异常节点再重新加入)

先确认哪个节点异常(在主节点执行)

复制代码
mongo --host 10.10.11.45 -u root -p 你的密码 --authenticationDatabase admin


rs.status().members.forEach(m=>{
  print(m.host, " 状态:", m.stateStr, " 健康:", m.health)
})

在主节点把坏节点剔除

复制代码
rs.remove("10.10.11.47:27017");
rs.status()  // 应该只剩 45、46

异常节点本身操作:停止服务 + 清空数据

复制代码
systemctl stop mongod  #停止服务

#清空数据
# 备份一下(可选)
mv /data/mongodb/data /data/mongodb/data_bad
mkdir -p /data/mongodb/data

# 权限必须正确
chown -R mongodb:mongodb /data/mongodb
chmod 600 /data/mongodb/key/keyfile

启动节点服务

复制代码
systemctl start mongod
systemctl status mongod

回到主节点,把它重新加回集群

复制代码
rs.add("10.10.11.47:27017");
相关推荐
ZKNOW甄知科技1 天前
深度对标ServiceNow:燕千云如何破解企业全球化运维难题?
大数据·运维·人工智能·科技·ai·自动化·运维开发
进击切图仔1 天前
ROS 跨机通信与 Docker 多机环境搭建
运维·docker·容器
主角1 71 天前
Nginx核心功能
运维·nginx
cyber_两只龙宝1 天前
【MySQL】MySQL主从复制架构
linux·运维·数据库·mysql·云原生·架构
切糕师学AI1 天前
Kubernetes 中的 Informer 机制
云原生·容器·kubernetes·informer
i建模1 天前
在 Windows CMD 中将当前路径永久添加到系统环境变量
运维·windows
虚拟世界AI1 天前
Linux运维实战:从部署到高可用全指南
linux·运维
闫记康1 天前
scp工具
linux·运维·服务器·学习·ssh·github
虾..1 天前
Linux 套接字编程---基于UDP协议实现简易的聊天室
linux·运维·udp
默|笙1 天前
【Linux】库制作与原理(2)_ELF格式
linux·运维·服务器