Перейти к основному содержимому

Уровень 3.0

Предусловия:

  • Изучена лекция 5 «Физическое резервное копирование»

Настройка и использование pg_probackup​

  1. Подключитесь к виртуальной машине посредством webssh, указав ip-адрес Host1.

  2. Проверьте наличие дистрибутива Pangolin в каталоге Distrib домашнего каталога пользователя student:

[student@ServerName ~]$ ls -1 ~/Distrib
license.json
PSQ-\{major-minor\}.0-176766-\{OS\}-distrib.zip
  1. Создайте каталог и перейдите в него для распаковки архива:

    [student@ServerName ~]$ mkdir ~/Distr && cd ~/Distr
  2. Распакуйте монолитный архив с дистрибутивом:

    [student@ServerName Distr]$ unzip ~/Distrib/PSQ-\{major-minor\}.0-176766-\{OS\}-distrib.zip
    Archive: /home/student/Distrib/PSQ-\{major-minor\}.0-176766-\{OS\}-distrib.zip
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-cyclonedx-distrib.json
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-installer-distrib.pom
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-installer-distrib.zip
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-owned-distrib.pom
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-owned-distrib.zip
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-party-distrib.pom
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-party-distrib.zip
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-swidtag-distrib.swidtag
    inflating: PSQ-\{major-minor\}.0-176766-\{OS\}-unpacker-distrib.sh
    inflating: PSQ-doc-\{major-minor\}.0-20-distrib.zip
    inflating: PSQ-doc-\{major-minor\}.0-20.pom
  3. Выполните скрипт распаковки:

    [student@ServerName Distr]$ bash PSQ-\{major-minor\}.0-176766-\{OS\}-unpacker-distrib.sh
    start
    ~/Distr/distributive ~/Distr
    successful completion: PSQ-06.006.00-distrib.tar.gz
    ~/Distr

    В результате выполнения скрипта установочное программное обеспечение перепаковывается в сжатый архив tar.gz с RPM-пакетами.

  4. Распакуйте архив PSQ-06.006.00-distrib.tar.gz и посмотрите список полученных rpm-пакетов:

    [student@ServerName Distr]$ tar xf PSQ-06.006.00-distrib.tar.gz
    [student@ServerName Distr]$ ls -1 *.rpm
    pangolin-backup-tools-1.2.5-\{OS\}.x86_64.rpm
    pangolin-copywala-v1.1.0-hotfix-\{OS\}.x86_64.rpm
    pangolin-core-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-dbms-\{major-minor\}-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-dbms-\{major-minor\}-client-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-dbms-\{major-minor\}-libpq-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-dbms-\{major-minor\}-libpq-dev-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-full-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-manager-2.1.8-\{OS\}.x86_64.rpm
    pangolin-manager-dcs-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-orchestrated-\{major-minor\}.0-\{OS\}.x86_64.rpm
    pangolin-pooler-1.5.2-\{OS\}.x86_64.rpm

    pg_probackup содержится в пакете pangolin-backup-tools-1.2.5-\{OS\}.x86_64.rpm.

    Однако перед его установкой необходимо установить зависимость pangolin-backup-tools-venv.

  5. Перейдите в каталог 3rdparty, распакуйте в нем архив 3rdparty.tar.gz и посмотрите список полученных rpm-пакетов:

    [student@ServerName Distr]$ cd 3rdparty/ && tar xf 3rdparty.tar.gz
    [student@ServerName 3rdparty]$ ls -1 pangolin-backup-tools-venv
    pangolin-backup-tools-venv-1.1.0-\{OS\}.x86_64.rpm
  6. Выполните установку зависимости pangolin-backup-tools-venv-1.1.0-\{OS\}.x86_64.rpm:

    [student@ServerName 3rdparty]$ sudo dnf -y install pangolin-backup-tools-venv/pangolin-backup-tools-venv-1.1.0-\{OS\}.x86_64.rpm
    ...
    Installed:
    pangolin-backup-tools-venv-1.1.0-\{OS\}.x86_64

    Complete!
  7. Перейдите в домашний каталог и выполните установку пакета с pg_probackup:

    [student@ServerName 3rdparty]$ cd ~
    [student@ServerName ~]$ sudo dnf -y install ~/Distr/pangolin-backup-tools-1.2.5-\{OS\}.x86_64.rpm
    ...
    Installed:
    pangolin-backup-tools-1.2.5-\{OS\}.x86_64

    Complete!

Подготовка​

  1. Запустите оболочку от имени пользователя postgres:
[student@ServerName ~]$ sudo -iu postgres
  1. Остановите экземпляр Pangolin, включите подсчет контрольных сумм и запустите экземпляр Pangolin:

    [postgres@ServerName ~]$ pg_ctl stop
    waiting for server to shut down....... done
    server stopped
    [postgres@ServerName ~]$ pg_checksums --enable
    Checksum operation completed
    Files scanned: 1318
    Blocks scanned: 168660
    Files written: 1082
    Blocks written: 168660
    pg_checksums: syncing data directory
    pg_checksums: updating control file
    Checksums enabled in cluster
    [postgres@ServerName ~]$ pg_ctl start -l logfile
    waiting for server to start.... done
    server started

    В производственных системах при инициализации кластера строго рекомендуется включать подсчет контрольных сумм для страниц. Это необходимо для своевременного выявления поврежденных страниц. Также проверка контрольных сумм выполняется pg_probackup при создании копий.

  2. Подключитесь в psql к базе данных postgres от имени пользователя postgres:

    [postgres@ServerName ~]$ psql
    psql (15.5)
    Type "help" for help.
  3. Создайте роль для выполнения резервных копий:

    postgres=# CREATE ROLE backup_role LOGIN REPLICATION;
    CREATE ROLE
  4. Создайте базу данных backup_db:

    postgres=# CREATE DATABASE backup_db OWNER backup_role;
    CREATE DATABASE
  5. Подключитесь к созданной базе данных:

    postgres=# \c backup_db
    You are now connected to database "backup_db" as user "postgres".
  6. Укажите разрешения, необходимые для выполнения резервных копий, для роли backup_role:

    backup_db=# BEGIN;
    GRANT USAGE ON SCHEMA pg_catalog TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.current_setting(text) TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.set_config(text, text, boolean) TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_is_in_recovery() TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_backup_start(text, boolean) TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_backup_stop(boolean) TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_create_restore_point(text) TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_switch_wal() TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_last_wal_replay_lsn() TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.txid_current() TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.txid_current_snapshot() TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.txid_snapshot_xmax(txid_snapshot) TO backup_role;
    GRANT EXECUTE ON FUNCTION pg_catalog.pg_control_checkpoint() TO backup_role;
    COMMIT;
    BEGIN
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    GRANT
    COMMIT

    Из соображений безопасности для выполнения резервных копий рекомендуется использовать отдельную роль, обладающую необходимым для этого набором прав.

  7. Создайте простую таблицу и наполните ее данными:

    backup_db=# CREATE TABLE some_table (value char(100));
    CREATE TABLE
    backup_db=# INSERT INTO some_table (SELECT 'FULL ' || md5(random()::text) || md5(random()::text) FROM generate_series(1,10000000));
    INSERT 0 10000000

Инициализация каталога копий​

  1. Откройте второй терминал в том же хосте и запустите оболочку от имени пользователя postgres:

    [student@ServerName ~]$ sudo -iu postgres

    Далее В этом разделе все действия выполняются во втором терминале.

  2. Добавьте путь к каталогу с pg_probackup в переменную PATH:

    [postgres@ServerName ~]$ export PATH=/opt/pangolin-backup-tools/bin:$PATH
  3. Проинициализируйте каталог резервных копий:

    [postgres@ServerName ~]$ pg_probackup init -B ~/pangolin_backups
    INFO: Backup catalog '/home/postgres/pangolin_backups' successfully inited

    Вспомним, что создание хранилища резервных копий в pg_probackup начинается с инициализации каталога копий с использованием команды init.

    Пользователь, запускающий pg_probackup, должен быть владельцем каталога копий, а также обладать правами на чтение каталога данных кластера баз данных.

    В данной лабораторной работе pg_probackup будет запускаться от имени пользователя postgres, поэтому дополнительных действий по предоставлению прав не требуется.

  4. Зарегистрируйте экземпляр сервера в созданном каталоге копий:

    [postgres@ServerName ~]$ pg_probackup add-instance -B ~/pangolin_backups -D /pgdata/{major-minor}.0/data/ --instance=pangolin_6_6
    INFO: Instance 'pangolin_6_6' successfully inited

    Вспомним, что регистрация экземпляра выполняется командой add-instance.

    Экземпляру присваивается имя с использованием ключа --instance.

  5. Посмотрите содержимое каталога копий:

    [postgres@ServerName ~]$ ls -R -1 pangolin_backups
    pangolin_backups:
    backups
    wal

    pangolin_backups/backups:
    pangolin_6_6

    pangolin_backups/backups/pangolin_6_6:
    pg_probackup.conf

    pangolin_backups/wal:
    pangolin_6_6

    pangolin_backups/wal/pangolin_6_6:

    В каталоге копий имеется два подкаталога:

    • backups — для резервных копий
    • wal — для архива wal

    В указанных каталогах созданы подкаталоги, названные заданным именем экземпляра (pangolin_6_6). Помимо этого, создан конфигурационный файл pg_probackup.conf для зарегистрированного экземпляра.

  6. Посмотрите значения конфигурационных параметров для зарегистрированного экземпляра:

    [postgres@ServerName ~]$ pg_probackup show-config -B ~/pangolin_backups --instance=pangolin_6_6
    # Backup instance information
    pgdata = /pgdata/\{major-minor\}.0/data
    system-identifier = 7561519366850455694
    xlog-seg-size = 16777216
    sync-timeout = 0
    # Connection parameters
    pgdatabase = postgres
    # Replica parameters
    replica-timeout = 5min
    # Archive parameters
    archive-timeout = 5min
    # Logging parameters
    log-level-console = INFO
    log-level-file = OFF
    log-format-console = PLAIN
    log-format-file = PLAIN
    log-filename = pg_probackup.log
    log-rotation-size = 0TB
    log-rotation-age = 0d
    # Retention parameters
    retention-redundancy = 0
    retention-window = 0
    wal-depth = 0
    # Compression parameters
    compress-algorithm = none
    compress-level = 1
    # Remote access parameters
    remote-proto = ssh

    Экземпляру утилитой pg_probackup был присвоен идентификатор (system-identifier).

    Также обратите внимание на параметры в разделах "# Connection parameters", "# Retention parameters" и "# Compression parameters".

    Некоторые параметры из указанных разделов будут задействованы в рамках данной лабораторной работы.

  7. Задайте параметры подключения и проверьте их значения:

    [postgres@ServerName ~]$ pg_probackup set-config -B ~/pangolin_backups --instance=pangolin_6_6 -d backup_db -U backup_role -h localhost
    [postgres@ServerName ~]$ pg_probackup show-config -B ~/pangolin_backups --instance=pangolin_6_6 | grep -A3 '# Connection parameters'
    # Connection parameters
    pgdatabase = backup_db
    pghost = localhost
    pguser = backup_role

    Вспомним, что значения параметров в конфигурационном файле могут быть заданы командой set-config, а получены командой show-config.

    В этом случае указано имя роли и базы данных, посредством которых будет осуществляться подключение к экземпляру Pangolin. Помимо этого, в качестве хоста указано значение localhost.

  8. Задайте параметры политики хранения резервных копий:

    [postgres@ServerName ~]$ pg_probackup set-config -B ~/pangolin_backups --instance=pangolin_6_6 -d backup_db --retention-redundancy=1 --wal-depth=3
    [postgres@ServerName ~]$ pg_probackup show-config -B ~/pangolin_backups --instance=pangolin_6_6 | grep -A3 '# Retention parameters'
    # Retention parameters
    retention-redundancy = 1
    retention-window = 0
    wal-depth = 3

    В этом случае политика хранения подразумевает хранение одной полной резервной копии (retention-redundancy = 1) и соответствующих ей инкрементальных копий. При этом время, за которое гарантировано восстановление данных, не задано (retention-window = 0).

    Также задано количество копий, для которых необходимо хранить сегменты WAL в архиве для возможности восстановление на момент времени (wal-depth = 3).

