MongoDB — Which Authentication Database should I use when creating users?
In MongoDB Authentication Database is:
“When adding a user, you create the user in a specific database. This database is the authentication database for the user. A user can have privileges across different databases; that is, a user’s privileges are not limited to their authentication database. By assigning to the user roles in other databases, a user created in one database can have permissions to act on other databases. For more information on roles, see Role-Based Access Control”
The users are stored in system.users collection within the admin database:
“The
system.users
collection in theadmin
database stores user authentication and authorization information. To manage data in this collection, MongoDB provides user management commands.”
But which Authentication Database should I use? The admin database or the database that the user needs to work on?
Either way would work, but there are pros and cons to each one. When coming from a traditional RDBMS world like Oracle, We are used to each server instance having a single database instance which holds the users. So we are used to creating our users at the database level.
MongoDB best practice is:
- Creating the users in the admin database
- Having a single user with permissions to multiple databases rather than having several or duplicate users
PROS
- Easier to manage
- Easier to audit
- More secure (the fewer users the better)
- When a database is deleted, it is not confusing that the user still exists
- More clarity (a user in flights access a collection in movies)
CONS
- Might confuse the consumer/developers forgetting to authenticate using a different database
- Might confuse the administrator thinking a user has over privileges in the admin database when connecting with admin as the authentication database
Querying for users
It is possible to query system.users collection:
MongoDB Enterprise > use admin
switched to db admin
MongoDB Enterprise > db.system.users.find().pretty()"_id" : "admin.root",
"user" : "root",
"db" : "admin",
"credentials" : {
"SCRAM-SHA-1" : {
"iterationCount" : 10000,
...
But I always prefer using a wrapper command db.getUsers() rather than fiddling with an internal system collection:
MongoDB Enterprise > use test
switched to db test
MongoDB Enterprise > db.getUsers(){
"_id" : "test.datadog",
"user" : "datadog",
"db" : "test",
"roles" : [
{
"role" : "read",
"db" : "admin"
},
{
"role" : "clusterMonitor",
"db" : "admin"
},
...
So if my users are scattered around different databases, I have to look for them by switching from database to database.
So unless some unique business case, I prefer creating my users in the admin database. 🛠👥