Docker Compose部署MongoDB时所有用户认证失败问题排查
MongoDB认证失败与用户创建失败问题排查与解决
问题描述
使用Docker Compose部署MongoDB容器与Node CRUD应用,容器启动正常,但启用认证后通过Compass登录始终提示“Authentication failed”,无论使用哪个用户或连接配置。查看Mongo容器日志发现用户创建失败,技术用户也存在相同错误。部署在本地开发服务器,仅作个人使用。
相关配置文件与日志
docker-compose.yml
services: mongodb: image: mongo:latest restart: unless-stopped ports: - "1335:27017" volumes: - database:/database - ./config/UserInit.js:/docker-entrypoint-initdb.d/UserInit.js:ro environment: - "MONGO_INITDB_ROOT_USERNAME=${MONGO_USER}" - "MONGO_INITDB_ROOT_PASSWORD=${MONGO_PW}" - "MONGO_INITDB_DATABASE=banking" stdin_open: true tty: true bankingbackend: depends_on: - mongodb build: . restart: unless-stopped stdin_open: true tty: true ports: - "1336:1336" volumes: database:
Dockerfile
FROM node:latest WORKDIR "/bankingBackend" COPY . . RUN npm install CMD ["npm", "start"]
UserInit.js(创建技术用户)
db.createUser( { user: process.env.MONGO_TEC_USER, pwd: process.env.MONGO_TEC_USER_PASS, roles: [ { role: "readWrite", db: "banking" } ] } ); use("banking"); db.createCollection("accounts"); db.createCollection("transactions");
Jenkinsfile(触发构建并提供环境变量)
pipeline { agent any stages { stage('checkout') { steps { checkout scm } } stage('docker-compose-up') { steps { withCredentials([ usernamePassword(credentialsId: 'Mongo tec user', passwordVariable: 'MONGO_PW', usernameVariable: 'MONGO_USER'), usernamePassword(credentialsId: 'Mongo tec user', passwordVariable: 'MONGO_TEC_USER_PASS', usernameVariable: 'MONGO_TEC_USER')]) { sh 'MONGO_USER=MONGO_USER MONGO_PW=MONGO_PW MONGO_TEC_USER_PASS=MONGO_TEC_USER_PASS MONGO_TEC_USER=MONGO_TEC_USER docker compose up -d --build --force-recreate' } } } } }
日志信息
"c":"ACCESS", "id":5286307, "ctx":"conn2","msg":"Failed to authenticate","attr":{"client":"192.166.124.101:53804","isSpeculative":false,"isClusterMember":false,"mechanism":"SCRAM-SHA-1","user":"adminUser","db":"admin","error":"UserNotFound: Could not find user \"adminUser\" for db \"admin\"","result":11,"metrics":{"conversation_duration":{"micros":451,"summary":{"0":{"step":1,"step_total":2,"duration_micros":421
问题原因分析
- Jenkins环境变量传递错误:Jenkinsfile的sh命令中,错误地将变量名作为值赋值(如
MONGO_USER=MONGO_USER),导致Mongo容器收到的是字符串"MONGO_USER"而非实际凭据值,根用户创建失败。 - Mongo初始化脚本语法错误:UserInit.js使用了Node.js的
process.env语法读取环境变量,但Mongo Shell不支持该语法,无法获取技术用户的账号密码,导致技术用户创建失败。 - 旧数据卷缓存:如果之前未正确初始化就创建了Mongo数据卷,旧的无效数据会导致初始化脚本无法重新执行。
解决方案
1. 修复Jenkins环境变量传递
修改Jenkinsfile中的sh命令,直接让shell继承Jenkins注入的环境变量:
pipeline { agent any stages { stage('checkout') { steps { checkout scm } } stage('docker-compose-up') { steps { withCredentials([ usernamePassword(credentialsId: 'Mongo tec user', passwordVariable: 'MONGO_PW', usernameVariable: 'MONGO_USER'), usernamePassword(credentialsId: 'Mongo tec user', passwordVariable: 'MONGO_TEC_USER_PASS', usernameVariable: 'MONGO_TEC_USER')]) { sh 'docker compose up -d --build --force-recreate' } } } } }
2. 修复Mongo初始化脚本
将UserInit.js中的process.env替换为Mongo Shell支持的os.getenv(),并更新docker-compose传递技术用户的环境变量:
修改后的UserInit.js
var tecUser = os.getenv("MONGO_TEC_USER"); var tecPass = os.getenv("MONGO_TEC_USER_PASS"); db.createUser( { user: tecUser, pwd: tecPass, roles: [ { role: "readWrite", db: "banking" } ] } ); use("banking"); db.createCollection("accounts"); db.createCollection("transactions");
更新docker-compose.yml的mongodb环境变量
services: mongodb: # ... 其他配置不变 environment: - "MONGO_INITDB_ROOT_USERNAME=${MONGO_USER}" - "MONGO_INITDB_ROOT_PASSWORD=${MONGO_PW}" - "MONGO_INITDB_DATABASE=banking" - "MONGO_TEC_USER=${MONGO_TEC_USER}" - "MONGO_TEC_USER_PASS=${MONGO_TEC_USER_PASS}"
3. 清理旧数据卷并重新部署
删除旧的Mongo数据卷,确保初始化脚本重新执行:
docker compose down -v
然后重新启动服务:
docker compose up -d --build
4. 验证Compass连接配置
- 根用户(
MONGO_USER)的认证数据库为admin,连接字符串示例:mongodb://<你的根用户名>:<你的根密码>@localhost:1335/admin?authSource=admin - 技术用户(
MONGO_TEC_USER)的认证数据库为banking,连接字符串示例:mongodb://<你的技术用户名>:<你的技术密码>@localhost:1335/banking?authSource=banking
内容的提问来源于stack exchange,提问作者Oidipous_REXX
相关产品推荐
相关产品推荐

