PostgreSQL உடன் பேரிடர் மீட்புக்காக சோம்பேறி பிரதியை எவ்வாறு பயன்படுத்தினோம்

PostgreSQL உடன் பேரிடர் மீட்புக்காக சோம்பேறி பிரதியை எவ்வாறு பயன்படுத்தினோம்
பிரதி என்பது காப்புப்பிரதி அல்ல. அல்லது இல்லை? தற்செயலாக நீக்கப்பட்ட ஷார்ட்கட்களை மீட்டெடுக்க, ஒத்திவைக்கப்பட்ட நகலெடுப்பை நாங்கள் எவ்வாறு பயன்படுத்தினோம் என்பது இங்கே உள்ளது.

உள்கட்டமைப்பு நிபுணர்கள் GitLab பணிக்கு பொறுப்பு GitLab.com - இயற்கையில் மிகப்பெரிய GitLab நிகழ்வு. 3 மில்லியன் பயனர்கள் மற்றும் ஏறக்குறைய 7 மில்லியன் திட்டங்களுடன், இது ஒரு பிரத்யேக கட்டிடக்கலை கொண்ட மிகப்பெரிய திறந்த மூல SaaS தளங்களில் ஒன்றாகும். PostgreSQL தரவுத்தள அமைப்பு இல்லாமல், GitLab.com உள்கட்டமைப்பு வெகுதூரம் செல்லாது, மேலும் தரவு இழக்கப்படும்போது ஏதேனும் தோல்விகள் ஏற்பட்டால் தவறு சகிப்புத்தன்மையை உறுதிப்படுத்த நாங்கள் என்ன செய்கிறோம். இது போன்ற ஒரு பேரழிவு நிகழ வாய்ப்பில்லை, ஆனால் நாங்கள் நன்கு தயார் நிலையில் உள்ளோம் மற்றும் பல்வேறு காப்பு மற்றும் நகலெடுக்கும் வழிமுறைகளுடன் இருப்போம்.

நகலெடுப்பது தரவுத்தளங்களை காப்புப் பிரதி எடுப்பதற்கான ஒரு வழிமுறை அல்ல (கீழே பார்) ஆனால் சோம்பேறி நகலெடுப்பைப் பயன்படுத்தி தற்செயலாக நீக்கப்பட்ட தரவை எவ்வாறு விரைவாக மீட்டெடுப்பது என்பதை இப்போது பார்ப்போம் GitLab.com பயனர் குறுக்குவழியை நீக்கியது திட்டத்திற்காக gitlab-ce மற்றும் இணைப்பு கோரிக்கைகள் மற்றும் பணிகளுடன் இணைப்புகளை இழந்தது.

ஒத்திவைக்கப்பட்ட பிரதி மூலம், நாங்கள் 1,5 மணிநேரத்தில் தரவை மீட்டெடுத்தோம். எப்படி நடந்தது என்று பாருங்கள்.

PostgreSQL உடன் நேரத்தை மீட்டெடுப்பதைக் குறிக்கவும்

PostgreSQL ஒரு உள்ளமைக்கப்பட்ட செயல்பாட்டைக் கொண்டுள்ளது, இது ஒரு தரவுத்தளத்தின் நிலையை ஒரு குறிப்பிட்ட நேரத்திற்கு மீட்டமைக்கிறது. அது அழைக்கபடுகிறது பாயிண்ட்-இன்-டைம் மீட்பு (PITR) மற்றும் நகலைப் புதுப்பித்த நிலையில் வைத்திருக்கும் அதே வழிமுறைகளைப் பயன்படுத்துகிறது: முழு தரவுத்தள கிளஸ்டரின் (அடிப்படை காப்புப்பிரதி) நம்பகமான ஸ்னாப்ஷாட்டில் தொடங்கி, ஒரு குறிப்பிட்ட கால கட்டத்தில் தொடர்ச்சியான நிலை மாற்றங்களைப் பயன்படுத்துகிறோம்.