Создание полной копии​

В этом разделе все действия выполняются во втором терминале.

  1. Создайте полную резервную копию:

    [postgres@ServerName ~]$ pg_probackup backup -b FULL -B ~/pangolin_backups --instance=pangolin_6_6 --stream --temp-slot
    INFO: Backup start, pg_probackup version: 2.5.11, instance: pangolin_6_6, backup ID: T4UUK8, backup mode: FULL, wal mode: STREAM, remote: false, compress-algorithm: none, compress-level: 1
    INFO: This PostgreSQL instance was initialized with data block checksums. Data block corruption will be detected
    INFO: Database backup start
    INFO: wait for pg_backup_start()
    INFO: Wait for WAL segment /home/postgres/pangolin_backups/backups/pangolin_major.minor/T4UUK8/database/pg_wal/000000010000000500000093 to be streamed
    INFO: PGDATA size: 1320MB
    INFO: Current Start LSN: 5/93000028, TLI: 1
    INFO: Start transferring data files
    INFO: Data files are transferred, time elapsed: 6s
    INFO: wait for pg_stop_backup()
    INFO: pg_stop backup() successfully executed
    INFO: stop_lsn: 5/9300B9B8
    INFO: Getting the Recovery Time from WAL
    INFO: Syncing backup files to disk
    INFO: Backup files are synced, time elapsed: 0
    INFO: Validating backup T4UUK8
    INFO: Backup T4UUK8 data files are valid
    INFO: Backup T4UUK8 resident size: 1337MB
    INFO: Backup T4UUK8 completed

    Вспомним, что полная копия создается командой backup с ключом -b FULL.

    В этом случае полная копия создана в режиме получения журнальных записей через протокол репликации (--stream) с использованием слота репликации (--temp-slot).

  2. Посмотрите список имеющихся резервных копий:

    [postgres@ServerName ~]$ pg_probackup show -B ~/pangolin_backups --instance=pangolin_6_6
    ========================================================================================================================================
    Instance Version ID Recovery Time Mode WAL Mode TLI Time Data WAL Zratio Start LSN Stop LSN Status
    ========================================================================================================================================
    pangolin_6_6 15 T4UUK8 2025-10-28 18:41:04+00 FULL STREAM 1/0 11s 1321MB 16MB 1.00 5/93000028 5/9300B9B8 OK

    Вспомним, что информацию об имеющихся копиях можно получить командой show.

    В выводе команды среди прочего имеется следующая информация для каждой копии:

    • ID — идентификатор копии
    • Recovery Time — самое раннее время, на которое может быть восстановлен кластер из данной копии
    • Mode — режим копирования (полный или один из инкрементальных)
    • WAL Mode — режим доставки журнальных записей (STREAM или ARCHIVE)
    • TLI — номера линий времени сегментов WAL (текущей копии и ее родителя)
    • Time — время, за которое была создана копия
    • Data — размер копии (без архива WAL)
    • Zratio — коэффициент сжатия
    • Start LSN и Stop LSN — LSN записей, соответствующих началу и окончанию копирования

    В этом случае копия занимает немного больше 1 GB. На ее создание потребовалось 11 секунд. Сжатие не применялось.

  3. Создайте еще одну полную резервную копию в два потока со сжатием:

    [postgres@ServerName ~]$ pg_probackup backup -b FULL -j 2 --compress-algorithm=zlib --compress-level=3 -B ~/pangolin_backups --instance=pangolin_6_6 --stream --temp-slot
    INFO: Backup start, pg_probackup version: 2.5.11, instance: pangolin_6_6, backup ID: T4UUNQ, backup mode: FULL, wal mode: STREAM, remote: false, compress-algorithm: zlib, compress-level: 3
    INFO: This PostgreSQL instance was initialized with data block checksums. Data block corruption will be detected
    INFO: Database backup start
    INFO: wait for pg_backup_start()
    INFO: Wait for WAL segment /home/postgres/pangolin_backups/backups/pangolin_major.minor/T4UUNQ/database/pg_wal/000000010000000500000095 to be streamed
    INFO: PGDATA size: 1320MB
    INFO: Current Start LSN: 5/95000028, TLI: 1
    INFO: Start transferring data files
    INFO: Data files are transferred, time elapsed: 17s
    INFO: wait for pg_stop_backup()
    INFO: pg_stop backup() successfully executed
    INFO: stop_lsn: 5/950001E0
    INFO: Getting the Recovery Time from WAL
    INFO: Syncing backup files to disk
    INFO: Backup files are synced, time elapsed: 0
    INFO: Validating backup T4UUNQ
    INFO: Backup T4UUNQ data files are valid
    INFO: Backup T4UUNQ resident size: 490MB
    INFO: Backup T4UUNQ completed

    Для указания количества потоков использован ключ -j. Для указания алгоритма сжатия — --compress-algorithm, степени сжатия (зависит от алгоритма, но обычно от 1 до 9) — --compress-level.

  4. Посмотрите список имеющихся резервных копий:

    [postgres@ServerName ~]$ pg_probackup show -B ~/pangolin_backups --instance=pangolin_6_6
    ========================================================================================================================================
    Instance Version ID Recovery Time Mode WAL Mode TLI Time Data WAL Zratio Start LSN Stop LSN Status
    ========================================================================================================================================
    pangolin_6_6 15 T4UUNQ 2025-10-28 18:43:20+00 FULL STREAM 1/0 20s 474MB 16MB 2.78 5/95000028 5/950001E0 OK
    pangolin_6_6 15 T4UUK8 2025-10-28 18:41:04+00 FULL STREAM 1/0 11s 1321MB 16MB 1.00 5/93000028 5/9300B9B8 OK

    Новая сжатая копия (ID=T4O5IO) почти в три раза меньше по размеру первой полной копии.

    При этом время создания копии увеличилось почти в два раза, несмотря на использование двух потоков. Это связано с выполнением сжатия.

