Repository navigation
Publish the recovered log end as the first checkpoint's lsn - #92
Merged
venkat1701 merged 3 commits intoOct 14, 2026
Merged
Conversation
When recovery replayed no commit, the first checkpoint put the old lsn back, so WAL records of a transaction that never committed stayed in the replay window. A new transaction could be handed the same id, and after a second crash recovery applied both as one commit. That made a node that was never acknowledged visible, and let a half-written transaction delete committed data. Start the checkpointer from the lsn recovery already computed. Fixes metacoglabs#91
Covers the durable-prefix case of the same problem: after recovery drops commits whose pages are missing, a commit made afterwards was lost on the next unclean stop. Refs metacoglabs#91
The next transaction id was only restored from Commit records, so the id of a transaction that died before committing was handed out again while its records were still in the log. Raise the recovered next id above the highest id found in the log. Refs metacoglabs#91
venkat1701
approved these changes
Oct 14, 2026
venkat1701
left a comment
Collaborator
There was a problem hiding this comment.
Checked: the three new tests fail on main and pass with the fix, full suite green. Thanks.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #91.
If recovery doesn't replay any commit, the first checkpoint after it put the old lsn back. That left the WAL records of a transaction that never committed inside the replay window. The next transaction can get the same id, and if the process is killed again before a checkpoint, recovery applies both as one commit.
So a node nobody ever got an ack for shows up, and a half-written transaction can delete committed data.
The fix is one line: start the
Checkpointerfrom the lsn recovery already computed. When recovery does replay commits that's what was used anyway, so nothing changes there.TxnIdReuseTestcrashes mid-commit, reopens, commits something, crashes again and reopens. One test checks the never-committed node stays gone, the other that committed data survives. Both fail onmainand pass now../mvnw installis green on JDK 25 (engine 170, db 35, server 15).The same lsn also covered commits dropped by the durable-prefix rule: a commit made after recovery discarded a bad tail was lost on the next crash.
commitsAfterADiscardedTailSurviveTheNextCrashinCrashRecoveryTestcovers it, and fails onmaintoo.As suggested on the issue, recovery also raises the next transaction id above the highest id it finds in the log, so an id from a dead transaction is never handed out again (
transactionIdsAreNotReusedAfterACrash).