Transaction Identifiers

Author      Ter-Petrosyan Hakob

Every transaction in PostgreSQL gets a special number called an xid. xid means transaction identifier. This number helps PostgreSQL keep track of transactions.

How xid Works

How VACUUM Helps

PostgreSQL uses a tool called VACUUM to prevent the wraparound problem. One of the main jobs of VACUUM is to freeze old data. Every table row stores the xid that created it in a hidden field called xmin. When VACUUM freezes a row, PostgreSQL treats that row as old—even if the xid counter starts again from a low number. This helps keep the order of transactions clear and safe.

Special Values and the Freezing Mechanism

NOTE: The xid counter starts at 3. This means no running transaction can have an xid lower than 3. Old versions changed the xmin to 2 to mark rows as frozen, but new versions use a status bit to keep the original xmin available.

Virtual and Real Transaction Identifiers

PostgreSQL tries not to waste xid numbers. When a transaction begins, it first gets a virtual xid. A virtual xid is not taken from the main counter. This way, if a transaction only reads data without making any changes, it does not use a real xid number.

Example Workflow:

By separating virtual and real xids, PostgreSQL saves xid numbers and uses a real xid only when needed.