Привет всем Хабр-читателям. Про развертывание и настройку HA кластера PostgreSQL с помощью Patroni написано много полезных статей, однако я не нашел описания алгоритма его работы. В этой статье я хочу поделиться своим исследованием по данному вопросу.

1) Настройка Patroni

Вкратце напомню, что конфигурационный файл состоит из нескольких блоков:

  • описание: scope (имя кластера), namespace (имя директории хранилища конфигурации, где Patroni будет хранить информацию о кластере), name (имя узла кластера);

  • блок «log»: настройки логирования;

  • блок «restapi»: настройки REST API Patroni;

  • блок «dcs»: настройки распределенного хранилища конфигураций (Distributed Configuration Store -–DCS);

  • блок «raft»: настройки для алгоритма RAFT (как правило используется DCS);

  • блок «bootstrap» в котором указываются динамические настройки, которые будут сохранены в DCS при инициализации кластера;

  • блок «postgresql» в котором указываются настройки для PostgreSQL;

  • - блок «watchdog»: настройки watchdog (для работы требуется: chown postgres:postgres /dev/watchdog);

  • блок «tags» настройка тегов для узла кластера

2) Инициализация кластера

Во время инициализации в DCS создаётся директория: /<namespace>/<scope>/ (пример: /service/postgresql-cluster/)

В указанной директории создается следующая структура ключей:

|- members (директория с описанием узлов кластера)

|    |- описание узла (имя, настройки подключения PostgreSQL, настройки                    |        Patroni, статус, роль, версия Patroni, значение xlog, значение timeline,                 |        значение ttl-ключа)

|    |- …

|- config (динамическая конфигурация для кластера)

|- failover

|- history (история switchover и failover)

|- initialize (уникальный номер для данного кластера)

|- leader (узел являющий лидером и его ttl-ключ)

|- status (время uptime)

3) Запуск Patroni

В начале Patroni:

  • проверяет доступность DCS;

  • запускает PostgreSQL;

  • из файла конфигурации считываются параметры локальной конфигурации;

  • проверяет DCS на наличие директории (параметр «namespace»);

  • проверяет DCS на наличие директории с именем кластера (параметр «scope»);

  • если в DCS нет информации о кластере, то производится процедура инициализации;

  • если в DCS есть настройки кластера, то из DCS считывается динамическая конфигурация;

  • происходит применение локальной и динамической конфигурации;

  • если это первый узел кластера, он становиться мастер-сервером ;

  • если в DCS есть уже мастер и нет данных об этом узле, то в распределенное хранилище записываются его параметры;

4) Алгоритм работы Patroni

Основные параметры

  • loop_wait (10 сек) время ожидания

  • ttl (30 сек) время хранения ключа

  • retry_timeout (10 сек) время для повторных попыток связи с DCS

ttl >= loop_wait + 2*retry_timeout 

Daemon Patroni использует цикл обработки:

 

Вначале цикла служба обновляет значение ttl-ключа лидера ttl-ключей каждого из узлов кластера в DCS и если не требуется выполнить других действий, то засыпает. Время, на которое засыпает Patroni равно значению loop_wait.

Если сервер становится недоступен или возникают ошибки в службе Patroni, то не обновляется значение ttl-ключа для данного узла, пока значение не достигнет 0.

В случае если истекло значение ttl-ключа узла реплики PostgreSQL, то узел исключается из кластера.

В случае если истекло значение ttl-ключа мастер узла PostgreSQL, то производятся перевыборы нового мастера из оставшихся членов кластера.

Перевыборы нового мастер-сервера PostgreSQL

В случае остановки службы PostgreSQL или истечения времени ttl-ключа на мастер-сервере производятся перевыборы нового мастера

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

5) Мониторинг

Для мониторинга DCS и PostgreSQL имеются шаблоны практически для большинства систем мониторинга. Для мониторинга Patroni я использую возможности его API, которое позволяет проверять статус мастер-сервера, узла реплики, а также состояния Patroni (http://{<ip-address>:<patroni_port>/health).

Спасибо за внимание, буду рад ответить на вопросы в комментариях.

Комментарии (2)


  1. Chupaka
    01.07.2022 09:30

    А клиенты при этом куда подключаются?


    1. fixed77
      01.07.2022 10:06

      например на плавающий между нодами адрес. (keepalived, vip-manager)