Ang pagtitiklop ay hindi isang backup. O hindi? Narito kung paano namin ginamit ang lazy replication para sa pagbawi sa pamamagitan ng aksidenteng pagtanggal ng mga shortcut.
Ang pagtitiklop ay hindi ang iyong database backup tool (gitlab-ce
Sa naantalang replica, na-recover namin ang data sa loob lang ng 1,5 oras. Tingnan kung paano ito.
Point-in-time na pagbawi gamit ang PostgreSQL
Ang PostgreSQL ay may built-in na function na nagpapanumbalik ng estado ng isang database sa isang tiyak na punto ng oras. Ito ay tinatawag na
Para magamit ang feature na ito para sa isang malamig na backup, regular kaming gumagawa ng base database backup at iniimbak ito sa isang archive (ang GitLab archive ay nakatira sa
Ano ang delayed replication?
Ang naantalang pagtitiklop ay ang aplikasyon ng mga pagbabago mula sa WAL na may pagkaantala. Ibig sabihin, nangyari ang transaksyon sa oras X
, ngunit lalabas ito sa replica na may pagkaantala d
sa isang oras X + d
.
Mayroong 2 paraan upang mag-set up ng isang pisikal na replika ng database sa PostgreSQL: pagpapanumbalik ng archive at pagtitiklop ng streaming.
Paano i-set up ang naantalang backup recovery
recovery.conf
... Halimbawa:
standby_mode = 'on'
restore_command = '/usr/bin/envdir /etc/wal-e.d/env /opt/wal-e/bin/wal-e wal-fetch -p 4 "%f" "%p"'
recovery_min_apply_delay = '8h'
recovery_target_timeline = 'latest'
Sa mga setting na ito, na-configure namin ang isang naantalang replica na may archive restore. Ginamit dito restore_command
) mula sa archive, at ang mga pagbabago ay ilalapat pagkatapos ng walong oras (recovery_min_apply_delay
). Babantayan ng Replica ang mga pagbabago sa timeline sa archive, gaya ng dahil sa isang cluster failover (recovery_target_timeline
).
Π‘ recovery_min_apply_delay
maaari kang mag-set up ng latency streaming replication, ngunit may ilang mga pitfalls na nauugnay sa mga replication slot, mainit na ekstrang feedback, at iba pa. Iniiwasan sila ng WAL archive.
Parametro recovery_min_apply_delay
lumitaw lamang sa PostgreSQL 9.3. Sa mga nakaraang bersyon, ang naantalang pagtitiklop ay nangangailangan ng kumbinasyon ng pg_xlog_replay_pause(), pg_xlog_replay_resume()
) o hawakan ang mga segment ng WAL sa archive para sa tagal ng pagkaantala.
Paano ito ginagawa ng PostgreSQL?
Nakakatuwang makita kung paano ipinapatupad ng PostgreSQL ang lazy restore. Tignan natin recoveryApplyDelay(XlogReaderState)
static bool
recoveryApplyDelay(XLogReaderState *record)
{
uint8 xact_info;
TimestampTz xtime;
long secs;
int microsecs;
/* nothing to do if no delay configured */
if (recovery_min_apply_delay <= 0)
return false;
/* no delay is applied on a database not yet consistent */
if (!reachedConsistency)
return false;
/*
* Is it a COMMIT record?
*
* We deliberately choose not to delay aborts since they have no effect on
* MVCC. We already allow replay of records that don't have a timestamp,
* so there is already opportunity for issues caused by early conflicts on
* standbys.
*/
if (XLogRecGetRmid(record) != RM_XACT_ID)
return false;
xact_info = XLogRecGetInfo(record) & XLOG_XACT_OPMASK;
if (xact_info != XLOG_XACT_COMMIT &&
xact_info != XLOG_XACT_COMMIT_PREPARED)
return false;
if (!getRecordTimestamp(record, &xtime))
return false;
recoveryDelayUntilTime =
TimestampTzPlusMilliseconds(xtime, recovery_min_apply_delay);
/*
* Exit without arming the latch if it's already past time to apply this
* record
*/
TimestampDifference(GetCurrentTimestamp(), recoveryDelayUntilTime,
&secs, µsecs);
if (secs <= 0 && microsecs <= 0)
return false;
while (true)
{
// Shortened:
// Use WaitLatch until we reached recoveryDelayUntilTime
// and then
break;
}
return true;
}
Ang ilalim na linya ay ang pagkaantala ay batay sa pisikal na oras na naitala sa timestamp ng transaksyon na ginawa (xtime
). Tulad ng nakikita mo, ang pagkaantala ay nalalapat lamang sa mga commit at hindi nakakaapekto sa iba pang mga tala - lahat ng mga pagbabago ay direktang inilalapat, at ang commit ay naantala, kaya makikita lamang namin ang mga pagbabago pagkatapos ng na-configure na pagkaantala.
Paano gamitin ang lazy replica para sa pagbawi ng data
Sabihin nating mayroon tayong database cluster sa produksyon at isang replica na may walong oras na pagkaantala. Tingnan natin kung paano i-recover ang data gamit ang isang halimbawa
Nung namulat tayo sa problema, tayo
SELECT pg_xlog_replay_pause();
Sa isang pag-pause, wala kaming panganib na ulitin ng replica ang kahilingan DELETE
. Kapaki-pakinabang na bagay kung kailangan mo ng oras upang malaman ang lahat.
Ang bottom line ay ang naantalang replica ay dapat umabot sa sandali bago ang kahilingan DELETE
. Tinatayang alam namin ang pisikal na oras ng pag-alis. Tinanggal namin recovery_min_apply_delay
at karagdagan recovery_target_time
Π² recovery.conf
. Kaya't ang replika ay umabot sa tamang sandali nang walang pagkaantala:
recovery_target_time = '2018-10-12 09:25:00+00'
Sa mga timestamp, mas mainam na bawasan ang sobra para hindi makaligtaan. Totoo, mas malaki ang pagbaba, mas maraming data ang nawawala sa amin. Muli, kung laktawan natin ang kahilingan DELETE
, ang lahat ay tatanggalin muli at kailangan mong magsimulang muli (o kahit na kumuha ng malamig na backup para sa PITR).
Sinimulan namin muli ang naantalang instance ng Postgres at ang mga segment ng WAL ay naulit hanggang sa tinukoy na oras. Maaari mong subaybayan ang pag-unlad sa yugtong ito sa pamamagitan ng pagtatanong:
SELECT
-- current location in WAL
pg_last_xlog_replay_location(),
-- current transaction timestamp (state of the replica)
pg_last_xact_replay_timestamp(),
-- current physical time
now(),
-- the amount of time still to be applied until recovery_target_time has been reached
'2018-10-12 09:25:00+00'::timestamptz - pg_last_xact_replay_timestamp() as delay;
Kung hindi na magbabago ang timestamp, kumpleto na ang pag-restore. Maaari mong i-customize ang pagkilos recovery_target_action
Ang database ay dumating sa estado bago ang masamang kahilingan na iyon. Ngayon ay maaari ka na, halimbawa, mag-export ng data. Na-export namin ang data ng remote na label at lahat ng mga link sa mga isyu at mga kahilingan sa pagsasanib at inilipat ang mga ito sa database ng produksyon. Kung malaki ang mga pagkalugi, maaari mo lamang i-promote ang replica at gamitin ito bilang pangunahing isa. Ngunit pagkatapos ay mawawala ang lahat ng pagbabago pagkatapos ng sandali kung saan kami nakabawi.
Mas mainam na gumamit ng mga transaction ID sa halip na mga timestamp. Kapaki-pakinabang na itala ang mga ID na ito, halimbawa, para sa mga pahayag ng DDL (tulad ng DROP TABLE
), sa pamamagitan ng paggamit log_statements = 'ddl'
. Kung mayroon kaming transaction ID, kukunin namin recovery_target_xid
at pinatakbo ang lahat hanggang sa transaksyon bago ang kahilingan DELETE
.
Ang pagbabalik sa trabaho ay napakasimple: alisin ang lahat ng pagbabago mula sa recovery.conf
at i-restart ang mga postgres. Sa lalong madaling panahon ang cue ay magkakaroon muli ng walong oras na pagkaantala, at handa na kami para sa mga problema sa hinaharap.
Mga Benepisyo sa Pagbawi
Sa isang naantalang replica, sa halip na isang malamig na backup, hindi mo kailangang gumastos ng oras sa pagpapanumbalik ng buong snapshot mula sa archive. Halimbawa, kailangan namin ng limang oras para makuha ang buong 2 TB base backup. At pagkatapos ay kailangan mo pa ring ilapat ang buong pang-araw-araw na WAL upang mabawi sa nais na estado (sa pinakamasamang kaso).
Ang isang naantalang replica ay mas mahusay kaysa sa isang malamig na backup sa dalawang paraan:
- Hindi mo kailangang kunin ang buong base backup mula sa archive.
- May nakapirming walong oras na palugit ng mga segment ng WAL na dapat ulitin.
Gayundin, patuloy naming sinusuri kung ang WAL ay maaaring PITRed, at mabilis naming mapapansin ang katiwalian o iba pang mga problema sa WAL archive sa pamamagitan ng pagsubaybay sa backlog ng naantalang replika.
Sa halimbawang ito, tumagal kami ng 50 minuto upang maibalik, ibig sabihin, ang bilis ay 110 GB ng WAL data kada oras (naka-on pa rin ang archive
Buod: kung saan kapaki-pakinabang ang isang naantalang replika (at kung saan hindi)
Gamitin ang naantalang pagtitiklop bilang pangunang lunas kung hindi mo sinasadyang mawalan ng data at mapansin ang sakuna na ito sa loob ng na-configure na pagkaantala.
Ngunit tandaan: ang pagtitiklop ay hindi isang backup.
Ang pag-backup at pagkopya ay may iba't ibang layunin. Magagamit ang isang malamig na backup kung hindi mo sinasadyang ginawa DELETE
o DROP TABLE
. Gumagawa kami ng backup mula sa malamig na imbakan at ibinabalik ang nakaraang estado ng isang talahanayan o isang buong database. Ngunit sa parehong oras ang kahilingan DROP TABLE
halos agad na muling ginawa sa lahat ng mga replika sa gumaganang kumpol, kaya ang regular na pagtitiklop ay hindi magse-save dito. Ang pagkopya mismo ay nagpapanatili ng database na magagamit kapag ang mga indibidwal na server ay naupahan at namamahagi ng load.
Kahit na may naantalang replica, minsan kailangan talaga namin ng malamig na backup sa isang ligtas na lugar, kung biglang may pagkabigo sa data center, nakatagong pinsala, o iba pang mga kaganapan na hindi mo agad napapansin. Dito mula sa isang pagtitiklop ay walang kahulugan.
Nota. Sa
Pinagmulan: www.habr.com