Создание инкрементальной копии PTRACK​

  1. В первом сеансе добавьте библиотеку ptrack в shared_preload_libraries:

    backup_db=# ALTER SYSTEM SET shared_preload_libraries = 'ptrack';
    ALTER SYSTEM

    Вспомним, что для создания инкрементальной копии в режиме PTRACK требуется расширение ptrack, которое должно быть заранее установлено и добавлено в загружаемые разделяемые библиотеки (shared_preload_libraries).

    Происходящие изменения в страницах данных сразу фиксируются в специальной битовой карте.

  2. В первом сеансе выйдите из psql и перезапустите экземпляр Pangolin:

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl restart -l logfile
    waiting for server to shut down.... done
    server stopped
    waiting for server to start.... done
    server started
  3. В первом сеансе подключитесь в psql к базе данных backup_db:

    [postgres@ServerName ~]$ psql -d backup_db
    psql (15.5)
    Type "help" for help.
  4. В первом сеансе создайте расширение ptrack и задайте размер его битовой карты:

    backup_db=# CREATE EXTENSION ptrack;
    CREATE EXTENSION
    backup_db=# ALTER SYSTEM SET ptrack.map_size = '2MB';
    ALTER SYSTEM

    Параметр ptrack.map_size определяет размер битовой карты. Его значение рекомендуется задавать в 1024 раза меньше размера кластера баз данных. Недостаточный размер битовой карты может приводить к ложным срабатываниям при определении страниц, в которых произошли изменения.

    Изменение значения параметра ptrack.map_size требует перезапуска экземпляра.

  5. В первом сеансе выйдите из psql и перезапустите экземпляр Pangolin:

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl restart -l logfile
    waiting for server to shut down.... done
    server stopped
    waiting for server to start.... done
    server started
  6. Во втором сеансе создайте полную резервную копию:

    [postgres@ServerName ~]$ pg_probackup backup -b FULL --delete-expired -B ~/pangolin_backups --instance=pangolin_6_6 --stream --temp-slot
    INFO: Backup start, pg_probackup version: 2.5.11, instance: pangolin_6_6, backup ID: T4UUWQ, backup mode: FULL, wal mode: STREAM, remote: false, compress-algorithm: none, compress-level: 1
    INFO: This PostgreSQL instance was initialized with data block checksums. Data block corruption will be detected
    INFO: Database backup start
    INFO: wait for pg_backup_start()
    INFO: Wait for WAL segment /home/postgres/pangolin_backups/backups/pangolin_major.minor/T4UUWQ/database/pg_wal/000000010000000500000097 to be streamed
    INFO: PGDATA size: 1320MB
    INFO: Current Start LSN: 5/97000028, TLI: 1
    INFO: Start transferring data files
    INFO: Data files are transferred, time elapsed: 7s
    INFO: wait for pg_stop_backup()
    INFO: pg_stop backup() successfully executed
    INFO: stop_lsn: 5/97000198
    INFO: Getting the Recovery Time from WAL
    INFO: Syncing backup files to disk
    INFO: Backup files are synced, time elapsed: 0
    INFO: Validating backup T4UUWQ
    INFO: Backup T4UUWQ data files are valid
    INFO: Backup T4UUWQ resident size: 1337MB
    INFO: Backup T4UUWQ completed
    INFO: Evaluate backups by retention
    INFO: Backup T4UUWQ, mode: FULL, status: OK. Redundancy: 1/1, Time Window: 0d/0d. Active
    INFO: Backup T4UUNQ, mode: FULL, status: OK. Redundancy: 2/1, Time Window: 0d/0d. Expired
    INFO: Backup T4UUK8, mode: FULL, status: OK. Redundancy: 3/1, Time Window: 0d/0d. Expired
    INFO: Delete: T4UUNQ 2025-10-28 18:43:20+00
    INFO: Delete: T4UUK8 2025-10-28 18:41:04+00
    INFO: There are no backups to merge by retention policy
    INFO: Purging finished
    INFO: There is no WAL to purge by retention policy

    На этот раз был использован ключ --delete-expired. Он указывает на необходимость удаления копий, не соответствующих заданной политике хранения.

    В нашем случае должна остаться одна последняя полная копия.

    Также ключ --delete-expired можно использовать в команде непосредственного удаления копий — pg_probackup delete.

  7. В первом сеансе подключитесь в psql к базе данных backup_db и добавьте 1000 строк в таблицу some_table:

    [postgres@ServerName ~]$ psql -d backup_db
    psql (15.5)
    Type "help" for help.
    backup_db=# INSERT INTO some_table (SELECT 'PTRACK ' || md5(random()::text) || md5(random()::text) FROM generate_series(1,1000));
    INSERT 0 1000
  8. Во втором сеансе создайте инкрементальную копию PTRACK:

    [postgres@ServerName ~]$ pg_probackup backup -b PTRACK -B ~/pangolin_backups --instance=pangolin_6_6 --stream --temp-slot
    INFO: Backup start, pg_probackup version: 2.5.11, instance: pangolin_6_6, backup ID: T4UV20, backup mode: PTRACK, wal mode: STREAM, remote: false, compress-algorithm: none, compress-level: 1
    INFO: This PostgreSQL instance was initialized with data block checksums. Data block corruption will be detected
    INFO: Database backup start
    INFO: wait for pg_backup_start()
    INFO: Parent backup: T4UUWQ
    INFO: Wait for WAL segment /home/postgres/pangolin_backups/backups/pangolin_major.minor/T4UV20/database/pg_wal/000000010000000500000099 to be streamed
    INFO: PGDATA size: 1320MB
    INFO: Current Start LSN: 5/99000028, TLI: 1
    INFO: Parent Start LSN: 5/97000028, TLI: 1
    INFO: Extracting pagemap of changed blocks
    INFO: Pagemap successfully extracted, time elapsed: 0 sec
    INFO: Start transferring data files
    INFO: Data files are transferred, time elapsed: 0
    INFO: wait for pg_stop_backup()
    INFO: pg_stop backup() successfully executed
    INFO: stop_lsn: 5/99005F68
    INFO: Getting the Recovery Time from WAL
    INFO: Syncing backup files to disk
    INFO: Backup files are synced, time elapsed: 0
    INFO: Validating backup T4UV20
    INFO: Backup T4UV20 data files are valid
    INFO: Backup T4UV20 resident size: 19MB
    INFO: Backup T4UV20 completed

    Для создания копии PTRACK был использован ключ -b PTRACK.

  9. Во втором сеансе посмотрите список резервных копий:

    [postgres@ServerName ~]$ pg_probackup show -B ~/pangolin_backups --instance=pangolin_6_6
    ==========================================================================================================================================
    Instance Version ID Recovery Time Mode WAL Mode TLI Time Data WAL Zratio Start LSN Stop LSN Status
    ==========================================================================================================================================
    pangolin_6_6 15 T4UV20 2025-10-28 18:51:37+00 PTRACK STREAM 1/1 10s 2720kB 16MB 1.00 5/99000028 5/99005F68 OK
    pangolin_6_6 15 T4UUWQ 2025-10-28 18:48:34+00 FULL STREAM 1/0 10s 1321MB 16MB 1.00 5/97000028 5/97000198 OK

    Инкрементальная копия по сравнению с полной копией имеет совсем небольшой размер, несмотря на отсутствие сжатия.

  10. Во втором сеансе восстановите кластер из последней резервной копии:

    [postgres@ServerName ~]$ pg_probackup restore -D ~/restored -B ~/pangolin_backups --instance=pangolin_6_6
    INFO: Validating parents for backup T4UV20
    INFO: Validating backup T4UUWQ
    INFO: Backup T4UUWQ data files are valid
    INFO: Validating backup T4UV20
    INFO: Backup T4UV20 data files are valid
    INFO: Backup T4UV20 WAL segments are valid
    INFO: Backup T4UV20 is valid.
    INFO: Restoring the database from backup at 2025-10-28 18:51:36+00
    INFO: Start restoring backup files. PGDATA size: 1336MB
    INFO: Backup files are restored. Transfered bytes: 1336MB, time elapsed: 8s
    INFO: Restore incremental ratio (less is better): 100% (1336MB/1336MB)
    INFO: Syncing restored files to disk
    INFO: Restored backup files are synced, time elapsed: 0
    INFO: Restore of backup T4UV20 completed.

    Для восстановления кластера использована команда restore. При этом каталог для восстановления задан ключом -D.

    Без указания идентификатора копии (ключ -i) восстановление выполняется из последней имеющейся копии. При этом, если она является инкрементальной (как в нашем случае), то восстановление происходит последовательно по цепочке, начиная с ее родительской полной копии.

  11. В первом сеансе выйдите из psql и остановите экземпляр Pangolin:

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl stop
    waiting for server to shut down....... done
    server stopped
  12. В первом сеансе запустите экземпляр Pangolin, указав каталог с восстановленным кластером:

    [postgres@ServerName ~]$ pg_ctl start -D /home/postgres/restored -l logfile
    waiting for server to start.... done
    server started
  13. В первом сеансе подключитесь в psql к базе данных backup_db и проверьте содержимое таблицы some_table:

    [postgres@ServerName ~]$ psql -d backup_db
    psql (15.5)
    Type "help" for help.
    backup_db=# SELECT count(*) FROM some_table;
    count
    ----------
    10001000
    (1 row)

    Кластер успешно восстановлен — в таблице имеются строки как из полной копии, так и из инкрементальной.

  14. В первом сеансе выйдите из psql, остановите экземпляр с восстановленным кластером и запустите исходный экземпляр:

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl stop -D /home/postgres/restored
    waiting for server to shut down.... done
    server stopped
    [postgres@ServerName ~]$ pg_ctl start -l logfile
    waiting for server to start.... done
    server started
  15. В первом сеансе удалите каталог с восстановленным кластером:

    [postgres@ServerName ~]$ rm -rf ~/restored