குளிர் காப்புப்பிரதிக்கு இந்த அம்சத்தைப் பயன்படுத்த, நாங்கள் வழக்கமாக ஒரு அடிப்படை தரவுத்தள காப்புப்பிரதியை உருவாக்கி அதை ஒரு காப்பகத்தில் சேமித்து வைக்கிறோம் (GitLab archives live in கூகுள் கிளவுட் ஸ்டோரேஜ்) ரைட்-அஹெட் பதிவை காப்பகப்படுத்துவதன் மூலம் தரவுத்தளத்தின் நிலையில் ஏற்படும் மாற்றங்களையும் நாங்கள் கண்காணிக்கிறோம் (எழுத முன் பதிவு, WAL). இவை அனைத்தையும் கொண்டு, பேரழிவு மீட்புக்கான PITR ஐ நாம் செய்யலாம்: தோல்விக்கு முன் எடுக்கப்பட்ட ஸ்னாப்ஷாட்டில் தொடங்கி, WAL காப்பகத்திலிருந்து தோல்வி வரை மாற்றங்களைப் பயன்படுத்துதல்.

ஒத்திவைக்கப்பட்ட பிரதி என்றால் என்ன?

சோம்பேறி பிரதி என்பது WAL இலிருந்து மாற்றங்களை தாமதத்துடன் பயன்படுத்துவதாகும். அதாவது, ஒரு மணி நேரத்தில் பரிவர்த்தனை நடந்தது X, ஆனால் அது தாமதத்துடன் பிரதியில் தோன்றும் d ஒரு மணி நேரத்தில் X + d.

PostgreSQL ஆனது இயற்பியல் தரவுத்தளப் பிரதியை அமைக்க 2 வழிகளைக் கொண்டுள்ளது: காப்புப் பிரதி மீட்பு மற்றும் ஸ்ட்ரீமிங் பிரதியீடு. காப்பகத்திலிருந்து மீட்டமைக்கிறது, அடிப்படையில் PITR போன்று செயல்படுகிறது, ஆனால் தொடர்ந்து: WAL காப்பகத்திலிருந்து மாற்றங்களை நாங்கள் தொடர்ந்து மீட்டெடுத்து, அவற்றைப் பிரதியில் பயன்படுத்துகிறோம். ஏ ஸ்ட்ரீமிங் பிரதி அப்ஸ்ட்ரீம் தரவுத்தள ஹோஸ்டிலிருந்து WAL ஸ்ட்ரீமை நேரடியாக மீட்டெடுக்கிறது. காப்பக மீட்டெடுப்பை நாங்கள் விரும்புகிறோம் - அதை நிர்வகிப்பது எளிதானது மற்றும் உற்பத்தி கிளஸ்டருடன் தொடர்ந்து செயல்படும் இயல்பான செயல்திறன் உள்ளது.

காப்பகத்திலிருந்து தாமதமான மீட்டெடுப்பை எவ்வாறு அமைப்பது

மீட்பு விருப்பங்கள் கோப்பில் விவரிக்கப்பட்டுள்ளது recovery.conf. ஒரு எடுத்துக்காட்டு:

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'

இந்த அளவுருக்கள் மூலம், காப்புப் பிரதி மீட்டெடுப்புடன் ஒத்திவைக்கப்பட்ட பிரதியை உள்ளமைத்தோம். இங்கே அது பயன்படுத்தப்படுகிறது வால்-இ WAL பிரிவுகளைப் பிரித்தெடுக்க (restore_command) காப்பகத்திலிருந்து, மற்றும் மாற்றங்கள் எட்டு மணிநேரத்திற்குப் பிறகு பயன்படுத்தப்படும் (recovery_min_apply_delay) காப்பகத்தில் உள்ள காலவரிசை மாற்றங்களை பிரதி கண்காணிக்கும், எடுத்துக்காட்டாக, கிளஸ்டர் தோல்வியின் காரணமாக (recovery_target_timeline).

С recovery_min_apply_delay நீங்கள் தாமதத்துடன் ஸ்ட்ரீமிங் நகலெடுப்பை அமைக்கலாம், ஆனால் ரெப்ளிகேஷன் ஸ்லாட்டுகள், சூடான காத்திருப்பு கருத்து மற்றும் பலவற்றுடன் தொடர்புடைய இரண்டு ஆபத்துகள் இங்கே உள்ளன. அவற்றைத் தவிர்க்க WAL காப்பகம் உங்களை அனுமதிக்கிறது.

