Уровень 2.0
Предусловие:
- Изучен материал лекции 3 «Логическое резервное копирование» курса DBA3
В этом задании:
- Назначение и способы получения записей WAL
- Протокол репликации
- Непрерывное архивирование сегментов WAL
Протокол репликации и архив WAL
Из темы «Администрирование Pangolin. Внутреннее устройство.» вы можете знать, что для обеспечения возможности восстановления данных после сбоя в Pangolin ведется журнал предзаписи (WAL, Write-Ahead Log), в котором фиксируются все изменения страниц данных и статусов транзакций, происходящие в оперативной памяти.
Однако журнал WAL используется не только для восстановления данных после сбоя. Он также применяется при восстановлении из физической резервной копии и в процессе репликации.
Указанные процедуры рассматриваются в лекциях «Физическое резервное копирование», «Физическая репликация» и «Логическая репликация».
Получение журнальных записей для указанных целей возможно с использованием протокола репликации и непрерывного архивирования.
Протокол репликации
Протокол репликации в некотором смысле похож на клиент-серверный протокол, в соответствии с которым осуществляется взаимодействие клиента с экземпляром сервера при выполнении операций с данными.
Протокол репликации также применяется для взаимодействия с экземпляром сервера, но не для выполнения операций с данными, а для получения журнальных записей.
Стоит отметить, что передаются именно журнальные записи (по мере их формирования), а не их содержащие файлы-сегменты.
На экземпляре Pangolin за обслуживание подключения по протоколу репликации отвечает процесс wal sender.
Общее количество одновременно работающих процессов wal sender в экземпляре ограничено значением параметра max_wal_senders (по умолчанию 10).
Протоколом репликации обычно пользуются либо утилиты резервного копирования, либо сам экземпляр сервера, выступающий в роли реплики, для получения WAL-записей от другого экземпляра (мастера) при репликации.