Использование непрерывного архивирования​

  1. В первом сеансе подключитесь в psql к базе данных backup_db и настройте непрерывное архивирование:

    [postgres@ServerName ~]$ psql -d backup_db
    psql (15.5)
    Type "help" for help.
    backup_db=# ALTER SYSTEM SET archive_mode = on;
    ALTER SYSTEM
    backup_db=# ALTER SYSTEM SET archive_command = '/opt/pangolin-backup-tools/bin/pg_probackup archive-push -B /home/postgres/pangolin_backups --instance=pangolin_6_6 --wal-file-path=%p --wal-file-name=%f';
    ALTER SYSTEM

    Вспомним, что для сохранения сегментов WAL в архиве pg_probackup в параметре archive_command необходимо указать команду pg_probackup archive-push.

    Изменение параметра archive_mode требует перезапуска экземпляра.

  2. В первом сеансе выйдите из psql и перезапустите экземпляр Pangolin:

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl restart -l logfile
    waiting for server to shut down.... done
    server stopped
    waiting for server to start.... done
    server started
  3. В первом сеансе подключитесь в psql к базе данных backup_db и переключите используемый сегмент WAL:

    [postgres@ServerName ~]$ psql -d backup_db
    psql (15.5)
    Type "help" for help.
    backup_db=# SELECT pg_switch_wal();
    pg_switch_wal
    ---------------
    5/9A00024A
    (1 row)
  4. Во втором сеансе проверьте наличие сегмента WAL в архиве pg_probackup:

    [postgres@ServerName ~]$ pg_probackup show --archive -B ~/pangolin_backups --instance=pangolin_6_6
    ===============================================================================================================================
    TLI Parent TLI Switchpoint Min Segno Max Segno N segments Size Zratio N backups Status
    ===============================================================================================================================
    1 0 0/0 00000001000000050000009A 00000001000000050000009A 1 16MB 1.00 2 OK

    После смены сегмента WAL была выполнена команда archive_command и предыдущий сегмент был сохранен в архиве WAL.

    Информацию о содержимом архива WAL в pg_probackup можно получить с использование команды show --archive.

    В выводе данной команды каждой строке соответствует набор сегментов WAL одной линии времени (TLI).

    В этом случае для линии времени с номером 1 в архиве хранится только 1 сегмент (N segments).

  5. Во втором сеансе выполните полную резервную копию в режиме архивирования:

    [postgres@ServerName ~]$ pg_probackup backup -b FULL --delete-expired -B ~/pangolin_backups --instance=pangolin_6_6
    INFO: Backup start, pg_probackup version: 2.5.11, instance: pangolin_6_6, backup ID: T4UVB6, backup mode: FULL, wal mode: ARCHIVE, remote: false, compress-algorithm: none, compress-level: 1
    INFO: This PostgreSQL instance was initialized with data block checksums. Data block corruption will be detected
    INFO: Database backup start
    INFO: wait for pg_backup_start()
    INFO: Wait for WAL segment /home/postgres/pangolin_backups/wal/pangolin_major.minor/00000001000000050000009C to be archived
    INFO: PGDATA size: 1320MB
    INFO: Current Start LSN: 5/9C000028, TLI: 1
    INFO: Start transferring data files
    INFO: Data files are transferred, time elapsed: 7s
    INFO: wait for pg_stop_backup()
    INFO: pg_stop backup() successfully executed
    INFO: stop_lsn: 5/9D000100
    INFO: Getting the Recovery Time from WAL
    INFO: Syncing backup files to disk
    INFO: Backup files are synced, time elapsed: 0
    INFO: Validating backup T4UVB6
    INFO: Backup T4UVB6 data files are valid
    INFO: Backup T4UVB6 resident size: 1321MB
    INFO: Backup T4UVB6 completed
    INFO: Evaluate backups by retention
    INFO: Backup T4UVB6, mode: FULL, status: OK. Redundancy: 1/1, Time Window: 0d/0d. Active
    INFO: Backup T4UV20, mode: PTRACK, status: OK. Redundancy: 2/1, Time Window: 0d/0d. Expired
    INFO: Backup T4UUWQ, mode: FULL, status: OK. Redundancy: 2/1, Time Window: 0d/0d. Expired
    INFO: Delete: T4UV20 2025-10-28 18:51:37+00
    INFO: Delete: T4UUWQ 2025-10-28 18:48:34+00
    INFO: There are no backups to merge by retention policy
    INFO: Purging finished
    INFO: There is no WAL to purge by retention policy

    Поскольку настроено непрерывное архивирование, при создании резервной копии указание ключа --stream не потребовалось (хотя и возможно). Все необходимые для восстановления записи WAL будут получены из архива.

  6. Во втором сеансе посмотрите список резервных копий и информацию о сегментах WAL в архиве:

    [postgres@ServerName ~]$ pg_probackup show -B ~/pangolin_backups --instance=pangolin_6_6
    ========================================================================================================================================
    Instance Version ID Recovery Time Mode WAL Mode TLI Time Data WAL Zratio Start LSN Stop LSN Status
    ========================================================================================================================================
    pangolin_6_6 15 T4UVB6 2025-10-28 18:57:14+00 FULL ARCHIVE 1/0 9s 1321MB 16MB 1.00 5/9C000028 5/9D000100 OK
    [postgres@ServerName ~]$ pg_probackup show --archive -B ~/pangolin_backups --instance=pangolin_6_6
    ARCHIVE INSTANCE 'pangolin_6_6'
    ===============================================================================================================================
    TLI Parent TLI Switchpoint Min Segno Max Segno N segments Size Zratio N backups Status
    ===============================================================================================================================
    1 0 0/0 00000001000000050000009A 00000001000000050000009D 4 64MB 1.00 1 OK

    Обратите внимание, что количество сегментов в архиве увеличилось (N segments = 4).

    Дело в том, что при копировании в режиме ARCHIVE утилита pg_probackup принудительно переключает сегменты WAL, чтобы срабатывала команда archive_command и необходимые для восстановления записи WAL оказались в архиве.

  7. В первом сеансе вставьте две строки в таблицу some_table и посмотрите номера транзакций, в которых они были вставлены:

    backup_db=# INSERT INTO some_table VALUES('Строка должна восстановиться');
    INSERT 0 1
    backup_db=# INSERT INTO some_table VALUES('Строка НЕ должна восстановиться');
    INSERT 0 1
    backup_db=# SELECT xmin, value FROM some_table
    WHERE value ~ 'Строка должна восстановиться' OR value ~ 'Строка НЕ должна восстановиться';
    xmin | value
    ------+------------------------------------------------------------------------------------------------------
    884 | Строка должна восстановиться
    885 | Строка НЕ должна восстановиться
    (2 rows)

    Запомните номер транзакции xmin для строки со значением Строка должна восстановиться. Именно к транзакции с данным номером будет дальше выполняться восстановление на момент времени (PITR).

  8. Во втором сеансе создайте инкрементальную копию PAGE:

    [postgres@ServerName ~]$ pg_probackup backup -b PAGE -B ~/pangolin_backups --instance=pangolin_6_6
    INFO: Backup start, pg_probackup version: 2.5.11, instance: pangolin_6_6, backup ID: T4UVFS, backup mode: PAGE, wal mode: ARCHIVE, remote: false, compress-algorithm: none, compress-level: 1
    INFO: This PostgreSQL instance was initialized with data block checksums. Data block corruption will be detected
    INFO: Database backup start
    INFO: wait for pg_backup_start()
    INFO: Parent backup: T4UVB6
    INFO: Wait for WAL segment /home/postgres/pangolin_backups/wal/pangolin_major.minor/00000001000000050000009F to be archived
    INFO: PGDATA size: 1320MB
    INFO: Current Start LSN: 5/9F000028, TLI: 1
    INFO: Parent Start LSN: 5/9C000028, TLI: 1
    INFO: Extracting pagemap of changed blocks
    INFO: Pagemap successfully extracted, time elapsed: 0 sec
    INFO: Start transferring data files
    INFO: Data files are transferred, time elapsed: 0
    INFO: wait for pg_stop_backup()
    INFO: pg_stop backup() successfully executed
    INFO: stop_lsn: 5/A00000B8
    INFO: Getting the Recovery Time from WAL
    INFO: Syncing backup files to disk
    INFO: Backup files are synced, time elapsed: 0
    INFO: Validating backup T4UVFS
    INFO: Backup T4UVFS data files are valid
    INFO: Backup T4UVFS resident size: 2336kB
    INFO: Backup T4UVFS completed
  9. Во втором сеансе посмотрите список резервных копий:

    [postgres@ServerName ~]$ pg_probackup show -B ~/pangolin_backups --instance=pangolin_6_6
    ========================================================================================================================================
    Instance Version ID Recovery Time Mode WAL Mode TLI Time Data WAL Zratio Start LSN Stop LSN Status
    ========================================================================================================================================
    pangolin_6_6 15 T4UVFS 2025-10-28 18:59:53+00 PAGE ARCHIVE 1/1 3s 2336kB 16MB 1.00 5/9F000028 5/A00000B8 OK
    pangolin_6_6 15 T4UVB6 2025-10-28 18:57:14+00 FULL ARCHIVE 1/0 9s 1321MB 16MB 1.00 5/9C000028 5/9D000100 OK

    Созданная инкрементальная копия типа PAGE содержит обе вставленные строки.

  10. Во втором сеансе восстановите кластер из копии, указав в качестве цели восстановления номер транзакции, в которой была вставлена строка Строка должна восстановиться:

    [postgres@ServerName ~]$ pg_probackup restore --recovery-target-xid=884 -D ~/restored -B ~/pangolin_backups --instance=pangolin_6_6
    INFO: Validating backup T4UVB6
    INFO: Backup T4UVB6 data files are valid
    INFO: Backup validation completed successfully on time 2025-10-28 18:57:14+00, xid 884 and LSN 5/9D000100
    INFO: Backup T4UVB6 is valid.
    INFO: Restoring the database from backup at 2025-10-28 18:57:06+00
    INFO: Start restoring backup files. PGDATA size: 1320MB
    INFO: Backup files are restored. Transfered bytes: 1320MB, time elapsed: 4s
    INFO: Restore incremental ratio (less is better): 100% (1320MB/1320MB)
    INFO: Syncing restored files to disk
    INFO: Restored backup files are synced, time elapsed: 1s
    INFO: Restore of backup T4UVB6 completed.

    Для восстановления на момент времени В этом случае использован ключ --recovery-target-xid, задающий номер транзакции.

    При этом копию для восстановления указывать необязательно — pg_probackup самостоятельно ее определит по цели, до которой необходимо восстановить данные.

  11. В первом сеансе выйдите из psql и остановите экземпляр Pangolin:

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl stop
    waiting for server to shut down....... done
    server stopped
  12. В первом сеансе запустите экземпляр Pangolin, указав каталог с восстановленным кластером:

    [postgres@ServerName ~]$ pg_ctl start -D /home/postgres/restored -l logfile
    waiting for server to start.... done
    server started
  13. В первом сеансе подключитесь в psql к базе данных backup_db и проверьте содержимое таблицы some_table:

    [postgres@ServerName ~]$ psql -d backup_db
    psql (15.5)
    Type "help" for help.
    backup_db=# SELECT xmin, value FROM some_table
    WHERE value ~ 'Строка должна восстановиться' OR value ~ 'Строка НЕ должна восстановиться';
    xmin | value
    ------+------------------------------------------------------------------------------------------------------
    884 | Строка должна восстановиться
    (1 row)

    Восстановилась только первая строка. Вторая строка, созданная более поздней транзакцией, не восстановилась.

  14. В первом сеансе попробуйте вставить строку в таблицу some_table:

    backup_db=# INSERT INTO some_table VALUES('Строка после восстановления');
    ERROR: cannot execute INSERT in a read-only transaction

    Однако изменение данных в кластере невозможно.

    Дело в том, что восстановление на момент времени выполняется в управляемом режиме.

    Процедура восстановления В этом случае приостанавливается. Администратор должен определить, корректно ли была выбрана цель восстановления. Для этого ему доступно выполнение запросов, но не недоступно изменение данных.

    После проверки корректности администратор должен явно завершить восстановление с использованием функции pg_wal_replay_resume.

    Проверка состояния восстановления WAL выполняется функцией pg_is_wal_replay_paused.

  15. В первом сеансе проверьте состояние восстановления WAL:

    backup_db=# SELECT pg_is_wal_replay_paused();
    pg_is_wal_replay_paused
    -------------------------
    t
    (1 row)
  16. В первом сеансе завершите восстановление и проверьте возможность внесения изменений в таблицу:

    backup_db=# SELECT pg_wal_replay_resume();
    pg_wal_replay_resume
    ----------------------

    (1 row)
    backup_db=# INSERT INTO some_table VALUES('Строка после восстановления');
    INSERT 0 1

    Восстановление завершено. Экземпляр готов принимать запросы как на чтение, так и на запись.

  17. В первом сеансе проверьте текущий номер линии времени:

    backup_db=# SELECT timeline_id FROM pg_control_checkpoint();
    timeline_id
    -------------
    2
    (1 row)

    Линия времени после восстановления увеличилась на 1. Теперь все новые сегменты WAL будут иметь линию времени, равную 2. Это необходимо для исключения пересечения сегментов WAL в архиве.