அளவுரு recovery_min_apply_delay PostgreSQL 9.3 இல் மட்டுமே தோன்றியது. முந்தைய பதிப்புகளில், ஒத்திவைக்கப்பட்ட நகலெடுப்பிற்கு நீங்கள் கலவையை உள்ளமைக்க வேண்டும் மீட்பு மேலாண்மை செயல்பாடுகள் (pg_xlog_replay_pause(), pg_xlog_replay_resume()) அல்லது தாமதத்தின் காலத்திற்கு WAL பிரிவுகளை காப்பகத்தில் வைத்திருங்கள்.

PostgreSQL இதை எப்படிச் செய்கிறது?

PostgreSQL சோம்பேறி மீட்டெடுப்பை எவ்வாறு செயல்படுத்துகிறது என்பதைப் பார்ப்பது சுவாரஸ்யமானது. பார்க்கலாம் recoveryApplyDelay(XlogReaderState). இருந்து அழைக்கப்படுகிறது முக்கிய மீண்டும் வளையம் WAL இலிருந்து ஒவ்வொரு நுழைவுக்கும்.

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, &microsecs);
    if (secs <= 0 && microsecs <= 0)
        return false;

    while (true)
    {
        // Shortened:
        // Use WaitLatch until we reached recoveryDelayUntilTime
        // and then
        break;
    }
    return true;
}

முக்கிய விஷயம் என்னவென்றால், பரிவர்த்தனை கமிட் நேர முத்திரையில் பதிவுசெய்யப்பட்ட நேரத்தின் அடிப்படையில் தாமதம் ஏற்படுகிறது (xtime) நீங்கள் பார்க்கிறபடி, தாமதமானது கமிட்களுக்கு மட்டுமே பொருந்தும் மற்றும் பிற உள்ளீடுகளைப் பாதிக்காது - எல்லா மாற்றங்களும் நேரடியாகப் பயன்படுத்தப்படும், மேலும் உறுதி தாமதமாகும், எனவே உள்ளமைக்கப்பட்ட தாமதத்திற்குப் பிறகு மட்டுமே மாற்றங்களைக் காண்போம்.

தரவை மீட்டெடுக்க தாமதமான பிரதியை எவ்வாறு பயன்படுத்துவது

எங்களிடம் ஒரு தரவுத்தள கிளஸ்டர் மற்றும் உற்பத்தியில் எட்டு மணிநேர தாமதத்துடன் ஒரு பிரதி உள்ளது என்று வைத்துக்கொள்வோம். உதாரணத்தைப் பயன்படுத்தி தரவை எவ்வாறு மீட்டெடுப்பது என்று பார்ப்போம் தற்செயலாக குறுக்குவழிகளை நீக்குகிறது.

பிரச்சனை பற்றி அறிந்ததும், நாங்கள் காப்பக மீட்பு இடைநிறுத்தப்பட்டுள்ளது ஒத்திவைக்கப்பட்ட பிரதிக்கு:

SELECT pg_xlog_replay_pause();

ஒரு இடைநிறுத்தத்துடன், பிரதி கோரிக்கையை மீண்டும் செய்யும் அபாயம் இல்லை DELETE. எல்லாவற்றையும் கண்டுபிடிக்க உங்களுக்கு நேரம் தேவைப்பட்டால் ஒரு பயனுள்ள விஷயம்.

விஷயம் என்னவென்றால், ஒத்திவைக்கப்பட்ட பிரதி கோரிக்கைக்கு முந்தைய தருணத்தை அடைய வேண்டும் DELETE. அகற்றுவதற்கான உடல் நேரத்தை நாங்கள் தோராயமாக அறிந்தோம். நாங்கள் நீக்கிவிட்டோம் recovery_min_apply_delay மற்றும் சேர்க்கப்பட்டது recovery_target_time в recovery.conf. இந்த பிரதி தாமதமின்றி சரியான தருணத்தை அடைகிறது:

recovery_target_time = '2018-10-12 09:25:00+00'

