How to Set Up MongoDB Authentication

How-To Guide

How to Set Up MongoDB Authentication

TL;DR

Start MongoDB without auth, create an admin user, add authorization: enabled to mongod.conf, restart, then create application-specific users with only the roles they need. Takes about 20 minutes. Always use authenticated connection strings in your app.

Prerequisites:

  • MongoDB installed (local or server)
  • MongoDB shell access (mongosh)
  • Admin/root access to the server

Why This Matters

A MongoDB instance without authentication is completely open to anyone who can reach its port. Thousands of databases have been ransomed because they were left exposed on the internet without auth. Over 30,000 unsecured MongoDB instances were found publicly accessible in a single 2023 scan by security researchers.

Proper auth prevents unauthorized access, enables audit logging, and is a hard requirement for SOC 2 and most other compliance frameworks.

Step-by-Step Guide

1

Connect to MongoDB without auth (initial setup)

If authentication isn't enabled yet, connect to create the first admin user:

# Connect to MongoDB
mongosh

# Or with older mongo shell
mongo

If MongoDB Atlas, skip to step 4 - Atlas handles this automatically.

2

Create an admin user

In the admin database, create a user with full privileges:

// Switch to admin database
use admin

// Create admin user
db.createUser({
  user: "adminUser",
  pwd: passwordPrompt(),  // Prompts for password (more secure)
  roles: [
    { role: "userAdminAnyDatabase", db: "admin" },
    { role: "readWriteAnyDatabase", db: "admin" },
    { role: "dbAdminAnyDatabase", db: "admin" },
    { role: "clusterAdmin", db: "admin" }
  ]
})

// Or with explicit password (less secure, avoid in scripts)
db.createUser({
  user: "adminUser",
  pwd: "yourStrongPassword123!",
  roles: ["root"]
})
3

Enable authentication in MongoDB config

Edit the MongoDB configuration file:

# Location varies by OS:
# Linux: /etc/mongod.conf
# macOS (Homebrew): /usr/local/etc/mongod.conf
# Windows: C:\Program Files\MongoDB\Server\{version}\bin\mongod.cfg

# Add or modify security section:
security:
  authorization: enabled

Restart MongoDB:

# Linux
sudo systemctl restart mongod

# macOS
brew services restart mongodb-community

# Windows
net stop MongoDB && net start MongoDB
4

Create application-specific users

Connect as admin and create a user for your application:

# Connect with admin credentials
mongosh -u adminUser -p --authenticationDatabase admin

# In the shell:
use myappdb

// Create app user with minimal permissions
db.createUser({
  user: "myapp",
  pwd: passwordPrompt(),
  roles: [
    { role: "readWrite", db: "myappdb" }
  ]
})

// For read-only access (reporting, analytics)
db.createUser({
  user: "myapp_readonly",
  pwd: passwordPrompt(),
  roles: [
    { role: "read", db: "myappdb" }
  ]
})
5

Update your application connection string

Add authentication to your MongoDB connection:

// Connection string format
mongodb://username:password@host:port/database?authSource=admin

// Example for local development
mongodb://myapp:mypassword@localhost:27017/myappdb

// With options
mongodb://myapp:mypassword@localhost:27017/myappdb?authSource=myappdb&retryWrites=true

// In Node.js with Mongoose
import mongoose from 'mongoose';

await mongoose.connect(process.env.MONGODB_URI, {
  // Connection options are included in the URI
});

// Or with explicit options
await mongoose.connect('mongodb://localhost:27017/myappdb', {
  user: process.env.MONGO_USER,
  pass: process.env.MONGO_PASSWORD,
  authSource: 'myappdb'
});
6

Set up role-based access for teams

Create custom roles for different access levels:

use myappdb

// Create a custom role for developers
db.createRole({
  role: "developer",
  privileges: [
    {
      resource: { db: "myappdb", collection: "" },
      actions: ["find", "insert", "update", "createIndex"]
    }
  ],
  roles: []
})

// Create developer user
db.createUser({
  user: "dev_john",
  pwd: passwordPrompt(),
  roles: [{ role: "developer", db: "myappdb" }]
})

// Create a read-only role for analytics
db.createRole({
  role: "analyst",
  privileges: [
    {
      resource: { db: "myappdb", collection: "" },
      actions: ["find", "listCollections"]
    }
  ],
  roles: []
})
  • Never connect your application as the admin user. Create a separate user with only the roles the app needs.
  • Use strong passwords (20+ characters). passwordPrompt() in mongosh avoids typing them in shell history.
  • Store credentials in environment variables, not in code.
  • Enable TLS for connections over any network that isn't loopback.
  • Bind to localhost or a specific IP. 0.0.0.0 means the whole internet can try to connect.
  • Rotate credentials periodically and audit user access from the admin console.

How to Verify It Worked

  1. Rejected connection test: Try connecting without credentials. It should fail immediately.
  2. App user login: Connect with your app user credentials. It should succeed.
  3. Permission boundary: Verify the app user can't read the admin database or other app databases.
  4. Log check: Tail the mongod logs and look for auth success/failure events after each test.
# This should fail
mongosh --eval "db.stats()"

# This should succeed
mongosh -u myapp -p yourpassword --authenticationDatabase myappdb myappdb --eval "db.stats()"

# Try accessing admin database with app user (should fail)
mongosh -u myapp -p yourpassword --authenticationDatabase myappdb admin --eval "db.getUsers()"

Common Errors & Troubleshooting

Error: "Authentication failed"

Check username, password, and authSource. The authSource must match the database where the user was created.

Error: "not authorized on admin to execute command"

You're trying to perform an admin operation with a non-admin user. Use the admin account or grant necessary roles.

Can't connect after enabling auth

Make sure you created the admin user BEFORE enabling authorization. If you're locked out, restart MongoDB with the --noauth flag, create the user, then restart normally.

Mongoose connection timeout

Check that the authSource in your connection string matches where the user was created (usually the app database or admin).

Should I use MongoDB Atlas instead of self-hosted?

For most startups, yes. Atlas handles authentication, encryption, backups, and scaling automatically. Self-host only if you've got specific compliance requirements or a DevOps team that can own the infrastructure.

What's the difference between authSource and the database name?

authSource is where MongoDB looks up your credentials. The database name is what you're connecting to. They can differ: many setups create users in the admin database but connect to an app database.

How do I enable TLS/SSL for MongoDB connections?

Add TLS configuration to mongod.conf and use mongodb+srv:// or add ?tls=true to your connection string. Atlas enables TLS by default.

Related guides:PostgreSQL Roles Setup · Database Encryption · Connection Pooling

How-To Guides

How to Set Up MongoDB Authentication