Завершение​

В этом разделе все действия выполняются в первом сеансе.

  1. Выйдите из psql, остановите экземпляр и удалите каталог с восстановленным кластером.

    backup_db=# \q
    [postgres@ServerName ~]$ pg_ctl stop -D /home/postgres/restored
    waiting for server to shut down.... done
    server stopped
    [postgres@ServerName ~]$ rm -rf /home/postgres/restored
  2. Запустите экземпляр с исходным кластером и подключитесь в psql к базе данных postgres:

    [postgres@ServerName ~]$ pg_ctl start -l logfile
    waiting for server to start.... done
    server started
    [postgres@ServerName ~]$ psql
    psql (15.5)
    Type "help" for help.
  3. Удалите базу данных backup_db и роль backup_role, сбросьте все конфигурационные параметры и выйдите из psql:

    postgres=# DROP DATABASE backup_db;
    DROP DATABASE
    postgres=# DROP ROLE backup_role;
    DROP ROLE
    postgres=# ALTER SYSTEM RESET ALL;
    ALTER SYSTEM
    postgres=# \q
  4. Перезапустите экземпляр:

    [postgres@ServerName ~]$ pg_ctl restart -l logfile
    waiting for server to shut down.... done
    server stopped
    waiting for server to start.... done
    server started
  5. Удалите каталог копий:

    [postgres@ServerName ~]$ rm -rf ~/pangolin_backups/

