mongodump 无法备份 admin 库中的 system.users 集合,因 mongodb 4.2+ 出于安全限制默认跳过系统集合;正确方式是用 mongosh 调用 db.getusers({showcredentials: true}) 导出 json,再通过 createuser 脚本导入。

不能直接用 mongodump 备份系统用户信息(admin 库里的 system.users)——它默认跳过这些集合,即使显式指定也会被忽略。
为什么 mongodump 不会导出系统用户
MongoDB 从 4.2 起强制限制 mongodump 对 admin 库中系统集合(如 system.users、system.roles)的访问,这是出于安全隔离设计。即使你用 admin 用户登录、加了 --authenticationDatabase admin,执行 mongodump --collection system.users 也只会静默跳过,不报错也不写入数据。
正确导出用户数据:必须用 mongosh + db.getUsers()
系统用户信息只能通过 MongoDB Shell 查询接口获取,不是普通文档集合。实际操作需连接到源集群的 admin 库,执行命令导出为 JSON:
mongosh "mongodb://user:pass@source_host:27017/admin?authSource=admin" \
--eval 'JSON.stringify(db.getUsers({ usersInfo: true, showCredentials: true }), null, 2)' \
> users_dump.json
-
showCredentials: true是关键——否则密码哈希(credentials.SHA-256)不会返回,恢复后用户无法认证 - 输出是纯 JSON,不是 BSON,不能直接给
mongorestore用 - 注意:该操作需具备
root或userAdminAnyDatabase角色权限
导入用户时不能用 mongorestore,得用 db.createUser() 脚本
users_dump.json 是结构化数组,需转成可执行的 JavaScript 脚本再批量创建:
cat users_dump.json | jq -r '.[] | "db.createUser(\(. | tojson));"' > create_users.js
然后运行:
mongosh "mongodb://user:pass@target_host:27017/admin?authSource=admin" create_users.js
- 如果目标库已存在同名用户,
createUser会报UserExists错误,需先db.dropUser("username") - 角色定义里若含自定义数据库(如
{"role":"read","db":"appdb"}),要确保该库在目标环境已存在,否则角色创建失败 -
mongosh必须 ≥ 1.10(对应 MongoDB 5.0+),低版本不支持getUsers({showCredentials:true})
迁移后必须验证的三个点
用户数据“导出来、再写进去”不等于可用,容易漏掉权限上下文:
- 检查
db.runCommand({connectionStatus: 1}).authInfo.authenticatedUsers是否包含预期用户 - 用新用户连一次目标库:
mongosh "mongodb://newuser:newpass@target/admin?authSource=admin",确认不报AuthenticationFailed - 执行
db.runCommand({rolesInfo: {role: "root", db: "admin"}})看是否返回完整角色定义,避免因inheritedRoles缺失导致权限缩水
系统用户迁移不是数据搬运,而是权限体系重建。最常出问题的是密码哈希未导出、角色依赖库不存在、以及脚本执行时没切到 admin 数据库上下文——这三处不核对,恢复后的用户大概率无法登录或权限异常。











