Percona Backup for MongoDB: logical, physical and PITR
Run consistent backups of replica sets and sharded clusters with PBM, enable point-in-time recovery from oplog slices, and rehearse restores.
- Describe PBM architecture: agents, storage, control collections
- Choose logical, physical or incremental backups
- Enable PITR and restore to a timestamp
- Run and validate a restore drill
conceptThe concept
Percona Backup for MongoDB (PBM) is an open-source backup tool for replica sets and sharded clusters. A pbm-agent runs next to every mongod; you drive it with the pbm CLI. Agents coordinate through control collections in the admin database and write to remote storage (S3-compatible, GCS, Azure Blob or a shared filesystem).
| Type | How | Best for |
|---|---|---|
| Logical | Exports documents and replays the oplog for consistency | Small and medium data, selective restore of namespaces, version changes |
| Physical | Copies WiredTiger files through a backup cursor (Percona Server for MongoDB) | Large data sets; restore time close to copy time |
| Incremental physical | Copies only changed blocks since the base | Very large data with frequent backups |
| PITR | Agents continuously upload oplog slices | Restoring to just before a bad operation |
For sharded clusters PBM produces a backup that is consistent across shards and the config server replica set.
whyWhy it matters
mongodump alone is not consistent across shards, is slow on large data and has no point-in-time capability. A self-hosted MongoDB estate needs scheduled backups, PITR and tested restores; PBM provides that without a commercial licence, and it is what the Percona Operator uses on Kubernetes.
Use caseReal-world scenario
At 14:05 a script runs deleteMany({}) on orders. The DBA lists backups, picks the nightly physical backup, and restores to 14:04:59 on a staging cluster with pbm restore --time. After validating counts, the orders collection is copied back to production. Total time: 40 minutes, data loss: zero.
Try itExamples
Run and edit these in the interactive lesson.
# /etc/pbm/pbm_config.yaml
storage:
type: s3
s3:
region: ap-south-1
bucket: acme-mongo-backups
prefix: prod-rs0
pitr:
enabled: true
oplogSpanMin: 10
export PBM_MONGODB_URI="mongodb://pbmuser:****@localhost:27017/?authSource=admin&replSetName=rs0"
pbm config --file /etc/pbm/pbm_config.yaml
pbm statuspbm backup --type=physical # or logical, incremental --base
pbm list # snapshots and the PITR timeline
pbm restore 2026-10-07T23:00:12Z # full restore of one snapshot
pbm restore --time="2026-10-08T14:04:59" # point in time
pbm restore 2026-10-07T23:00:12Z --ns=shop.orders # selective (logical backups)
pbm logs --tail=50use admin
try { db.dropUser("pbmuser") } catch (e) {}
try { db.dropRole("pbmAnyAction") } catch (e) {}
db.createRole({ role: "pbmAnyAction", privileges: [{ resource: { anyResource: true }, actions: ["anyAction"] }], roles: [] })
db.createUser({ user: "pbmuser", pwd: "change-me", roles: ["backup", "clusterMonitor", "restore", { role: "pbmAnyAction", db: "admin" }] })
db.getUser("pbmuser").roles.map(r => r.role)const summary = db.getCollectionNames().filter(c => !c.startsWith("system.") && !c.startsWith("lab_"))
.map(c => ({ coll: c, docs: db.getCollection(c).countDocuments(), indexes: db.getCollection(c).getIndexes().length }));
summaryinternalsUnder the hood
With PITR enabled, one agent per replica set uploads the oplog in chunks (10 minutes by default). A PITR restore applies the base backup, then replays slices up to the requested time; the timeline is only continuous if PITR has been running since the last base backup. During a physical restore PBM stops the mongod processes and replaces their data, so restores are disruptive and require agents on every node. Users and roles are part of the backup, which matters when restoring into a different cluster.
Avoid / preferDo this, not that
# backups to a bucket, never restored pbm backup --type=logical
# scheduled backups plus a regular restore drill into a scratch cluster pbm backup --type=physical pbm list pbm restore <backup_name> # on the drill cluster, then verify counts
A backup you have never restored is a hope, not a plan. Drills find missing permissions, wrong storage settings and slow restore times before an incident does.
pbm config --set pitr.enabled=false # base backups only
pbm config --set pitr.enabled=true pbm restore --time="2026-10-08T09:15:00"
Base backups alone lose everything since the last backup. With PITR, PBM saves oplog slices continuously so you can restore to just before the bad write.
PitfallsCommon mistakes
- Running pbm-agent on only some nodes; every mongod needs an agent.
- Never testing a restore, so the first attempt happens during an incident.
- Disabling PITR temporarily and not noticing the gap in the timeline.
- Restoring a physical backup straight over production instead of a side cluster when only one collection is damaged.
LimitsWhen not to use it
PBM backs up replica sets and sharded clusters with consistent cluster-wide snapshots. For a single small database where minutes of loss are acceptable, a scheduled mongodump may be enough. Physical backups are fast for large data sets but restore only to the same major version and need the cluster stopped during restore.
SecuritySecurity notes
The PBM user needs backup and restore privileges on the whole cluster; keep its credentials out of shell history and scripts. Lock down the storage bucket (no public access, versioning or object lock against deletion, server-side encryption), because the backups contain every document.
ChallengeTry it yourself
Write the PBM commands to enable PITR, take a physical backup, list backups and restore to 09:15 today.
Show one solution
pbm config --file /etc/pbm/pbm-config.yaml
pbm config --set pitr.enabled=true
pbm backup --type=physical
pbm list
pbm restore --time="2026-10-08T09:15:00"InterviewQuestions you should be able to answer
How would you recover from an accidental deleteMany on a self-hosted replica set?
Find the exact time from the oplog (op: "d" burst on that namespace). With PBM and PITR enabled, restore the last base backup plus oplog up to one second before the delete onto a staging cluster (pbm restore --time), validate, and copy the collection back. Without PITR, restore the last snapshot and replay the oplog manually with mongorestore --oplogReplay --oplogLimit. Afterwards, restrict delete privileges and rehearse restores.
QuizCheck your understanding
4 questions with instant feedback in the interactive lesson; a wrong answer goes into your review deck.