I den forrige del vovede jeg at lege med en ikke implementeret funktion, der fantaserede om, hvordan den ville fungere. Nå, HA i første omgang er et spørgsmål om design og først derefter implementering. Det undskylder ikke dårlig implementering, det får heller ikke naivt design til at se smart ud. Men efter at du har dækket alle mulige scenarier og fundet en passende bedste regel for de fleste tilfælde, kan nogle gange en meget primitiv lille ændring ødelægge højborgen. Nedenfor vil jeg sandboxe.
Hvad sker der, når pgpool skulle failover, men ikke kan?
Når sundhedstjekket mislykkes for masteren, udløses failover_kommandoen for at degenerere alle eller forfremme næste slave til primær. Lyder solidt. Hvad hvis det fejler sig selv, f.eks. ssh-forbindelsen fejler (f.eks. fordi anden - dårlig admin fjern nøgle fra ~/.ssh/authorized_keys). Hvad har vi?
Så snart health_check_timeout (standard 20) er ude (også påvirket af forsinkelse af genforsøg, maks. trækker sig tilbage og så videre), bliver noden død, så:
t=# select nid,port,st from dblink('host=localhost port=5433','show pool_nodes') as t (nid int,hostname text,port int,st text,lb_weight float,role text,cnt int,cur_node text,del int);
nid | port | st
-----+------+------
0 | 5400 | down
1 | 5401 | up
2 | 5402 | up
(3 rows)
Så der var ingen genforsøg tilbage, og failoveren mislykkedes. Den første mulighed er naturligvis at udføre failover manuelt. Men hvis failover mislykkedes på grund af en eller anden dum fejl, er master tilbage på skinnerne, og det eneste problem, du har, er at pgpool tror, at masteren er offline - du ville sikkert gerne lade tingene være, som de plejede at være før ulykken i stedet for - ikke? Det er selvfølgelig ikke nok at flytte master tilbage online. Pgpool har allerede "degenereret" den primære. Bare det at tilføje det som en ny node hjælper heller ikke. Det værste er, at pgpool efter hændelsen ikke vil forsøge at kontrollere, om den gamle master er pg_is_in_recovery() eller ej, og vil derfor aldrig acceptere den som primær. I henhold til fejlsporet skal du "Kassér pgpool_status fil og ikke gendan tidligere status" med pgpool -D kommandoen.
Efter at have kasseret status, opretter vi forbindelse igen for at undgå at se, at serveren lukker forbindelsen uventet og kører:
t=# select nid,port,st,role from dblink('host=localhost port=5433','show pool_nodes') as t (nid int,hostname text,port int,st text,lb_weight float,role text,cnt int,cur_node text,del int);
nid | port | st | role
-----+------+----+---------
0 | 5400 | up | primary
1 | 5401 | up | standby
2 | 5402 | up | standby
(3 rows)
Alle noder er i gang igen, pgpool genkender masteren.
Til sidst vil jeg dække nogle tip og observationer om brug af pgpool:
-
Ændring af backend-indstillinger er lidt vanskelig:værtsnavn, port og bibliotek kræver genindlæsning for at tilføje nye noder, men kræver genstart for at redigere eksisterende. Mens vægt og flag kan ændres ved blot at genindlæse.
-
Forveksle ikke load_balance_node kolonneværdier med konfiguration. Hvis du kun ser én node med sand, er det ikke bare OK - det er ment sådan. Det betyder ikke, at du kun har én node i balancepuljen - det viser bare, hvilken node der er valgt til netop denne session. Nedenfor er forespørgselsresultatet med alle tre noder, der deltager i SELECT-sætningsbalancering, med node-id 2 valgt:
t=# show pool_nodes; node_id | hostname | port | status | lb_weight | role | select_cnt | load_balance_node | replication_delay ---------+-----------+------+--------+-----------+---------+------------+-------------------+------------------- 0 | localhost | 5400 | up | 0.125000 | primary | 61 | false | 0 1 | localhost | 5401 | up | 0.312500 | standby | 8 | false | 0 2 | localhost | 5402 | up | 0.562500 | standby | 11 | true | 0 (3 rows)
-
Du kan kontrollere, hvilken node der blev valgt til belastningsbalancering med show pool_nodes, men du vil gerne kende den til din forespørgsel, ikke "vis"-en, så en sådan kontrol er ikke altid informativ nok. Nå, du kan overvåge, hvilken node du bruger til den aktuelle forespørgsel, med noget som:
t=# select *,current_setting('port') from now(); now | current_setting -------------------------------+----------------- 2018-04-09 13:56:17.501779+01 | 5401 (1 row)
Vigtig! Men ikke:
t=# select now, setting from now() join pg_settings on name='port';
now | setting
-----------------------------+---------
2018-04-09 13:57:17.5229+01 | 5400
(1 row)
Da det ALTID returnerer master's port. Det samme gælder for alle pg_catalog SELECT.
-
Som du har bemærket i tidligere dele, bruger jeg mere kompliceret måde end blot at vise pool_nodes for at liste noder med tilstand. Jeg gør det bevidst for at demonstrere, hvordan du kan gøre resultatet overskueligt. Brug af hvor gør forespørgslen længere, men resultatet overskueligt, og springer alt det over, der distraherer opmærksomheden for vores særlige opgave. Sammenlign:
t=# select nid,port,st,role from dblink('host=localhost port=5433','show pool_nodes') as t (nid int,hostname text,port int,st text,lb_weight float,role text,cnt int,cur_node text,del int);
nid | port | st | role
-----+------+----+---------
0 | 5400 | up | primary
1 | 5401 | up | standby
2 | 5402 | up | standby
Med output fra indledende show pool_nodes...
-
Du kan ikke sammenligne pgbouncer og pgpool. Men hvis du gør det, er det vigtigst at vide, at parsing af forespørgsler i pgpool afhænger af pg-versionen. Så når du opgraderer postgreSQL, skal du også opgradere pgpool, mens en pgbouncer-instans kan have konfiguration til 8,9,10 forskellige klynger i den samme ini-fil.
-
Hvorfor kan jeg ikke kun bruge et failover-script i stedet for pgpool? Du kan. Men pgpool tilbyder det SAMMEN med memcached og forbindelsespooling og balancering og split hjernekontrol og kontrolleres af årtiers brug.
-
Fejlsporingssystem er på plads - værd at besøge det, hvis du arbejder med pgpool:https://www.pgpool.net/mantisbt/my_view_page.php
-
Adskillige tastefejl i dokumentationen, såsom bakance (backend + balance?..), statemnet, tilladt eller mismatch på tværs af version (pool_nodes plejede at være int og nu er enum, men link til gamle værdier i pcp_node-info er der stadig) ødelægger indtrykket på dette vidunderlige produkt. En formular til at sende rapporten om fundet "fejl" i dokumentationen (ligesom "indsend rettelse" på postgres docs) ville dog forbedre den meget.
-
Vigtigt tip: før du stoler på noget trin - tjek det. For eksempel. efter at have promoveret noden kan du ikke repromovere den (her er promovering ikke postgres operation, men snarere registrering af noden som master for pgpool):
[email protected]:~# sudo -u postgres pcp_promote_node -w -h 127.0.0.1 -U vao -n 1 pcp_promote_node -- Command Successful [email protected]:~# sudo -u postgres pcp_promote_node -w -h 127.0.0.1 -U vao -n 1 FATAL: invalid pgpool mode for process recovery request DETAIL: specified node is already primary node, can't promote node id 1
Det lyder logisk og ser godt ud. Men hvis du kører dette mod den forkerte node (f.eks. er node 0 ! pg_is_in_recovery):
[email protected]:~# for i in $(seq 1 3); do pcp_promote_node -w -h 127.0.0.1 -U vao -n 0; echo $?; done
pcp_promote_node -- Command Successful
0
pcp_promote_node -- Command Successful
0
pcp_promote_node -- Command Successful
0
Hvilket er dårligt, fordi du ikke kan repromovere noden og forvente en fejl, men du får afslutningsstatus 0...
Download Whitepaper Today PostgreSQL Management &Automation med ClusterControlFå flere oplysninger om, hvad du skal vide for at implementere, overvåge, administrere og skalere PostgreSQLDownload WhitepaperVigtigt tip:Spil ikke for meget. Spil aldrig på prod!
Da jeg legede med recovery_1st_stage_command ved hjælp af pg_rewind, tænkte jeg af nysgerrighed at prøve et andet abehack - forespørge pgpool_recovery() uden argumenter (som jeg alligevel ignorerer dem i min opsætning) og så bare prøve at vedhæfte noden til pgpool:
[email protected]:~# psql -p 5433 -h localhost template1 -c "SELECT pgpool_recovery('or_1st.sh', '', '', '')"
pgpool_recovery
-----------------
t
(1 row)
[email protected]:~# pcp_attach_node -h 127.0.0.1 -U vao -w -n 1
pcp_attach_node -- Command Successful
Denne dumme idé bragte mig til:
[email protected]:~# ps -aef | grep pgpool
postgres 15227 1 0 11:22 ? 00:00:00 pgpool -D
postgres 15240 15227 0 11:22 ? 00:00:00 pgpool: health check process(0)
postgres 15241 15227 0 11:22 ? 00:00:00 pgpool: health check process(1)
postgres 15242 15227 0 11:22 ? 00:00:00 pgpool: health check process(2)
postgres 15648 15227 0 11:24 ? 00:00:00 [pgpool] <defunct>
postgres 16264 15227 0 11:26 ? 00:00:00 pgpool: PCP: wait for connection request
postgres 16266 15227 0 11:26 ? 00:00:00 [pgpool] <defunct>
postgres 16506 16264 0 11:26 ? 00:00:00 pgpool: PCP: processing recovery request
postgres 16560 15227 0 11:26 ? 00:00:00 [pgpool] <defunct>
postgres 16835 15227 0 11:26 ? 00:00:00 [pgpool] <defunct>
postgres 16836 15227 0 11:26 ? 00:00:00 [pgpool] <defunct>
Ingen flugt, jeg skal:
[email protected]:~# kill -9
[email protected]:~# rm /var/run/pgpoolql/.s.PGSQL.5433
[email protected]:~# rm /var/run/pgpoolql/.s.PGSQL.9898
Over 5433 er pgpool port og 9898 er pcp port. Efter nedbrud bliver filer naturligvis ikke fejet, så du skal gøre det manuelt.
- Læs omhyggeligt og spil en masse, før du tager pgpool til produktion. Det er meget sværere at finde hjælp til pgpool end postgres selv. Nogle spørgsmål bliver aldrig besvaret. Især når der blev spurgt på det forkerte sted (jeg svarede det ud fra det rigtige sted for at få svaret)...
- Glem ikke den seneste tidslinje for kaskadereplikering (ikke rigtig pgpool-tip, men ofte forstår folk ikke, at det ikke er nok at angive et rigtigt slutpunkt for modtageren for at hente en ny master).
- Arkitektur med diagram kan findes her.
Konklusion
I løbet af 10 år dukkede nye lovende funktioner (watchdog og virtuel ip) og vigtige rettelser (f.eks. serialize_accept) op, men generelt efterlader det et undervurderet indtryk. Docs har stavefejl, der har boet der i 10 år. Jeg tror ikke, der er nogen, der læser dokumenterne. Jeg tror ikke, ingen lagde mærke til det. Du kan bare ikke rapportere dem på nogen nem måde. Der er masser af våben ladt og forberedt, liggende på dokumentationsstedet, som nybegynderen kan tage, pege mod foden og trykke på aftrækkeren. Jeg har ingen rimelig idé om, hvordan jeg kan forbedre det - jeg advarer bare skytterne. Fejlfortolkning af én parameter kan kaste dig i en desperat position med omvendt konstruktion for at finde din fejl. Alle disse år plejede pgpool at være og forbliver et slags produkt for avancerede brugere. Når jeg læste dokumentation, kunne jeg ikke lade være med at huske den gamle russiske joke om Sherlock Holmes:Sherlock og Watson flyver på ballonen. Pludselig blæser den stærke vind dem tusindvis af kilometer væk. Da de kan lande, ser de pigen, der græsser får. Holmes spørger pigen:"Kære, hvor er vi?" og pigen svarer "Du er på ballonen!". Sherlock takker, og mens de letter siger "Vinden tog os meget langt - vi er i Rusland". "Men hvordan ved du det?" spørger Watson. "Det er indlysende - kun i Rusland græsser koderne får" svarer Sherlock. "Men hvordan ved du, at pigen er koder?" - "Det er indlysende - hun gav os et helt præcist og totalt ubrugeligt svar".