Replikering är en nyckelfunktion för de flesta inställningar och den stöds av de flesta databastekniker på marknaden. PostgreSQL-communityt introducerade replikering i version 9.0 (kallad Streaming Replication eller SR), sedan dess har replikeringen i PostgreSQL utvecklats med ytterligare funktioner som Cascading Replication, Logical Decoding och flera andra optimeringar.
I den här bloggen kommer vi att titta på hur vi använder Ansible-rollen postgresql som utvecklats av "Demonware" (en gaffel av rollen "ANXS/postgresql"). Jag hade redan pratat om att använda rollen "ANXS/postgresql" i min tidigare blogg men jag diskuterade inte replikeringsfunktionen. Ansible-rollen "postgresql" lägger till möjligheten att ställa in PostgreSQL-replikering med repmgr.
Om Repmgr
Repmgr är ett kommandoradsverktyg med öppen källkod utvecklat och underhållet av 2ndQuadrant. Verktyget automatiserar de flesta uppgifter relaterade till hantering av PostgreSQL-replikeringsklustret. Nedan är listan över uppgifter som kan utföras smidigt med repmgr-kommandot och repmgrd-demonen.
- Starta PostgreSQL-replikeringsklustret.
- Gör auto-failover och manuell övergång av den primära instansen.
- Lägga till och ta bort standby- (läs-replik)-instanser.
Förbereder kontrollnoden
Förbered kontrollernoden med rollen Ansible PostgreSQL, spelböcker, inventeringar och anpassad PostgreSQL-replikering.
$ mkdir demo
$ pushd demo
$ mkdir roles
$ git clone https://github.com/Demonware/postgresql roles/postgresql
$ pushd roles/postgresql
$ git checkout add-repmgr-extension
I den nedladdade rollen finns det två standardvariabelfiler main.yml och repmgr.yml-fil. Ansible kommer dock endast att överväga filen main.yml. För att göra Ansible använd också filen repmgr.yml, vi flyttar båda filerna till katalogen defaults/main.
$ mkdir defaults/main
$ mv defaults/main.yml defaults/repmgr.yml defaults/main
$ popd
Ansible Inventory File
För demon kommer vi att ställa in PostgreSQL-replikeringsklustret på tre noder. Jag skapade tre CentOS virtuella datorer vm-01, vm-02 och vm-03, alla är listade under gruppen postgres_cluster i filen development.yaml.
$ cat development.yaml
all:
children:
postgres_cluster:
hosts:
vm-01:
vm-02:
vm-03:
vars:
ansible_user: "vagrant"
Gör Ansible-pinga och se till att vi kan nå alla värdar under gruppen postgres_cluster.
$ ansible -i development.yaml -m ping postgres_cluster
vm-01 | SUCCESS => {
"changed": false,
"ping": "pong"
}
vm-03 | SUCCESS => {
"changed": false,
"ping": "pong"
}
vm-02 | SUCCESS => {
"changed": false,
"ping": "pong"
}
Anpassad variabelfil
I den anpassade variabelfilen custom-vars.yaml kommer vi att definiera följande saker:
- PostgreSQL-version att installera och kodning att använda
- Om du ändrar PostgreSQL-konfigurationen för att möjliggöra replikering kommer vi att modifiera parametrarna som wal_level, max_wal_senders, max_replication_slots, hot_standby, archive_mode, archive_command
- Skapa nödvändiga användare och databas
- Ändra filen pg_hba.conf för att tillåta den nödvändiga anslutningen från programmet och repmgr-replikeringen
- Några repmgr-relaterade variabler
$ cat custom-vars.yaml
# Basic settings
postgresql_version: 11
postgresql_encoding: "UTF-8"
postgresql_locale: "en_US.UTF-8"
postgresql_ctype: "en_US.UTF-8"
postgresql_admin_user: "postgres"
postgresql_default_auth_method: "peer"
postgresql_listen_addresses: "*"
postgresql_wal_level: "replica"
postgresql_max_wal_senders: 10
postgresql_max_replication_slots: 10
postgresql_wal_keep_segments: 100
postgresql_hot_standby: on
postgresql_archive_mode: on
postgresql_archive_command: "/bin/true"
postgresql_shared_preload_libraries:
- repmgr
postgresql_users:
- name: "{{repmgr_user}}"
pass: "password"
postgresql_databases:
- name: "{{repmgr_database}}"
owner: "{{repmgr_user}}"
encoding: "UTF-8"
postgresql_user_privileges:
- name: "{{repmgr_user}}"
db: "{{repmgr_database}}"
priv: "ALL"
role_attr_flags: "SUPERUSER,REPLICATION"
postgresql_pg_hba_custom:
- { type: "host", database: "all", user: "all", address: "192.168.0.0/24", method: "md5" }
- { type: "host", database: "replication", user: "repmgr", address: "192.168.0.0/24", method: "md5" }
- { type: "host", database: "replication", user: "repmgr", address: "127.0.0.1/32", method: "md5" }
# repmgr related variables
postgresql_ext_install_repmgr: yes
repmgr_target_group: "postgres_cluster"
repmgr_target_group_hosts: "{{ groups[repmgr_target_group] }}"
repmgr_master: "vm-03"
Följande är några av de anmärkningsvärda variablerna som definieras i custom-vars.yaml:
- postgresql_version:11 - Installerar PostgreSQL version 11
- postgresql_ext_install_repmgr:ja - Installerar repmgr-tillägget på PostgreSQL-klustret
- repmgr_target_group:"postgres_cluster" - Repmgr fungerar på de värdar som definieras under gruppen "postgres_cluster" som definieras i inventeringsfilen
- repmgr_master:"vm-03" - Host vm-03 kommer att vara PostgreSQL primära instans, vm-01 och vm--02 kommer att replikera från vm-03
Ansible Playbook
I spelboken postgres-play.yaml nedan har jag tilldelat rollen postgresql mot värdgruppen postgres_cluster. Jag har också inkluderat anpassad variabelfil custom-vars.yaml som har konfigurationen för PostgreSQL och repmgr.
$ cat postgres-play.yaml
- hosts: postgres_cluster
become: yes
vars_files:
- ./custom-vars.yaml
roles:
- postgresql
Köra Ansible Playbook
Vi har nu skapat följande Ansible-artefakter och vi är redo att köra Ansible-spelboken.
- roller/postgresql, Ansible rollkatalog.
- custom-vars.yaml, Ansible-variabelfil.
- development.yaml, Ansible inventeringsfil.
- postgres-play.yam, Ansible playbook-fil.
Kör nedan ansible-playbook-kommando från kontrollernoden. Eftersom postgresql-rollen förväntar sig kontrollens sudo-åtkomst, specificerar vi -K-alternativet i kommandot, vilket i sin tur ber oss att ange SUDO-lösenordet för kontrollnoden.
$ ansible-playbook -Ki development.yaml postgres-play.yaml
SUDO password:
PLAY [postgres_cluster] ********************************************************************************************************************************************************************************************************************************************************
TASK [Gathering Facts] *********************************************************************************************************************************************************************************************************************************************************
ok: [vm-01]
ok: [vm-02]
ok: [vm-03]
...
...
PLAY RECAP *********************************************************************************************************************************************************************************************************************************************************************
vm-01 : ok=41 changed=4 unreachable=0 failed=0
vm-02 : ok=41 changed=5 unreachable=0 failed=0
vm-03 : ok=43 changed=5 unreachable=0 failed=0
Kontrollera PLAY RECAP i kommandoutgången och se till att antalet misslyckade är 0.
Kontrollera PostgreSQL-replikering
Med repmgr cluster show-kommandot nedan kan vi kontrollera statusen för PostgreSQL-replikeringsklustret. Den visar rollen, statusen och tidslinjen för alla PostgreSQL-instanser i replikeringsklustret.
$ sudo -u postgres /usr/pgsql-11/bin/repmgr -f /etc/postgresql/11/data/repmgr.conf cluster show
ID | Name | Role | Status | Upstream | Location | Priority | Timeline | Connection string
----+-------+---------+-----------+----------+----------+----------+----------+--------------------------------------------------------
1 | vm-01 | standby | running | vm-03 | default | 100 | 1 | host=vm-01 user=repmgr dbname=repmgr connect_timeout=2
2 | vm-02 | standby | running | vm-03 | default | 100 | 1 | host=vm-02 user=repmgr dbname=repmgr connect_timeout=2
3 | vm-03 | primary | * running | | default | 100 | 1 | host=vm-03 user=repmgr dbname=repmgr connect_timeout=2
Från utgången av kommandot ovan är vm-03 den primära och vm-01, vm02 är standby-instansen som replikerar från uppströmsnoden vm-03. Alla PostgreSQL-instanser är i driftläge.
Kontrollerar pg_stat_replication view på primär vm-03 för att bekräfta att både vm-01 och vm-02 replikerar bra.
$ sudo -iu postgres /usr/pgsql-11/bin/psql -h vm-03 -c 'select * from pg_stat_replication'
Password for user postgres:
pid | usesysid | usename | application_name | client_addr | client_hostname | client_port | backend_start | backend_xmin | state | sent_lsn | write_lsn | flush_lsn | replay_lsn | write_lag | flush_lag | replay_lag | sync_priority | sync_state
------+----------+---------+------------------+---------------+-----------------+-------------+-------------------------------+--------------+-----------+-----------+-----------+-----------+------------+-----------+-----------+------------+---------------+------------
8480 | 16384 | repmgr | vm-02 | 192.168.0.122 | | 59972 | 2019-07-18 09:04:44.315859+00 | | streaming | 0/A000870 | 0/A000870 | 0/A000870 | 0/A000870 | | | | 0 | async
8481 | 16384 | repmgr | vm-01 | 192.168.0.121 | | 35598 | 2019-07-18 09:04:44.336693+00 | | streaming | 0/A000870 | 0/A000870 | 0/A000870 | 0/A000870 | | | | 0 | async
(2 rows)
Lägga till ytterligare en standby-nod till klustret
För att lägga till ytterligare en PostgreSQL-nod till klustret måste vi bara köra Ansible-spelboken igen efter att ha lagt till den specifika värden i inventeringen. I stegen nedan lägger jag till vm-04 till mitt befintliga Repmgr Postgresql-replikeringskluster.
- Lägger till vm-04 i Ansible-inventeringsfilen developmeb
$ cat development.yaml all: children: postgres_cluster: hosts: vm-01: vm-02: vm-03: vm-04: vars: ansible_user: "vagrant"
- Kör Ansible playbook
$ ansible-playbook -Ki development.yaml postgres-play.yaml SUDO password: PLAY [postgres_cluster] ******************************************************************************************************************************************************************************************************************************************************** TASK [Gathering Facts] ********************************************************************************************************************************************************************************************************************************************************* ok: [vm-01] ok: [vm-04] ok: [vm-03] ok: [vm-02] ... ... RUNNING HANDLER [postgresql : restart postgresql] ****************************************************************************************************************************************************************************************************************************** changed: [vm-04] changed: [vm-02] changed: [vm-01] changed: [vm-03] PLAY RECAP ********************************************************************************************************************************************************************************************************************************************************************* vm-01 : ok=41 changed=4 unreachable=0 failed=0 vm-02 : ok=41 changed=5 unreachable=0 failed=0 vm-03 : ok=43 changed=5 unreachable=0 failed=0 vm-04 : ok=46 changed=32 unreachable=0 failed=0
- Kontrollera replikeringskluster
$ sudo -u postgres /usr/pgsql-11/bin/repmgr -f /etc/postgresql/11/data/repmgr.conf cluster show ID | Name | Role | Status | Upstream | Location | Priority | Timeline | Connection string ----+-------+---------+-----------+----------+----------+----------+----------+-------------------------------------------------------- 1 | vm-01 | standby | running | vm-03 | default | 100 | 1 | host=vm-01 user=repmgr dbname=repmgr connect_timeout=2 2 | vm-02 | standby | running | vm-03 | default | 100 | 1 | host=vm-02 user=repmgr dbname=repmgr connect_timeout=2 3 | vm-03 | primary | * running | | default | 100 | 1 | host=vm-03 user=repmgr dbname=repmgr connect_timeout=2 4 | vm-04 | standby | running | vm-03 | default | 100 | 1 | host=vm-04 user=repmgr dbname=repmgr connect_timeout=2
Slutsats
Hittills har vi sett hur vi ställer in Repmgr PostgreSQL-replikeringsklustret med Ansible. När repmgr-klustret har ställts in kan vi använda repmgr-kommandot för att göra annat underhåll på replikeringsklustret som att göra failover och switch-over av den primära noden och ställa in kaskadreplikering. Se repmgr-dokumentationen för mer information.