Regular backups are essential for any MongoDB deployment. mongodump and mongorestore are the standard tools for creating and restoring logical backups of MongoDB databases. This guide covers backup strategies, automation, compression, and restoration procedures for both standalone and replica set deployments.
Understanding MongoDB Backup Options
MongoDB offers several backup approaches:
- mongodump/mongorestore — logical backups; flexible, portable, but slower for large databases
- Filesystem snapshots — fast point-in-time copies using LVM or cloud snapshots
- MongoDB Atlas Backups — automated cloud backups (Atlas only)
- Percona Backup for MongoDB — distributed backup solution for sharded clusters
This guide focuses on mongodump/mongorestore, which works with all MongoDB deployments and produces portable backup files.
Basic mongodump Usage
# Backup entire server (all databases)
mongodump --uri="mongodb://admin:password@localhost:27017" --out=/backup/mongodb/$(date +%Y%m%d)
# Backup a specific database
mongodump --uri="mongodb://admin:password@localhost:27017/myapp" --out=/backup/mongodb/$(date +%Y%m%d)
# Backup a specific collection
mongodump --uri="mongodb://admin:password@localhost:27017/myapp" --collection=orders --out=/backup/mongodb/$(date +%Y%m%d)
# Backup with compression (recommended)
mongodump --uri="mongodb://admin:password@localhost:27017" --gzip --out=/backup/mongodb/$(date +%Y%m%d)
# Backup to a single archive file
mongodump --uri="mongodb://admin:password@localhost:27017" --gzip --archive=/backup/mongodb/backup-$(date +%Y%m%d).gz
Backup from a Replica Set
Always backup from a secondary to avoid impacting primary performance:
# Read from secondary member
mongodump --uri="mongodb://admin:password@node1:27017,node2:27017,node3:27017/myapp?replicaSet=rs0&readPreference=secondary" --gzip --archive=/backup/mongodb/rs-backup-$(date +%Y%m%d).gz
# Use --oplog for consistent point-in-time backup
mongodump --uri="mongodb://admin:password@localhost:27017" --oplog --gzip --out=/backup/mongodb/$(date +%Y%m%d)
The --oplog flag captures oplog entries during the dump, ensuring a consistent snapshot even while writes are occurring.
Filtered Backups
# Backup with a query filter (only recent orders)
mongodump --uri="mongodb://admin:password@localhost:27017/myapp" --collection=orders --query='{"created_at":{"$gte":{"$date":"2025-01-01T00:00:00Z"}}}' --gzip --out=/backup/filtered/
# Exclude specific collections
mongodump --uri="mongodb://admin:password@localhost:27017/myapp" --excludeCollection=sessions --excludeCollection=logs --gzip --out=/backup/mongodb/$(date +%Y%m%d)
Automated Backup Script
#!/bin/bash
# /usr/local/bin/mongodb-backup.sh
BACKUP_DIR="/backup/mongodb"
RETENTION_DAYS=14
MONGO_URI="mongodb://backup_user:BackupPass123@localhost:27017"
DATE=$(date +%Y%m%d-%H%M%S)
LOG="/var/log/mongodb-backup.log"
echo "[$(date)] Starting MongoDB backup..." >> "$LOG"
# Create backup directory
mkdir -p "$BACKUP_DIR"
# Run mongodump with compression
mongodump --uri="$MONGO_URI" \
--gzip \
--archive="$BACKUP_DIR/mongodb-$DATE.gz" \
--oplog \
2>> "$LOG"
if [ $? -eq 0 ]; then
BACKUP_SIZE=$(du -sh "$BACKUP_DIR/mongodb-$DATE.gz" | cut -f1)
echo "[$(date)] Backup completed successfully. Size: $BACKUP_SIZE" >> "$LOG"
# Upload to S3 (optional)
aws s3 cp "$BACKUP_DIR/mongodb-$DATE.gz" \
"s3://my-backups/mongodb/mongodb-$DATE.gz" \
--storage-class STANDARD_IA \
2>> "$LOG"
# Clean up old local backups
find "$BACKUP_DIR" -name "mongodb-*.gz" -mtime +$RETENTION_DAYS -delete
echo "[$(date)] Cleaned backups older than $RETENTION_DAYS days" >> "$LOG"
else
echo "[$(date)] BACKUP FAILED!" >> "$LOG"
# Send alert (e.g., webhook, email)
curl -s -X POST "https://hooks.slack.com/services/xxx" \
-H "Content-Type: application/json" \
-d "{\"text\":\"MongoDB backup FAILED on $(hostname) at $(date)\"}"
fi
# Add to crontab — daily at 3 AM
0 3 * * * /usr/local/bin/mongodb-backup.sh
Restoring from Backup
Full Restore
# Restore from directory
mongorestore --uri="mongodb://admin:password@localhost:27017" --gzip /backup/mongodb/20250115/
# Restore from archive
mongorestore --uri="mongodb://admin:password@localhost:27017" --gzip --archive=/backup/mongodb/mongodb-20250115.gz
# Restore with oplog replay (for point-in-time consistency)
mongorestore --uri="mongodb://admin:password@localhost:27017" --oplogReplay --gzip /backup/mongodb/20250115/
Selective Restore
# Restore a single database
mongorestore --uri="mongodb://admin:password@localhost:27017" --nsInclude="myapp.*" --gzip --archive=/backup/mongodb/backup.gz
# Restore a single collection
mongorestore --uri="mongodb://admin:password@localhost:27017" --nsInclude="myapp.orders" --gzip --archive=/backup/mongodb/backup.gz
# Restore to a different database name
mongorestore --uri="mongodb://admin:password@localhost:27017" --nsFrom="myapp.*" --nsTo="myapp_restored.*" --gzip --archive=/backup/mongodb/backup.gz
Restore Options
# Drop existing collections before restore (DESTRUCTIVE)
mongorestore --drop --gzip --archive=/backup/mongodb/backup.gz
# Insert only (skip existing documents)
mongorestore --noIndexRestore --gzip /backup/mongodb/20250115/
# Restore with parallel collections
mongorestore --numParallelCollections=4 --gzip /backup/mongodb/20250115/
Verifying Backups
# List contents of an archive without restoring
mongorestore --gzip --archive=/backup/mongodb/backup.gz --dryRun
# Compare document counts
mongosh --eval "db.getSiblingDB('myapp').getCollectionNames().forEach(c => print(c + ': ' + db.getSiblingDB('myapp').getCollection(c).countDocuments()))"
Performance Tuning
- Use
--gzipcompression to reduce backup size by 60-80% and speed up network transfers - Use
--archiveformat for single-file backups (easier to manage and transfer) - Set
--numParallelCollectionsto speed up both backup and restore on multi-core systems - For very large databases (100GB+), consider filesystem snapshots instead of mongodump
- Schedule backups during low-traffic periods and read from secondaries
Best Practices
- Always test restore procedures — a backup is only useful if you can restore it
- Use
--oplogfor consistent backups on replica sets - Store backups in a different location than the database (different server, cloud storage)
- Implement the 3-2-1 rule: 3 copies, 2 different media types, 1 offsite
- Monitor backup size trends to detect unexpected growth
- Encrypt backups at rest, especially when storing in cloud storage
- Document and automate your restore procedure so it can be executed under pressure