{"post":{"slug":"point-in-time-recovery-2026","title":"Point-in-Time Recovery: Undoing the DELETE You Regret","excerpt":"Replication copies your mistakes instantly. Point-in-time recovery is the only mechanism that lets you go back to just before someone ran a DELETE without a WHERE clause.","category":"code","date":"January 4, 2026","author":"ByteLedger Team","content":"<span class=\"dropcap\">S</span>omeone runs a `DELETE` without a `WHERE` clause against a production table at 14:31. Every replica applies it faithfully within milliseconds. High availability worked perfectly and made things worse.\n\nReplication protects against a machine failing. It does nothing about a mistake, because a mistake is a valid transaction that replicates like any other.\n\n## What changed in 2026\n\n- **Managed platforms made it standard.** Continuous archiving with a retention window became a default feature rather than a configuration project.\n- **Recovery time got scrutinised.** Teams began measuring how long a restore actually takes rather than assuming.\n- **Restore drills became expected practice.** Testing recovery moved from good hygiene to a routine requirement — see [restore drills](/blog/restore-drills-2026).\n- **Logical backups regained a role.** Alongside physical recovery, table-level logical dumps became a common complement for selective restores.\n\n## How it works\n\nTwo components.\n\n**A base backup** — a full copy of the database at some moment.\n\n**Archived write-ahead log segments** — every change since that moment, retained continuously.\n\nRecovery restores the base backup and then replays log segments up to a chosen target time. Stop replaying at 14:30 and you have the database as it was one minute before the deletion.\n\nThe window you can recover to is bounded by how far back your base backups and archives go. That retention period is your real recovery capability, and it is worth knowing rather than assuming.\n\n## Recovery time depends on backup frequency\n\nThe consequence people discover during an incident.\n\nRecovery time is dominated by replaying logs from the base backup to the target time. A base backup from a week ago means replaying a week of changes, which on a busy database can take hours.\n\n| Base backup age | Log replay | Recovery time |\n| --- | --- | --- |\n| Hours | Small | Fast |\n| A day | Moderate | Moderate |\n| A week | Large | Hours |\n| A month | Very large | Impractical |\n\nSo base backup frequency is really a recovery-time decision. More frequent base backups cost storage and reduce the time to recover. If your recovery objective is measured in minutes, a weekly base backup cannot meet it regardless of how complete your archives are.\n\nTwo numbers are worth stating explicitly and measuring rather than assuming: how much data you can lose (bounded by archive frequency) and how long recovery takes (bounded by backup frequency and replay speed).\n\n## Restoring in practice\n\n**Restore to a new instance.** Never over the original. You may need to try several target times to find the right moment, and the original may contain data written after the incident that you want to preserve.\n\n**Finding the target time** is frequently the hard part. You know roughly when the mistake happened, and narrowing it precisely usually means examining logs. Restoring to a slightly earlier time and comparing is a practical approach.\n\n**Extract rather than replace, where possible.** For an accidental deletion of one table's rows, restoring a copy and copying the missing rows back is far less disruptive than replacing the whole database and losing everything written since.\n\nThat approach preserves subsequent legitimate work, which a wholesale restore discards.\n\n**Test it.** A backup that has never been restored is an assumption. Restoring on purpose, on a schedule, is the only way to know the archives are complete, the process works, and how long it takes — see [backup verification](/blog/backup-verification-2026).\n\n## Common mistakes\n\n- **Treating replication as backup.** It replicates mistakes.\n- **Infrequent base backups.** Recovery time becomes impractical.\n- **Never testing a restore.** Discovering it fails during an incident.\n- **Restoring over the original.** Loses everything since, and forecloses retries.\n- **Not knowing the retention window.** Your actual recovery capability.\n- **Archives on the same storage as the database.** A storage failure takes both.\n- **No documented procedure.** Improvising recovery under pressure.\n\n## FAQ\n\n**How often should I take a base backup?**\nFrequently enough that log replay fits your recovery time objective. Daily is common; hourly for systems where recovery time is critical.\n\n**Does this protect against corruption?**\nSometimes — if the corruption occurred at a known time, restoring to just before it works. Gradual corruption that went unnoticed may exist in your base backups too, which is an argument for longer retention.\n\n**Can I recover a single table?**\nNot directly with physical recovery — you restore the whole database and extract what you need. Logical dumps complement this by enabling table-level restore.\n\n**How long can I go back?**\nAs far as your oldest retained base backup plus continuous archives. Know this number; it is your actual recovery capability.\n\n## Where to go next\n\nFor confirming backups actually work, read [backup verification](/blog/backup-verification-2026) and [restore drills](/blog/restore-drills-2026). For why replication is not sufficient, [replication lag](/blog/replication-lag-explained-2026) and [write-ahead logging](/blog/write-ahead-logging-explained-2026).","hue":304,"metaTitle":"Point-in-Time Recovery: Undoing the DELETE You Regret","metaDescription":"How point-in-time recovery combines a base backup with archived logs to restore any moment, and why recovery time depends on backup frequency.","keywords":["point in time recovery","pitr database","wal archiving","recovery point objective","accidental deletion recovery","backup strategy","restore testing","database operations 2026"],"tldr":["**Replication is not a backup** — it replicates deletions faithfully and immediately.","**A base backup plus archived logs lets you restore to any moment** — that is the whole mechanism.","**Recovery time scales with log volume since the base backup** — more frequent base backups mean faster recovery.","**Restore to a new instance, not over the original** — you may need to try several target times.","**Skip:** assuming your backups work. Restore one on purpose before you need to."],"readTime":"4 min read","wordCount":802},"related":[{"slug":"restore-drills-2026","title":"Restore Drills: Practising Recovery Before You Need It","excerpt":"Verified backups prove the data can come back. A drill proves your team can bring it back, under pressure, using a procedure that has been read by someone other than its author.","category":"code","date":"January 9, 2026","author":"ByteLedger Team","readTime":"4 min read","hue":308},{"slug":"backup-verification-2026","title":"Backup Verification: A Backup You Have Not Restored Is a Guess","excerpt":"Backup jobs report success by writing a file. Whether that file can be restored into a working database is a different question, and it is the only one that matters.","category":"code","date":"January 6, 2026","author":"ByteLedger Team","readTime":"4 min read","hue":313},{"slug":"failover-testing-2026","title":"Failover Testing: Finding Out Before Production Does","excerpt":"Automatic failover is configured and has never fired. Whether it works, how long it takes, and whether your application reconnects are all unknowns until you trigger it deliberately.","category":"code","date":"January 12, 2026","author":"ByteLedger Team","readTime":"4 min read","hue":308}],"sameCategory":[{"slug":"bazel-build-explained-2026","title":"Bazel Explained: What Hermetic Builds Actually Cost","excerpt":"Bazel delivers reproducible, precisely cached builds and demands that you describe everything. Here is what you get, what it costs, and who should say no.","category":"code","date":"August 19, 2026","author":"ByteLedger Team","readTime":"3 min read","hue":145},{"slug":"graphql-federation-2026","title":"GraphQL Federation: One Graph, Many Teams","excerpt":"Federation composes independently-owned subgraphs into a single API. Here is what it solves, the operational cost it adds, and when a simpler gateway is enough.","category":"code","date":"August 19, 2026","author":"ByteLedger Team","readTime":"3 min read","hue":300},{"slug":"hermetic-builds-explained-2026","title":"Hermetic Builds Explained: Same Inputs, Same Output","excerpt":"A hermetic build depends only on declared inputs. Here is what that property gives you, the common leaks that break it, and how to move toward it incrementally.","category":"code","date":"August 19, 2026","author":"ByteLedger Team","readTime":"3 min read","hue":130},{"slug":"monorepo-tooling-compared-2026","title":"Monorepo Tooling Compared: What You Actually Need","excerpt":"Monorepo tools solve task orchestration and caching, not repository layout. Here is what each tier provides and how to tell when you have outgrown the simple option.","category":"code","date":"August 19, 2026","author":"ByteLedger Team","readTime":"3 min read","hue":150}],"newer":{"slug":"lock-timeouts-explained-2026","title":"Lock Timeouts: Failing Fast Instead of Queueing Forever","excerpt":"A migration waiting for a lock does not just wait. Everything arriving behind it queues too, and a brief schema change becomes a full outage.","category":"code","date":"January 4, 2026","author":"ByteLedger Team","readTime":"4 min read","hue":300},"older":{"slug":"webhook-signing-explained-2026","title":"Webhook Signing: Verifying What Arrived at Your Endpoint","excerpt":"Your webhook endpoint is a public URL anyone can post to. Without signature verification, anyone can tell your system that a payment succeeded.","category":"code","date":"January 4, 2026","author":"ByteLedger Team","readTime":"4 min read","hue":308}}