Переезд PostgreSQL на новую версию без простоя: разбор
Логическая репликация позволяет перенести работающую базу PostgreSQL на новый кластер и сократить паузу до переключения приложения. Но DDL, последовательности и незавершённые транзакции требуют отдельного плана — иначе «почти без простоя» обернётся потерей данных.

Что на самом деле значит «без простоя»
При переезде, например, с PostgreSQL 16 на PostgreSQL 17 можно заранее развернуть новый кластер, скопировать в него данные и непрерывно передавать изменения из старой базы. Приложение продолжает работать почти до самого переключения. Но в момент смены адреса подключения записи нужно остановить, незавершённые транзакции — завершить, а отставание реплики — свести к нулю.
Поэтому точнее говорить о миграции с коротким окном переключения, а не о гарантированном нулевом простое. Его длительность зависит от объёма оставшихся изменений, числа соединений и того, насколько хорошо приложение переживает переподключение. Если нельзя приостановить запись даже на короткое время, это отдельное архитектурное требование: одной настройки PostgreSQL для него недостаточно.
Логическая репликация переносит изменения строк, но не превращает новую базу в точную копию всего старого кластера. Схему, последовательности и момент переключения приходится контролировать отдельно.
Как изменения проходят между кластерами
В этом разборе источник — PostgreSQL 16, приёмник — PostgreSQL 17. На исходном кластере создают публикацию таблиц, а на целевом — подписку на неё. При первоначальной синхронизации PostgreSQL копирует существующие строки, затем применяет накопившиеся и новые изменения. После этого изменения продолжают идти из журнала транзакций WAL через механизм логического декодирования.
Подписчик применяет полученные операции к своим таблицам. Это не побайтовое копирование файлов базы: у кластеров разные каталоги данных и версии, а передаются логические изменения. Такой способ позволяет оставить старый сервер источником истины, пока новый догоняет его, и отложить переключение до удобного момента.
WAL — журнал предзаписи PostgreSQL. В нём фиксируются изменения, необходимые для восстановления и передачи данных; логическая репликация превращает подходящие записи журнала в операции над строками.
Что логическая репликация не перенесёт автоматически
- Изменения схемы. Создание таблиц, изменение типов и другие DDL-операции нужно отдельно и согласованно выполнять на целевом кластере. Если приложение уже пишет в новую колонку, а на приёмнике её нет, применение изменений может остановиться.
- Состояние последовательностей. Значения sequence, в том числе используемые столбцами identity и serial, логическая репликация не синхронизирует. Перед переключением нужно перенести их актуальное состояние и проверить, что следующая выдача значения не столкнётся с уже существующим ключом.
- Большие объекты. Их нельзя считать перенесёнными вместе с обычными строками таблиц. Если приложение использует large objects, нужен отдельный способ переноса и проверки.
- Таблицы без подходящей идентификации строк. Для UPDATE и DELETE подписчику нужно понять, какую строку менять. Обычно для этого используют первичный ключ; если его нет, заранее проверьте требования к replica identity и выберите подходящую схему.
При этом версии расширений и их совместимость тоже нужно проверять отдельно. Скопировать таблицы недостаточно, если приложение зависит от расширения, которого нет на целевом сервере или которое там ведёт себя иначе.
Почему выбирают этот способ, а не pg_upgrade
Методы миграции решают разные задачи. Логическая репликация полезна, когда важно сократить окно недоступности и есть время подготовить второй кластер. Если допустима остановка приложения на время обновления, штатный pg_upgrade обычно проще: он переносит существующий кластер между major-версиями, но требует согласованного окна обслуживания. Резервная копия с восстановлением даёт прямолинейный перенос, однако время простоя зависит от объёма базы и скорости копирования.
| Подход | Что происходит | Главная цена | Когда выбирать |
|---|---|---|---|
| Логическая репликация | Новый кластер копирует таблицы и получает поток изменений от старого | Нужно отдельно вести DDL, последовательности и проверку согласованности | Когда критично короткое окно переключения и можно поддерживать два кластера |
| pg_upgrade | Существующий кластер обновляют до новой major-версии | Нужны остановка приложения и время на проверку после обновления | Когда допустимо окно обслуживания и нужна более простая схема переноса |
| Резервная копия и восстановление | Данные выгружают и загружают в целевой кластер | Запись обычно приходится остановить на время переноса и проверки | Для небольших баз или миграции, где длительная пауза приемлема |
Время переноса нельзя надёжно вывести только из размера базы. Для логической репликации важны скорость первоначального копирования, темп записи в исходную базу, пропускная способность сети и способность приёмника применять изменения быстрее, чем они накапливаются. Эти параметры нужно измерить на копии или тестовом стенде с похожей нагрузкой.
Где чаще всего ломается план
Приёмник отстаёт от источника
Если приложение создаёт изменения быстрее, чем подписчик их применяет, очередь растёт. Смотрите на состояние подписки, задержку применения и объём WAL, удерживаемого слотом репликации. Простой подписчика может привести не только к большому отставанию, но и к росту занятого диска на источнике: нужный для передачи WAL нельзя удалить, пока слот его удерживает.
Приложение меняет схему во время копирования
Логическая репликация не разносит DDL автоматически. Изменение нужно внести на обеих сторонах в совместимом порядке: сначала подготовить целевую схему, затем перевести приложение на использование нового поля или таблицы. Правильная последовательность зависит от конкретного изменения; универсальный сценарий для всех DDL-операций небезопасен.
Проверили строки, но забыли о прочих данных
Сравнение числа строк помогает найти грубые расхождения, но само по себе не доказывает, что данные совпадают. Для критичных таблиц сравните контрольные выборки или контрольные суммы по согласованному алгоритму, а также проверьте ограничения, индексы и последовательности. Учитывайте, что проверка больших таблиц сама создаёт нагрузку и может конкурировать с рабочими запросами.
Переключили адрес, но не соединения
Изменение DNS или строки подключения не заставляет уже открытые соединения мгновенно перейти на новый сервер. Перед переключением нужно прекратить приём новых записей старым приложением, дождаться завершения активных транзакций и предусмотреть переподключение пулов. Если часть экземпляров приложения продолжит писать в старый кластер, появятся две расходящиеся версии данных: автоматического объединения обратно не будет.
Порядок переключения без гонки записей
- Проверьте совместимость. Сверьте версии PostgreSQL, расширений и клиентских библиотек, типы данных и настройки приложения. Убедитесь, что целевая схема готова принимать все изменения, которые приложение передаёт при репликации.
- Поднимите целевой кластер и настройте репликацию. Создайте публикацию и подписку по документации PostgreSQL для используемых версий. Дождитесь завершения первоначальной синхронизации всех таблиц. Проверка: подписка активна, синхронизация закончена, ошибки применения не накапливаются.
- Проверьте качество переноса. Сравните данные на выбранных критичных таблицах, проверьте ограничения и отдельно подготовьте последовательности. Проверка: расхождения объяснены, а следующий идентификатор не повторит существующее значение.
- Подготовьте короткое окно переключения. Остановите или ограничьте запись, завершите активные транзакции и дождитесь применения последних изменений на целевом кластере. Проверка: источник больше не принимает новые записи, а подписчик не отстаёт по применяемым изменениям.
- Переключите приложение и проверьте его работу. Направьте новые подключения на PostgreSQL 17, восстановите запись и проверьте ключевые операции приложения, ошибки и задержки запросов. Проверка: новые данные появляются на целевом кластере, а запросы не продолжают случайно идти на старый.
Откат после возобновления записи на новом сервере — не кнопка «вернуть DNS». Старый кластер уже не получает новые изменения. До переключения подготовьте критерии отката и решите, как поступать с записями, созданными после него: без обратной репликации или отдельного восстановления они могут потеряться при возврате на старую базу.
Что делать дальше
Начните не с переключения, а с репетиции на копии базы. Зафиксируйте, сколько занимает первоначальная синхронизация, как быстро приёмник догоняет источник под типичной нагрузкой и сколько длится прекращение записи с переподключением приложения. В продуктивной среде наблюдайте за отставанием подписки и свободным местом на диске, который удерживает WAL. Отдельно проверьте текущие ограничения и детали настройки в документации PostgreSQL 16 и 17: совместимость зависит от конкретной версии и конфигурации.
Разбор научной статьи: Сложный текст — понятным языком, с терминами
Спросить за 12 ₽Источники: PostgreSQL 17: Logical Replication, PostgreSQL 17: Restrictions
Частые вопросы
Можно ли совсем не останавливать запись при переключении?
Перенесутся ли автоматически индексы и ограничения?
Что будет, если подписчик остановится во время миграции?
Можно ли вернуться на старый кластер после переключения?
Подойдёт ли эта схема для другой пары версий PostgreSQL?
Нужно ли отдельно синхронизировать sequence?
Материал носит информационный характер и подготовлен редакцией «Агентуры». Он не является офертой, рекламой или индивидуальной консультацией. Упомянутые продукты, компании и торговые знаки принадлежат их правообладателям. Перед принятием решений, влекущих юридические или финансовые последствия, обратитесь к профильному специалисту.