Также стоит отметить утилиту pg_receivewal (см. документацию), с использованием которой может быть организовано накопление сегментов WAL в виде отдельного архива.
Такой архив, в свою очередь, может использоваться как при резервном копировании, так и при репликации.
Стоит отметить, что архив WAL может быть создан и без использования протокола репликации, а именно методом непрерывного архивирования, который будет рассмотрен ниже.
Помимо этого, в экспериментальных целях также имеется возможность подключения к процессу wal sender посредством psql. Пример этого будет рассмотрен в лабораторной работе.
Ограничение на уровень журнала WAL
Для возможности использования протокола репликации необходимо, чтобы конфигурационный параметр wal_level имел значение replica или logical.
Вспомним, что параметр wal_level определяет уровень журнала предзаписи. Чем выше уровень, тем больше информации сохраняется в журнал.
На уровне minimal журналируется минимально достаточная информация для восстановления после сбоя.
В частности, не журналируются операции массовой обработки данных, такие как CREATE INDEX, CREATE TABLE AS SELECT или COPY FROM, поскольку долговечность данных в этом случае гарантируется самими операциями.
Однако протокол репликации используется для других целей, поэтому он требует сохранения в записях WAL полной информации об изменениях в данных, блокировках объектов и активных транзакциях.
Различие уровней журнала replica и logical в том, что на уровне logical также сохраняется информация о смысле совершенных изменений — для возможности ее интерпретации на несовместимой платформе (или другой основной версии Pangolin) при логической репликации.
Стоит отметить, что параметр wal_level по умолчанию имеет значение replica.
Необходимые права доступа
Подключение к экземпляру сервера по протоколу репликации может выполняться либо ролью с атрибутом REPLICATION, либо суперпользователем.
При этом в файле pg_hba.conf должны быть указаны разрешения подключения к виртуальной базе данных replication, например:
# TYPE DATABASE USER ADDRESS METHOD
local all all trust
host all all 127.0.0.1/32 scram-sha-256
host all all ::1/128 scram-sha-256
local replication all trust
host replication all 127.0.0.1/32 scram-sha-256
host replication all ::1/128 scram-sha-256
Необходимо отметить, что использование ключевого слова all в качестве базы данных не предполагает доступ по протоколу репликации. Разрешение для виртуальной базы данных replication должно быть указано отдельно.
Слот репликации
Экземпляр сервера по умолчанию хранит журнальные записи начиная с начала последней завершенной контрольной точки, выполненной процессом checkpointer.
Указанные записи необходимы для восстановления после сбоя. Предшествующие им записи могут быть удалены по завершении контрольной точки.
Однако ненужные для восстановления журнальные записи могут быть еще нужны процессам wal sender, поскольку по тем или иным причинам они их еще не успели передать клиентам.
Для гарантии сохранности журнальных записей, еще не переданных по протоколу репликации, предусмотрен специальный серверный объект под названием слот репликации.
Слот репликации пропускает через себя журнальные записи и блокирует удаление тех сегментов WAL, в которых имеются не прошедшие через него записи.
Одним слотом могут пользоваться разные клиенты, но однажды прошедшая через слот журнальная запись больше не будет им блокироваться от удаления.
Например, с использованием функции pg_create_physical_replication_slot(name) именованный слот физической репликации может быть создан, а с использованием функции pg_drop_replication_slot(name) удален.
Важно отметить, что слот репликации блокирует удаление записей даже в случае отсутствия подключенных клиентов.
Такая ситуация может возникнуть, например, при разрыве соединения клиента с экземпляром. В этом случае сегменты WAL будут накапливаться, заполняя все свободное пространство на накопителях.
Поэтому важно осуществлять мониторинг использования слотов репликации и своевременно удалять неиспользуемые слоты.
Для мониторинга слотов предусмотрено системное представление pg_replication_slots.
Общее количество слотов репликации ограничено значением параметра max_replication_slots.
Необходимо отметить, что в некоторой степени предотвращение удаления старых сегментов WAL может быть также обеспечено использованием параметра wal_keep_size (по умолчанию 0), задающего минимальный объем журнала WAL.
Для работы со слотами репликации предусмотрен набор функций и соответствующих команд протокола репликации.
Непрерывное архивирование сегментов WAL
Из курса DBA2 «Администрирование Pangolin. Внутреннее устройство» известно, что восстановление согласованности данных после сбоя выполняется путем последовательного применения записей WAL процессом startup.
При наличии копии кластера баз данных и соответствующих сегментов WAL, накопленных за некоторый период времени, может быть обеспечено восстановление данных на заданный момент времени (Point-In-Time Recovery, PITR).
Для этого при восстановлении процессу startup достаточно прекратить применение записей WAL в определенный момент времени.
Более подробно восстановление на момент времени и другие варианты использования накопленных сегментов WAL будут рассмотрены в Лекции 5 «Физическое резервное копирование» курса DBA3.
Как было отмечено выше, накопление сегментов WAL может быть организовано с помощью утилиты pg_receivewal, основанной на использовании протокола репликации.
Однако, основным способом накопления сегментов WAL является непрерывное архивирование, которое выполняется непосредственно экземпляром сервера без необходимости использования дополнительных средств.
За его реализацию отвечает специальный фоновый процесс под названием archiver, который запускается параметром archive_mode = on (по умолчанию выключен). Изменение значения archive_mode требует перезапуска экземпляра.
Параметр archive_command
При заполнении очередного сегмента WAL процесс archiver выполняет его копирование путем применения команды оболочки, указанной в параметре archive_command.
Сегмент считается скопированным в архив, если команда archive_command завершилась нулевым статусом. В этом случае сегмент может быть удален контрольной точкой.
В противном случае копируемый сегмент и все следующие за ним не будут удаляться контрольной точкой — archiver будет повторять попытки выполнения команды копирования, пока не будет получен нулевой статус.
Для указания пути копируемого файла сегмента относительно каталога данных в команде используется подстановка %p, для указания только имени файла — %f.
Команда может иметь любое содержание. Ответственность за корректность archive_command лежит на администраторе.
Например, задание параметра archive_command может выглядеть следующим образом:
ALTER SYSTEM SET archive_command = 'test ! -f /archive/%f && cp %p /archive/%f';
SELECT pg_reload_conf();
Для применения значения archive_command достаточно перечитать конфигурацию.
В этом случае сначала проверяется наличие файла с названием копируемого сегмента, и только в случае его отсутствия выполняется копирование сегмента.
Проверка наличия архивного файла перед копированием сегмента с тем же именем — это распространенная мера сохранения целостности архива в случае ошибки администратора. Она защищает от перезаписи архивных файлов, например, в случае использования одного архивного каталога для разных экземпляров сервера.
Стоит упомянуть, что помимо команды оболочки, задаваемой в параметре archive_command, для копирования сегментов WAL при непрерывном архивировании также может применяться разделяемая библиотека, указанная в параметре archive_library (см. документацию)
Переключение на следующий сегмент
У непрерывного архивирования есть существенный недостаток: сегменты WAL по умолчанию копируются только после их полного заполнения.
При невысокой нагрузке заполнение сегмента WAL может занимать продолжительное время (вспомним, что размер сегмента составляет 16 MB). Соответственно накопленные в нем записи WAL долго не будут попадать в архив.
Компенсировать указанный эффект можно путем задания значения параметра archive_timeout. В нем указывается время, по истечении которого выполняется переключение на новый сегмент WAL, даже если текущий еще не заполнен.
Тогда недозаполненные сегменты по истечении archive_timeout секунд будут копироваться в архив.
Необходимо учитывать, что физический размер сегмента в этом случае остается равным 16 MB.
Поэтому выбор слишком маленького значения archive_timeout может привести к раздуванию архивного хранилища.
При необходимости высокой скорости пополнения архива WAL следует рассмотреть возможность использования протокола репликации вместо непрерывного архивирования.
Еще раз подчеркнем, что по протоколу репликации каждая новая запись WAL отдается подключенным клиентам по мере формирования.
Помимо этого, переключение на следующий сегмент журнала может быть выполнено принудительно с использованием функции pg_switch_wal.
Мониторинг непрерывного архивирования
Состояние непрерывного архивирования можно узнать с использованием системного представления pg_stat_archiver (см. документацию).
Однако стоит иметь в виду, что в случае прерывания процесса archiver (например, из-за ошибки оболочки) отследить указанную проблему посредством этого представления не получится.
Для этой цели можно использовать сборщик сообщений, за включение которого отвечает параметр logging_collector=on. В этом случае сообщения об ошибках выполнения команды archive_command будут попадать в журнал экземпляра сервера.
Итоги
- Журнал WAL используется не только для восстановления после сбоя; он также используется при резервном копировании и репликации
- Существует два способа получения записей WAL: протокол репликации и непрерывное архивирование
- Протокол репликации работает на уровне записей WAL, требуется поддерживающий его клиент
- Непрерывное архивирование работает на уровне сегментов WAL, может использоваться без дополнительных средств
Самопроверка
Вопрос 1
Какой процесс используется экземпляром сервера для обслуживания клиента, подключенного по протоколу репликации?
Вопрос 2
Какие значения параметра wal_level допустимы для возможности использования протокола репликации? Выберите все верные варианты ответа:
Вопрос 3
Какие средства можно использовать для предотвращения удаления сегментов WAL, еще не переданных по протоколу репликации? Выберите все верные варианты ответа:
Вопрос 4
Что из перечисленного инициирует копирование сегмента WAL в архив при непрерывном архивировании? Выберите все верные варианты ответа: