Postgresql 13 – Ускорьте pg_dump до 5 минут вместо 70 минут.

Вопрос или проблема

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

pg_dump -Fc database_name

На это уходит около часа, и создается файл размером более 30 Гбайт.

Как мы можем ускорить процесс?

Наша самая большая таблица содержит необработанные данные изображений в виде столбца bytea.

Когда мы делали простой COPY из psql на этой таблице в stdout, это было довольно быстро (1 или 2 минуты), но pg_dump был очень медленным. Это заняло около 60 минут.

Итак, исследуя это, я наткнулся на это обсуждение. Похоже, что сжатие pg_dump довольно медленно, если данные уже сжаты, как это бывает с данными изображений в формате bytea. И лучше сжимать вне pg_dump (-Z0).

Кроме того, мы обнаружили, что можем использовать нашу многопоточную CPU (-j 10 и pigz -p 10, чтобы использовать 10 ядер. Вы можете выбрать другое количество ядер).

Итак, теперь мы делаем это так:

$ pg_dump -Z0 -j 10 -Fd database_name -f dumpdir
$ tar -cf - dumpdir | pigz -p 10 > dumpdir.tar.gz
$ rm -r dumpdir

Время сократилось с ~70 минут до ~5 минут. Довольно удивительно.

Вы можете восстановить его так:

$ mkdir -p dumpdir
$ pigz -dc dumpdir.tar.gz | tar -C dumpdir --strip-components 1 -xf -
$ pg_restore -j 10 -Fd -O -d database_name dumpdir

Ответ или решение

Оптимизация времени выполнения pg_dump для PostgreSQL 13: Достигните 5 минут вместо 70

Использование pg_dump для создания ночных снимков вашей базы данных является стандартной, но часто весьма ресурсоемкой задачей, особенно когда речь идет о больших объемах данных, как в вашем случае — файл размером более 30 ГБ. Давайте рассмотрим, как можно значительно ускорить этот процесс, сократив его время выполнения с 70 до 5 минут, следуя предложенному вами решению.

Проблема и временные затраты

Исходный вызов:

pg_dump -Fc database_name

занимал около часа. Основная причина этого — наличие большого объема данных в формате bytea, которые содержат сжатые изображения. Это делает процесс медленным, поскольку встроенная компрессия pg_dump неэффективна для уже сжатых данных.

Решение: Оптимизация через распределение нагрузки

  1. Отключение компрессии в pg_dump: Использование флага -Z0 отключает компрессию на стороне pg_dump, что существенно сокращает время, затрачиваемое на эту операцию.

  2. Увеличение параллелизма: Флаг -j позволяет распределять работу по нескольким потокам. Если у вас мультикорный процессор, вы можете параллелить этот процесс и использовать ресурсы вашего оборудования более эффективно. В вашем примере используются 10 потоков, что существенно снижает время выполнения операции:

    pg_dump -Z0 -j 10 -Fd database_name -f dumpdir
  3. Ускоренная компрессия с pigz: Используйте pigz, расширенную версию gzip, поддерживающую многопоточность, для компрессии созданного дампа. Это позволит более эффективно использовать доступные ресурсы процессора:

    tar -cf - dumpdir | pigz -p 10 > dumpdir.tar.gz
  4. Очистка временных файлов:

    rm -r dumpdir

Восстановление дампа

Для восстановления данных из оптимизированного дампа следуйте следующей процедуре:

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

    mkdir -p dumpdir
  2. Разархивируйте и извлеките файлы:

    pigz -dc dumpdir.tar.gz | tar -C dumpdir --strip-components 1 -xf -
  3. Восстановите базу данных с параллелизмом:

    pg_restore -j 10 -Fd -O -d database_name dumpdir

Заключение

Ваша проделанная работа по оптимизации не только решает проблему времени выполнения, но и демонстрирует эффективное использование ресурсов современных процессоров. Это значительно сокращает время создания дампа без потери качества резервного копирования и восстановления данных. Урок из этого примера: разумное распределение нагрузки и использование правильных инструментов может привести к впечатляющим улучшениям производительности, что особенно важно при регулярной обработке больших объемов данных.

Оцените материал
Добавить комментарий

Капча загружается...