நேர முத்திரைகளுடன், தவறவிடாமல் இருக்க அதிகப்படியான அளவைக் குறைப்பது நல்லது. உண்மை, எந்த அளவு குறைகிறதோ, அவ்வளவு டேட்டாவை இழக்கிறோம். மீண்டும், நாங்கள் கோரிக்கையைத் தவறவிட்டால் DELETE, எல்லாம் மீண்டும் நீக்கப்படும், நீங்கள் மீண்டும் தொடங்க வேண்டும் (அல்லது PITR க்கு குளிர் காப்புப்பிரதி எடுக்கவும்).

ஒத்திவைக்கப்பட்ட போஸ்ட்கிரெஸ் நிகழ்வை நாங்கள் மறுதொடக்கம் செய்தோம் மற்றும் குறிப்பிட்ட நேரம் வரை WAL பிரிவுகள் மீண்டும் மீண்டும் செய்யப்பட்டன. நீங்கள் கேட்பதன் மூலம் இந்த கட்டத்தில் முன்னேற்றத்தைக் கண்காணிக்கலாம்:

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;

நேரமுத்திரை மாறவில்லை என்றால், மீட்பு முடிந்தது. செயலை தனிப்பயனாக்கலாம் recovery_target_actionமீண்டும் முயற்சித்த பிறகு நிகழ்வை மூட, விளம்பரப்படுத்த அல்லது இடைநிறுத்த (இயல்புநிலையாக இது இடைநிறுத்தப்படும்).

அந்த துரதிர்ஷ்டவசமான கோரிக்கைக்கு முன் தரவுத்தளம் அதன் நிலைக்குத் திரும்பியது. இப்போது நீங்கள் எடுத்துக்காட்டாக, தரவை ஏற்றுமதி செய்யலாம். நீக்கப்பட்ட லேபிள் தரவையும் சிக்கல்களுக்கான அனைத்து இணைப்புகளையும் ஏற்றுமதி செய்தோம் மற்றும் கோரிக்கைகளை ஒன்றிணைத்து அவற்றை தயாரிப்பு தரவுத்தளத்திற்கு நகர்த்தினோம். இழப்புகள் பெரிய அளவில் இருந்தால், நீங்கள் வெறுமனே பிரதியை விளம்பரப்படுத்தலாம் மற்றும் அதை முதன்மையாகப் பயன்படுத்தலாம். ஆனால் நாம் மீட்டெடுத்த புள்ளிக்குப் பிறகு அனைத்து மாற்றங்களும் இழக்கப்படும்.

நேர முத்திரைகளுக்குப் பதிலாக, பரிவர்த்தனை ஐடிகளைப் பயன்படுத்துவது நல்லது. இந்த ஐடிகளைப் பதிவு செய்வது பயனுள்ளது, எடுத்துக்காட்டாக, டிடிஎல் அறிக்கைகளுக்கு (எ.கா DROP TABLE), பயன்படுத்தி log_statements = 'ddl'. எங்களிடம் பரிவர்த்தனை ஐடி இருந்தால், நாங்கள் எடுப்போம் recovery_target_xid மற்றும் கோரிக்கைக்கு முன் பரிவர்த்தனை வரை அனைத்தையும் இயக்கியது DELETE.

வேலைக்குத் திரும்புவது மிகவும் எளிது: எல்லா மாற்றங்களையும் அகற்றவும் recovery.conf மற்றும் Postgres ஐ மீண்டும் தொடங்கவும். பிரதி விரைவில் மீண்டும் எட்டு மணி நேரம் தாமதமாகும், மேலும் எதிர்கால பிரச்சனைகளுக்கு நாங்கள் தயாராக இருக்கிறோம்.

மீட்பு நன்மைகள்

குளிர்ந்த காப்புப்பிரதிக்குப் பதிலாக ஒத்திவைக்கப்பட்ட பிரதியுடன், காப்பகத்திலிருந்து முழுப் படத்தையும் மீட்டெடுக்க நீங்கள் மணிநேரம் செலவிட வேண்டியதில்லை. எடுத்துக்காட்டாக, முழு அடிப்படை 2 TB காப்புப்பிரதியைப் பெற எங்களுக்கு ஐந்து மணிநேரம் ஆகும். பின்னர் நீங்கள் விரும்பிய நிலைக்கு (மோசமான நிலையில்) மீட்க முழு தினசரி WAL ஐப் பயன்படுத்த வேண்டும்.