Самопроверка​

Вопрос 1

В конфигурационном файле pg_probackup.conf заданы следующие настройки политики хранения:

# Retention parameters
retention-redundancy = 2
retention-window = 7
wal-depth = 3

Какое количество копий может быть использовано для восстановления на момент времени, в соответствии с заданной политикой хранения?

Вопрос 2

Резервная копия создана с использованием следующей команды:

[postgres@pangolin-prac-3zu3jq ~]$ pg_probackup backup -b FULL -B /pangolin_backups --instance=pangolin_6_6 --stream

В какой каталог были сохранены сегменты WAL, необходимые для восстановления согласованности данных, при условии, что созданной копии был присвоен идентификатор "T4QMCY"?

Вопрос 3

В оболочке bash выполнена следующая последовательность команд:

[postgres@pangolin-prac-3zu3jq ~]$ pg_probackup show-config -B /pangolin_backups --instance=pangolin_6_6 | grep -A3 '# Retention parameters'
# Retention parameters
retention-redundancy = 2
retention-window = 0
wal-depth = 0

[postgres@pangolin-prac-3zu3jq ~]$ pg_probackup show -B /pangolin_backups --instance=pangolin_6_6
=========================================================================================================================================
Instance      Version  ID      Recovery Time           Mode   WAL Mode  TLI  Time    Data   WAL  Zratio  Start LSN   Stop LSN    Status
=========================================================================================================================================
pangolin_6_6  15       T4QQP4  2025-10-26 13:27:10+00  FULL   STREAM    1/0   11s  1321MB  16MB    1.00  4/E1000028  4/E10001E0  OK
pangolin_6_6  15       T4QQO5  2025-10-26 13:26:35+00  DELTA  STREAM    1/1   10s   136kB  16MB    1.00  4/DF000028  4/DF000198  OK
pangolin_6_6  15       T4QQNE  2025-10-26 13:26:09+00  FULL   STREAM    1/0   11s  1321MB  16MB    1.00  4/DD000028  4/DD0001E0  OK
pangolin_6_6  15       T4QQ86  2025-10-26 13:17:00+00  DELTA  STREAM    1/1    9s   168kB  32MB    1.00  4/DB000028  4/DB000198  OK
pangolin_6_6  15       T4QMCY  2025-10-26 11:53:29+00  FULL   STREAM    1/0   10s  1321MB  16MB    1.00  4/D9000028  4/D9007D20  OK

[postgres@pangolin-prac-3zu3jq ~]$ pg_probackup delete --delete-expired -B /pangolin_backups --instance=pangolin_6_6

Копии с какими идентификаторами будут удалены в результате выполнения последней команды?

Вопрос 4

Восстановление из резервной копии выполняется с использованием следующей команды:

[postgres@pangolin-prac-3zu3jq ~]$ pg_probackup restore -i T4OTFW --recovery-target-xid=1050 -D /restored -B /pangolin_backups --instance=pangolin_6_6

Какие условия необходимы для возможности восстановления с использованием указанной команды?