调用rs.initiate()致MongoDB服务器崩溃,请求技术协助
问题分析
错误MongoServerError: This node was not started with replication enabled的核心原因是:Docker官方Mongo镜像在首次初始化数据目录时,会启动一个临时的mongod实例来执行docker-entrypoint-initdb.d下的脚本,这个临时实例不会加载你在command中指定的--replSet等复制相关参数,因此在该阶段执行rs.initiate()会触发报错,进而导致容器崩溃。
解决方案
1. 调整初始化脚本
修改startup.js,移除rs.initiate()操作,只保留必要的初始化逻辑(比如创建管理员用户):
print("############## 1 ######################"); // 示例:创建管理员用户(如果需要) // db.createUser({ // user: "admin", // pwd: process.env.MONGO_INITDB_ROOT_PASSWORD, // roles: [{ role: "root", db: "admin" }] // }); print("############## 2 ######################");
2. 容器启动后手动初始化复制集
等MongoDB容器完全启动后,执行以下步骤:
- 进入容器的MongoShell:
# 如果已创建管理员用户 docker exec -it mongodb mongosh -u admin -p <你的管理员密码> --authenticationDatabase admin # 未创建用户时直接进入 docker exec -it mongodb mongosh
- 在Shell中初始化复制集:
rs.initiate({ _id: "dbrs", members: [ { _id: 0, host: "localhost:27017" } ] });
执行完成后,复制集就会启动,节点会自动切换为PRIMARY状态。
3. 自动化初始化(可选)
如果需要自动完成复制集初始化,可以编写一个启动脚本,等待MongoDB就绪后执行初始化:
- 创建
init-replica.sh脚本:
#!/bin/bash set -e # 等待MongoDB服务就绪 until mongosh --eval "db.adminCommand('ping')" >/dev/null 2>&1; do echo "Waiting for MongoDB to become available..." sleep 2 done # 初始化复制集 mongosh <<EOF rs.initiate({ _id: "dbrs", members: [{ _id: 0, host: "localhost:27017" }] }); EOF echo "Replica set initialized successfully"
- 在docker-compose中挂载并执行该脚本:
修改docker-compose.yml的mongo服务配置,添加脚本挂载和命令:
mongo: # 原有配置不变 volumes: # 原有挂载项 - ./mongodb/init/init-replica.sh:/docker-entrypoint-initdb.d/init-replica.sh:ro command: bash -c "mongod --replSet dbrs --bind_ip_all --config /etc/mongo.conf & sleep 10 && /docker-entrypoint-initdb.d/init-replica.sh && wait"
注意:需要确保脚本有可执行权限,或者在命令中用bash执行。
关键检查项
- 确认
./db/mongo目录首次启动时为空,否则镜像不会执行docker-entrypoint-initdb.d下的初始化脚本。 - 检查
keyFile权限:你的Dockerfile已经设置了chmod 600和chown 999:999,这部分配置正确,无需修改。 - 确保
mongo.conf中没有与复制集冲突的配置项,当前的security配置是合规的。
内容的提问来源于stack exchange,提问作者Reda Bourial
相关产品推荐
相关产品推荐

