Skip to content

Two-Phase Commit with Freshness Check

Commit protocol — instantiates Use-Time Precondition Binding

Coordinates a multi-party action as prepare-then-commit and re-verifies every precondition is still fresh at the commit boundary before any change is allowed to land.

Two-Phase Commit with Freshness Check binds check to use across several parties that must all act together. In the first phase each participant prepares and votes that it can proceed; in the second phase a final freshness re-check runs at the commit boundary, and only if every precondition still holds does the coordinator tell everyone to commit — otherwise the whole thing aborts and each participant rolls back. Its defining move is a last-moment, all-or-nothing gate: the risky window between "everyone agreed" and "everyone acted" is closed by re-verifying freshness at the commit point itself, so no party lands its share of the change on state that went stale during preparation. Where a lock holds one resource still, this coordinates a set of them and reconciles at the end.

Example

At a real-estate closing, the pieces are "prepared" over the preceding days: the buyer's financing is approved, title comes back clear, the seller agrees to sign, funds are staged in escrow. Everyone has agreed — but nothing changes hands yet. At the closing table a final set of checks runs at that moment: title is re-run for last-minute liens, the buyer's funds are confirmed still available, no party has withdrawn. Only when all of those pass at once do the deed and the money swap — the atomic commit. If the final title search turns up a fresh lien, the closing aborts and every prepared step unwinds; nobody is left having half-transferred a house. The days-old agreement is never mistaken for permission to act; the commit is gated on freshness re-verified at the boundary.

How it works

  • Prepare and vote first. Each participant reserves its part and promises it can commit, without yet committing.
  • Re-check freshness at the boundary. Just before the point of no return, every precondition is validated again — the step that separates this from a plain commit that trusts the prepare-time agreement.
  • Commit only on unanimity. One stale check or one dissenting vote aborts the whole; there is no partial landing.
  • Roll back on abort. Every prepared-but-uncommitted step has an unwind path, so a failed commit leaves nothing half-applied.

Tuning parameters

  • Freshness-check scope — re-verify everything at commit versus only the volatile preconditions; broader is safer, narrower is faster.
  • Prepare-window length — how long parties may sit prepared before the commit; longer windows raise the odds something goes stale, and with it the abort rate.
  • Abort versus retry — on a stale check, whether to fail outright or re-prepare and try again; retry salvages progress but can livelock under churn.
  • Coordinator trust / timeout — how long participants stay prepared if the coordinator goes silent; too long freezes resources, too short abandons live commits.
  • Rollback versus compensation — whether prepared work is truly reversible or must be undone by a compensating action; the latter is needed when a step cannot simply be discarded.

When it helps, and when it misleads

Its strength is that it is the mechanism for actions that span multiple resources or parties, where a partial commit on stale state is the real disaster. The freshness gate plus all-or-nothing commit is what keeps a set of changes jointly valid at the exact instant they land — a guarantee no single-resource mechanism can give. It is the classic distributed-transaction shape, two-phase commit, hardened with a use-time re-check.[1]

Its failure mode is that coordination is expensive and the protocol blocks: participants hold resources prepared while they wait, and the notorious weakness is coordinator failure after prepare — everyone sits locked, unable to safely commit or abort. Long prepare windows raise the abort rate because there is more time to go stale, and heavy churn can drive it into repeated abort-and-retry with little forward progress. The classic misuse is weakening or skipping the freshness re-check to shave latency — which turns it back into a plain commit that trusts a days-old agreement, the exact defect the archetype targets. The discipline is to keep prepare windows short, make the freshness check non-negotiable, bound coordinator waits with timeouts, and ensure every prepared step can genuinely roll back.

How it implements the components

  • use_action_boundary — the commit point is the use-action boundary; the mechanism places its freshness gate exactly there, at the instant of no return.
  • conflict_abort_and_retry_policy — a failed freshness check or a dissenting vote triggers a defined abort (and an optional re-prepare) instead of a partial commit.
  • compensation_or_rollback_path — every prepared-but-uncommitted step has an unwind or compensating path, so an abort leaves nothing half-applied.

It does not stamp a validity_window_or_lease (that's Lease-Bound Capability Token) or freeze a single state_version_or_freshness_token to decide against (that's Snapshot-Pinned Decision); it coordinates many parties and gates their joint commit on a fresh check at the boundary.

Notes

The freshness check is what earns the name. A two-phase commit without it — plain 2PC — guarantees atomicity but not currency: all parties commit together, yet possibly against state that went stale during the prepare window. The archetype's contribution is precisely the second-phase re-verification that closes that gap.

References

[1] Two-phase commit coordinates an atomic commit across participants through a prepare/vote phase and then a commit/abort phase. Its classic limitation is blocking: if the coordinator fails after participants have voted to commit, they can be left holding resources, unable to safely resolve on their own. The use-time freshness re-check adds currency to 2PC's atomicity but inherits this coordination cost.