pg_rewind — synchronise le répertoire des données de PostgreSQL avec un autre répertoire de données
pg_rewind
[option
...] { -D
| --target-pgdata
} répertoire
{ --source-pgdata=
| répertoire
--source-server=
} chaine_de_connexion
pg_rewind est un outil qui permet de synchroniser une instance PostgreSQL avec une copie de cette même instance, a postériori de la séparation des timelines. Le scénario classique consiste à réactiver un ancien serveur primaire, après une bascule, en tant que serveur secondaire répliqué depuis le nouveau serveur primaire.
Le résultat est le même que lorsqu'on remplace le répertoire de données cible avec celui de la source. Seuls les blocs modifiés des fichiers des relations déjà existants sont copiés, tous les autres fichiers sont copiés intégralement, fichiers de configurations compris. L'avantage de pg_rewind par rapport à la réalisation d'une nouvelle sauvegarde de base, ou l'utilisation d'un outil tel que rsync, est que pg_rewind n'a pas besoin de lire tous les blocs non modifiés des fichiers de l'ancienne instance. Cela rend l'opération éminement plus rapide lorsqu'on est face à une volumétrie conséquente et qu'il a peu de différences entre les deux instances.
pg_rewind inspecte l'historique de la timeline
de l'instance source et de l'instance cible pour déterminer à quel moment a
eu lieu la séparation, et s'attend à trouver tous les fichiers WAL jusqu'au
moment de la bascule dans le répertoire pg_wal
. Le
point de divergence peut être trouvé soit sur la ligne de temps cible, soit
sur la ligne de temps source, soit sur leur ancêtre commun. Dans un
scénario de bascule classique, où l'instance cible a été arrêtée peu après
le changement, cela ne pose aucun problème. En revanche, si l'instance
cible a travaillé un certain temps après le changement, les anciens
fichiers WAL peuvent ne plus être présents dans le répertoire
pg_wal
. Dans ce cas, ils peuvent être copiés à la main
depuis les fichiers WAL archivés vers le répertoire
pg_wal
.
L'utilisation de pg_rewind n'est pas limitée au
failover : un serveur standby peut être promu, écrire quelques
transactions, puis transformé de nouveau en standby avec cet outil.
Lorsque l'instance cible est démarrée pour la première fois après avoir
utilisé pg_rewind, elle va se mettre en mode de
restauration (recovery) et va rejouer tous
les fichiers WAL générés par l'instance source depuis la bascule. Si
certains fichiers WAL ne sont plus disponibles sur la source lorsque
pg_rewind est en cours, ils ne peuvent donc plus
être copiés par la session pg_rewind. Il est
alors nécessaire de faire en sorte qu'ils puissent être disponibles lorsque
le serveur cible sera démarré. Cela est possible en créant un fichier
recovery.signal
dans le répertoire des données cible
et en configurant correctement le paramètre restore_command dans le fichier
postgresql.conf
.
pg_rewind nécessite que l'instance cible ait
l'option wal_log_hints activée dans le fichier de
configuration postgresql.conf
ou que les sommes de
contrôle sur les données aient été activées lorsque l'instance a été
initialisée par la commande initdb. Aucune de
ces options n'est active par défaut. Le paramètre full_page_writes doit lui aussi être activé. Il l'est par
défaut.
Si pg_rewind échoue lors du traitement, le répertoire des données de la cible est très probablement dans un état inutilisable. Dans ce cas, réaliser une nouvelle sauvegarde est recommandé.
pg_rewind échouera immédiatement s'il trouve des fichiers qu'il ne peut pas modifier. Ceci peut arriver quand les serveurs source et cible utilisent les mêmes emplacements pour les clés et les certificats SSL qui sont habituellement en lecture seule. Si de tels fichiers sont présents sur le serveur cible, il est recommandé de les supprimer avant d'exécuter pg_rewind. Après l'avoir exécuté, certains de ces fichiers devront peut-être être copiés de la source, auquel cas il pourrait être nécessaire de supprimer les données copiées et de restaurer l'ensemble des liens utilisés avant l'exécution de l'outil.
pg_rewind accepte les arguments suivants en ligne de commande :
-D répertoire
--target-pgdata=répertoire
Cette option définit le répertoire de données cible qui va être synchronisé avec le répertoire source. Cette option requiert que le serveur source ait été arrêté proprement.
--source-pgdata=répertoire
Cette option définit le répertoire de données source qui va être synchronisé avec le répertoire cible. Si cette option est utilisée, l'instance source doit être arrêtée proprement.
--source-server=chaine de connexion
Définit une chaine de connexion libpq permettant d'accéder à l'instance PostgreSQL source de façon à pouvoir la synchroniser avec la cible. Cette option requiert l'utilisation d'une connexion standard avec un rôle ayant les droits suffisants pour exécuter les fonctions utilisées par pg_rewind sur le serveur source (voir la section Notes pour les détails) ou un rôle superutilisateur.
-n
--dry-run
Réalise toutes les opérations sans modifier le répertoire cible.
-N
--no-sync
Par défaut, pg_rewind
attendra l'écriture certaine
de tous les fichiers sur disque. Cette option permet de forcer le
retour de pg_rewind
sans attente, ce qui est plus
rapide, mais signifie qu'un crash ultérieur du système d'exploitation
pourrait laisser le répertoire des données dans un état
corrompu. En général, cette option est utile pour des tests, mais ne
devrait pas être utilisée pour créer un serveur en production.
-P
--progress
Permet d'activer les traces. Activer cette option vous fournira les informations au fil de l'eau sur l'avancée de la copie des données depuis l'instance source.
--debug
Affiche les détails de la sortie de débogage, ce qui est surtout utile aux développeurs qui travaillent sur pg_rewind.
-V
--version
Affiche les informations concernant la version, puis quitte.
-?
--help
Affiche l'aide, puis quitte.
Lorsque l'option --source-server
est utilisée,
pg_rewind utilise aussi les variables
d'environnement supportées par la bibliothèque
libpq (voir Section 33.14).
La variable d'environnement PG_COLOR
indique s'il faut
utiliser les couleurs dans les messages de diagnotiques. Les valeurs
possibles sont always
, auto
,
never
.
Lors de l'exécution de pg_rewind sur une
instance en ligne comme source, un rôle doté des droits suffisants pour
exécuter les fonctions utilisées par pg_rewind
sur l'instance source peut être utilisé à la place d'un superutilisateur.
Voici comment créer ce rôle, nommé ici
rewind_user
:
CREATE USER rewind_user LOGIN; GRANT EXECUTE ON function pg_catalog.pg_ls_dir(text, boolean, boolean) TO rewind_user; GRANT EXECUTE ON function pg_catalog.pg_stat_file(text, boolean) TO rewind_user; GRANT EXECUTE ON function pg_catalog.pg_read_binary_file(text) TO rewind_user; GRANT EXECUTE ON function pg_catalog.pg_read_binary_file(text, bigint, bigint, boolean) TO rewind_user;
Lors de l'exécution de pg_rewind sur une
instance en ligne comme source récemment promue, il est nécessaire
d'exécuter un CHECKPOINT
après la promotion pour que son
fichier de contrôle reflète des informations de timeline à jour, qui est
utilisé par pg_rewind pour vérifier si
l'instance cible peut être rembobiné en utilisant l'instance source
désignée.
L'idée de base est de copier toutes les modifications de fichiers au niveau système de fichiers de l'instance source vers l'instance cible :
Parcourir les journaux de transactions de l'instance cible, en commençant du dernier checkpoint avant le moment où l'historique de timeline de l'instance source a dévié de celle de l'instance cible. Pour chaque enregistrement dans les journaux de transactions, enregistrer chaque bloc de données modifié. Ceci a pour résultat une liste de tous les blocs de données modifiés dans l'instance cible, après la séparation avec l'instance source.
Copier tous les blocs modifiés de l'instance source vers l'instance
cible, soit en utilisant un accès direct au système de fichiers
(--source-pgdata
) soit en SQL
(--source-server
).
Copier tous les autres fichiers, tels que pg_xact
et les fichiers de configuration de l'instance source vers l'instance
cible (sauf les fichiers des relations). De façon similaire aux
sauvegardes de base, le contenu des répertoires
pg_dynshmem/
, pg_notify/
,
pg_replslot/
, pg_serial/
,
pg_snapshots/
, pg_stat_tmp/
et
pg_subtrans/
sont omis des données copiées à partir
de l'instance source. Tout fichier ou répertoire commençant par
pgsql_tmp
est omis, ainsi que
backup_label
, tablespace_map
,
pg_internal.init
,
postmaster.opts
et
postmaster.pid
.
Appliquer les enregistrements des journaux de transactions provenant de l'instance source, en commençant à partir du checkpoint créé au moment du failover. (En fait, pg_rewind n'applique pas les journaux de transactions. Il crée simplement un fichier backup_label qui fera en sorte que PostgreSQL démarre en rejouant les enregistrements des journaux de transactions à partir de ce checkpoint.)