இரண்டு வழிகளில் குளிர் காப்புப்பிரதியை விட ஒத்திவைக்கப்பட்ட பிரதி சிறந்தது:

  1. காப்பகத்திலிருந்து முழு அடிப்படை காப்புப்பிரதியையும் அகற்ற வேண்டிய அவசியமில்லை.
  2. WAL பிரிவுகளின் நிலையான எட்டு மணிநேர சாளரம் உள்ளது, அது மீண்டும் மீண்டும் செய்யப்பட வேண்டும்.

WAL இலிருந்து PITR ஐ உருவாக்குவது சாத்தியமா என்பதை நாங்கள் தொடர்ந்து சரிபார்க்கிறோம், மேலும் ஒத்திவைக்கப்பட்ட பிரதியின் பின்னடைவைக் கண்காணிப்பதன் மூலம் WAL காப்பகத்தில் ஊழல் அல்லது பிற சிக்கல்களை விரைவாகக் கவனிப்போம்.

இந்த எடுத்துக்காட்டில், மீட்டமைக்க எங்களுக்கு 50 நிமிடங்கள் ஆனது, அதாவது ஒரு மணி நேரத்திற்கு 110 ஜிபி WAL தரவு வேகம் (காப்பகம் இன்னும் இயக்கத்தில் இருந்தது AWS S3) மொத்தத்தில், சிக்கலைத் தீர்த்து, 1,5 மணிநேரத்தில் தரவை மீட்டெடுத்தோம்.

முடிவுகள்: ஒத்திவைக்கப்பட்ட பிரதி பயனுள்ளதாக இருக்கும் (மற்றும் அது இல்லாத இடத்தில்)

நீங்கள் தற்செயலாக தரவை இழந்து, உள்ளமைக்கப்பட்ட தாமதத்திற்குள் இந்த சிக்கலைக் கவனித்திருந்தால், தாமதமான நகலெடுப்பை முதலுதவியாகப் பயன்படுத்தவும்.

ஆனால் நினைவில் கொள்ளுங்கள்: நகலெடுப்பது காப்புப்பிரதி அல்ல.

காப்புப் பிரதி மற்றும் பிரதி எடுப்பது வெவ்வேறு நோக்கங்களைக் கொண்டுள்ளது. நீங்கள் தற்செயலாக உருவாக்கினால், குளிர் காப்புப்பிரதி கைக்கு வரும் DELETE அல்லது DROP TABLE. நாங்கள் குளிர் சேமிப்பகத்திலிருந்து காப்புப்பிரதியை உருவாக்கி, அட்டவணையின் முந்தைய நிலையை அல்லது முழு தரவுத்தளத்தையும் மீட்டெடுக்கிறோம். ஆனால் அதே நேரத்தில் கோரிக்கை DROP TABLE வேலை செய்யும் கிளஸ்டரில் உள்ள அனைத்து பிரதிகளிலும் கிட்டத்தட்ட உடனடியாக இனப்பெருக்கம் செய்யப்படுகிறது, எனவே சாதாரண பிரதிகள் இங்கு உதவாது. தனித்தனி சேவையகங்கள் வாடகைக்கு விடப்பட்டு, சுமைகளை விநியோகிக்கும் போது, ​​பிரதியமைப்பு தானாகவே தரவுத்தளத்தை வைத்திருக்கும்.

ஒத்திவைக்கப்பட்ட பிரதியுடன் கூட, தரவு மையத்தில் செயலிழப்பு, மறைக்கப்பட்ட சேதம் அல்லது உடனடியாக கவனிக்கப்படாத பிற நிகழ்வுகள் ஏற்பட்டால், சில சமயங்களில் பாதுகாப்பான இடத்தில் குளிர் காப்புப் பிரதி எடுக்க வேண்டும். பிரதியெடுப்பு மட்டும் இங்கு பயன்படாது.

கருத்து. மீது GitLab.com நாங்கள் தற்போது கணினி மட்டத்தில் தரவு இழப்பிற்கு எதிராக மட்டுமே பாதுகாக்கிறோம் மற்றும் பயனர் மட்டத்தில் தரவை மீட்டெடுக்க மாட்டோம்.

ஆதாரம்: www.habr.com

கருத்தைச் சேர்