skip to content

Log records in a write-ahead log are stamped with a monotonically increasing log sequence number, and data pages carry one too. What is an LSN used for?

level: seniorimportance: should knowfreq 38%

answer

  1. monotonic; usually a byte offset in the log
  2. pageLSN = last change reflected in the page
  3. flush page only if flushedLSN >= pageLSN
  4. redo skipped when pageLSN >= record LSN
  5. lag and PITR measured in LSNs

basics

~20 s

An LSN is a monotonically increasing position in the log. Each page stores the LSN of the last change applied to it, so the engine can enforce log-before-data, skip redo of changes a page already has, and address a point in the log stream.

solid answer

~50 s

A **log sequence number** is a monotonically increasing identifier for a log record — usually its byte offset in the log stream, so it doubles as an address. Every data page header stores a **pageLSN**: the LSN of the most recent log record whose change is reflected in that page. That single field does three jobs. 1. **Enforcing write-ahead ordering.** Before flushing a page, the engine checks that the log has been flushed at least up to the page's pageLSN. If not, it flushes the log first. 2. **Making redo idempotent.** During recovery the engine compares each redo record's LSN with the page's pageLSN. If pageLSN is already greater than or equal to it, that change is already in the page and is skipped. Recovery can therefore crash and restart safely. 3. **Addressing positions in the stream.** \"Flushed up to LSN X\", \"replica has applied up to LSN Y\", \"restore to LSN Z\" are all expressed with LSNs, which is what makes replication lag and point-in-time recovery measurable.

code

text · 7 lines
text
redo record: LSN=5000, page=42, action=...

read page 42 -> header.pageLSN = 4800
4800 < 5000  -> apply change, set header.pageLSN = 5000

read page 42 -> header.pageLSN = 5200
5200 >= 5000 -> already applied, skip (redo stays idempotent)

go deeper

for a junior

It is enough to know an LSN is an increasing position in the log that identifies where a change sits in the sequence.

for a middle

Add the pageLSN and explain the flush check and the skip-if-already-applied rule during redo.

for a senior

Use LSNs operationally — measuring replica lag in log bytes, reasoning about which LSN pins log segments, choosing a recovery target.

for a principal

Treat the log position as the system's global ordering primitive and reason about what depends on it: commit acknowledgement thresholds, replication protocols, timeline divergence after failover, and recovery-target design.

## What an LSN is A log sequence number is a value assigned to each log record such that later records always get larger values. In most engines it is literally the record's byte position in the logical log stream, which makes it both an ordering and an address: given an LSN you can seek straight to the record. Because it is monotonic, comparisons are meaningful: LSN A < LSN B means the change described by A happened before the change described by B. ## pageLSN: the link between log and data The crucial trick is that the LSN is also written into the data page. Each page header holds a **pageLSN** — the LSN of the latest log record whose effect is present in that page's bytes. When a transaction modifies the page, the engine writes the log record, then stamps its LSN into the page header. This is what welds the two structures together. ### Job 1 — enforcing the write-ahead rule mechanically The write-ahead protocol says a page may not be written to disk before the log records describing its changes. With pageLSN, that becomes a one-line check in the buffer manager: before writing page P, ensure `flushedLSN >= P.pageLSN`; otherwise flush the log first. No bookkeeping of which transactions touched which pages is needed. ### Job 2 — idempotent redo Recovery replays the log forward. But recovery itself can be interrupted — the machine can crash again halfway through — so replay must be repeatable without double-applying anything. Consider a redo record with LSN 5000 for page 42. The engine reads page 42 from disk and inspects its pageLSN: - pageLSN = 4800 → the page predates this change; apply the redo and set pageLSN to 5000. - pageLSN = 5200 → the page already reflects this change and later ones; skip it. This matters because operations are not naturally idempotent. \"Decrement the balance by 60\" applied twice is wrong; the LSN comparison is what prevents it. It also means recovery does not need to know which pages were flushed before the crash — the pages tell it themselves. ### Job 3 — a coordinate system for the whole system Because LSNs are positions in a single ordered stream, they become the vocabulary for everything built on the log: - **Commit durability**: a commit is durable once the flushed LSN reaches its commit record's LSN. Sessions waiting on commit wait on that threshold, which is what enables group commit — one flush satisfies every waiter below the new flushed LSN. - **Replication**: a replica reports the LSN it has received, written, flushed and applied. Lag is the difference between the primary's current LSN and the replica's, measured in bytes of log — a far more meaningful number than seconds. - **Point-in-time recovery**: restore a base backup, then replay archived log up to a chosen LSN (or the timestamp mapped to one). - **Checkpoints**: a checkpoint record notes the LSN from which redo must start, since everything before it is guaranteed present in the data files. ## Related bookkeeping Undo processing needs its own chain, so log records typically also carry a **prevLSN** pointing to the previous record of the same transaction — a linked list that lets the engine walk one transaction's changes backwards without scanning the whole log. Recovery designs that log the undo work itself add a pointer to the next record still to be undone, so that even rollback is restartable. ## Practical implications Monotonicity is a real constraint: LSNs cannot be reused or rewound, which is why you cannot simply hand-edit or truncate a log and why a replica promoted ahead of its former primary creates a timeline divergence that must be tracked explicitly. And operationally, LSN arithmetic is how you answer real questions: how much log a lagging replica still has to consume, how much log a stalled archiver is pinning on disk, how far behind a standby is in bytes rather than guesses. ## Interview framing \"It is a monotonic address into the log, and because the page carries the LSN of its latest change, the engine can cheaply enforce log-before-data and skip redo the page already contains.\"

  • Why can't recovery just replay every redo record unconditionally instead of comparing LSNs?
    Because most logged operations are not idempotent — re-applying "subtract 60 from this balance" or "insert a tuple into this slot" twice corrupts the page. The pageLSN comparison tells recovery whether a given change is already baked into the page image it read from disk. It also makes recovery restartable: crashing halfway through replay and starting over produces the same final state.
  • How does the LSN make group commit possible?
    Every committing session waits for the flushed LSN to reach its own commit record's LSN. Since the log is a single ordered stream, one fsync that advances the flushed LSN past many commit records satisfies all of those waiters at once. The engine therefore batches concurrent commits into one durable write, converting per-commit flush cost into per-batch cost as concurrency rises.

saying these in an interview costs you the question

  • Describing the LSN as a transaction id or a timestamp
  • Not knowing the LSN is also stored in the page header
  • Claiming redo is applied unconditionally to every page
  • Saying LSNs can be reset or reused to reclaim space
  • Treating replication lag as purely time-based with no notion of log position

context