PG_AUTOCTL PERFORM PROMOTION(1)
π pg_autoctl perform promotion β the manual, but make it cute π
okay bestie, gather round π«Ά this one's from pg_auto_failover, and it's genuinely one of my faves because it lets you hand-pick who becomes the new primary. no cap.
β¨ NAME β¨
pg_autoctl perform promotion β bestie, it's literally the promotion command. π
pg_autoctl perform promotion β Perform a failover that promotes a target node. that's it, that's the whole job. she's a queen π
πΈ SYNOPSIS πΈ
so the monitor (pg_auto_promotion) kicks off a Postgres failover orchestration, and it aims it at whichever node you name:
usage: pg_autoctl perform promotion [ --pgdata --formation --group ]
--pgdata path to data directory
--formation formation to target, defaults to 'default'
--name node name to target, defaults to current node
--wait how many seconds to wait, default to 60
π¦ DESCRIPTION π¦
the pg_auto_promotion monitor can orchestrate a manual promotion, which some people also call a switchover (same vibe, different name, iykyk). and here's the slay part: when it does that, split-brain is prevented because the Finite State Machine uses intermediary states. she does not let two primaries happen. not on her watch π
the pg_autoctl perform promotion command just sits there and waits until the promotion is known complete on the monitor, or until the hard-coded 60s timeout has passed. whichever comes first, periodt.
also important: the promotion orchestration happens in the background, done by the monitor. so even if pg_autoctl perform promotion gives up on the timeout, the promotion keeps going at the monitor. she's not stopping for you, bestie, she's got main character energy β¨
π OPTIONS π
--pgdataβ where the Postgres node that's being managed locally lives. defaults to the environment variablePGDATA. and heads up: use--monitorto connect to a monitor from literally anywhere, instead of the monitor URI that a local Postgres node managed withpg_autoctlis using. π--formationβ which formation to target for the operation. defaults todefault.--nameβ name of the node that should be elected as the new primary node. your pick, your power π--waitβ how many seconds to wait for notifications about the promotion. the command stops when the promotion is finished (meaning a node is primary), or when the timeout has elapsed, whichever happens first. and the value0(zero) disables the timeout and lets the command wait forever. forever ever. no cap π
π ENVIRONMENT π
PGDATAβ Postgres directory location. can be used instead of the--pgdataoption. same thing, less typing πPG_AUTOCTL_MONITORβ Postgres URI to connect to the monitor node, can be used instead of the--monitoroption.PG_CONFIGβ can be set to the absolute path to thepg_configPostgres tool. this is mostly used in the context of building extensions, though it can be a useful way to select a Postgres version when several are installed on the same system.PATHβ used the usual way, mostly. some entries that are searched in thePATHby thepg_autoctlcommand are expected to be found only once, to avoid mistakes with Postgres major versions. one copy, please π«ΆPGHOST,PGPORT,PGDATABASE,PGUSER,PGCONNECT_TIMEOUT,...β see the Postgres docs about Environment Variables for details.TMPDIRβ thepgcopydbcommand creates all its work files and directories in${TMPDIR}/pgcopydb, and defaults to/tmp/pgcopydb.XDG_CONFIG_HOMEβ thepg_autoctlcommand stores its configuration files in the standard placeXDG_CONFIG_HOME. see the XDG Base Directory Specification.XDG_DATA_HOMEβ thepg_autoctlcommand stores its internal states files in the standard placeXDG_DATA_HOME, which defaults to~/.local/share. see the XDG Base Directory Specification.
β EXAMPLES β
okay so let's look at where we start. three nodes, node2 is the primary, everyone else is a secondary:
$ pg_autoctl show state
Name | Node | Host:Port | LSN | Connection | Current State | Assigned State
------+-------+----------------+-----------+--------------+---------------------+--------------------
node1 | 1 | localhost:5501 | 0/4000F88 | read-only | secondary | secondary
node2 | 2 | localhost:5502 | 0/4000F88 | read-write | primary | primary
node3 | 3 | localhost:5503 | 0/4000F88 | read-only | secondary | secondary
now we ask for a promotion targeting node1, and bestie, watch the states dance. this is the FSM doing her little choreography and honestly it's iconic:
$ pg_autoctl perform promotion --name node1
13:08:13 15297 INFO Listening monitor notifications about state changes in formation "default" and group 0
13:08:13 15297 INFO Following table displays times when notifications are received
Time | Name | Node | Host:Port | Current State | Assigned State
---------+-------+-------+----------------+---------------------+--------------------
13:08:13 | node1 | 0/1 | localhost:5501 | secondary | secondary
13:08:13 | node2 | 0/2 | localhost:5502 | primary | draining
13:08:13 | node2 | 0/2 | localhost:5502 | draining | draining
13:08:13 | node1 | 0/1 | localhost:5501 | secondary | report_lsn
13:08:13 | node3 | 0/3 | localhost:5503 | secondary | report_lsn
13:08:19 | node3 | 0/3 | localhost:5503 | report_lsn | report_lsn
13:08:19 | node1 | 0/1 | localhost:5501 | report_lsn | report_lsn
13:08:19 | node1 | 0/1 | localhost:5501 | report_lsn | prepare_promotion
13:08:19 | node1 | 0/1 | localhost:5501 | prepare_promotion | prepare_promotion
13:08:19 | node1 | 0/1 | localhost:5501 | prepare_promotion | stop_replication
13:08:19 | node2 | 0/2 | localhost:5502 | draining | demote_timeout
13:08:19 | node3 | 0/3 | localhost:5503 | report_lsn | join_secondary
13:08:19 | node2 | 0/2 | localhost:5502 | demote_timeout | demote_timeout
13:08:19 | node3 | 0/3 | localhost:5503 | join_secondary | join_secondary
13:08:20 | node1 | 0/1 | localhost:5501 | stop_replication | stop_replication
13:08:20 | node1 | 0/1 | localhost:5501 | stop_replication | wait_primary
13:08:20 | node2 | 0/2 | localhost:5502 | demote_timeout | demoted
13:08:20 | node1 | 0/1 | localhost:5501 | wait_primary | wait_primary
13:08:20 | node3 | 0/3 | localhost:5503 | join_secondary | secondary
13:08:20 | node2 | 0/2 | localhost:5502 | demoted | demoted
13:08:20 | node2 | 0/2 | localhost:5502 | demoted | catchingup
13:08:21 | node3 | 0/3 | localhost:5503 | secondary | secondary
13:08:21 | node1 | 0/1 | localhost:5501 | wait_primary | primary
13:08:21 | node2 | 0/2 | localhost:5502 | catchingup | catchingup
13:08:21 | node1 | 0/1 | localhost:5501 | primary | primary
and look at that glow-up π₯Ή node1 is the primary now, node2 got demoted and caught up as a secondary, node3 is chillin' as a secondary. ate. no crumbs.
$ pg_autoctl show state
Name | Node | Host:Port | LSN | Connection | Current State | Assigned State
------+-------+----------------+-----------+--------------+---------------------+--------------------
node1 | 1 | localhost:5501 | 0/40012F0 | read-write | primary | primary
node2 | 2 | localhost:5502 | 0/40012F0 | read-only | secondary | secondary
node3 | 3 | localhost:5503 | 0/40012F0 | read-only | secondary | secondary
π AUTHOR π
Microsoft
π COPYRIGHT π
Copyright (c) Microsoft Corporation. All rights reserved.
and that's the whole page, bestie! this is version 2.2, dated Apr 07, 2025, from the pg_auto_failover project π go promote somebody, you got this π«Άβ¨
π¦ where this page comes from
- debian trixie: pg-auto-failover-cli 2.2-2 Β· PostgreSQL
- ubuntu questing: pg-auto-failover-cli 2.2-2
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash on : a language model's rewrite of the original, under its terms