- PVSM.RU - https://www.pvsm.ru -
Операция VACUUM FULL полностью пересоздаёт таблицу, предельно оптимизируя её. Она требует полной блокировки таблицы, поэтому высоконагруженные таблицы обрабатывать ею без простоя системы нельзя. Вместо VACUUM FULL можно использовать расширение pg_repack. Оно создаёт на обрабатываемой таблице триггер, отслеживающей модификации, создаёт копию таблицы, догоняет набежавшие изменения. В конце работы берётся короткая блокировка, старая таблица удаляется, новая становится на её место.
Недостатком pg_repack является то, что она работает СЛИШКОМ БЫСТРО – фактически данные копируются и удваиваются в объёме (по отношению к исходной таблице). Каталог pg_wal забивается с такой скоростью, что архиватор не успевает обрабатывать файлы.
Далее описывается способ замедления работы pg_repack с использованием механизма cgroup.
Система:
Linux RedOS.
PostgreSQL 15.2 on x86_64-pc-linux-gnu, compiled by gcc (GCC) 8.3.1 20191121 (Red Hat 8.3.1-6), 64-bit.
pg_repack версия 1.4.8.
Экспериментальная таблица [data.usage] 17gb – 13gb данные, 4gb индекс.
Если в системе работает только pg_repack и нет другой нагрузки, при ограничениях IO она может подолгу ожидать заполнения WAL-файла, чтобы переключиться на новый. Чтобы имитировать загрузку системы и оперативное переключение на новый WAL, создаём таблицу t1 (CREATE TABLE t1(i INTEGER);) и запускаем вечный скрипт [series.sh] – с интервалом 1 раз в секунду удаляет из неё строки и записывает 1000 строк. Скрипт [series.sh]:
#!/bin/bash
while true
do
psql -d db01 -c "DELETE FROM t1; INSERT INTO t1 SELECT generate_series(1,1000,1);" > /dev/null
sleep 1
done
Если операции оптимизации таблиц выполняются на работающей под нагрузкой базе данных, запускать этот скрипт ни к чему – WAL-файлы постоянно наполняются и сменяются.
Скрипт [run.sh] – перестроение таблицы с замером времени:
#!/bin/bash
t1=$(date +%s)
pg_repack -d db01 -p 5432 -t data.usage
t2=$(date +%s)
echo "time: $(($t2-$t1))"
Добавляем в корневую группу cgroup возможность управления ограничениями IO и создаём подгруппу g1.
# echo "+io" >> /sys/fs/cgroup/cgroup.subtree_control
# mkdir /sys/fs/cgroup/g1
Смотрим блоки major и minor раздела, который хотим ограничить (sdb, 8:16):
# lsblk
NAME MAJ:MIN RM SIZE RO TYPE MOUNTPOINTS
fd0 2:0 1 4K 0 disk
sda 8:0 0 100G 0 disk
├─sda1 8:1 0 500M 0 part /boot
...
sdb 8:16 0 4T 0 disk
├─sdb1 8:17 0 500M 0 part /boot
...
Будем смотреть время обработки таблицы, количество WAL-файлов в каталоге pg_wal к завершению отработки.
Ограничиваем 20mb/sec скорость чтения и записи раздела sdb процессам группы g1.
# echo "8:16 rbps=$((20*1024*1024)) wbps=$((20*1024*1024))" > /sys/fs/cgroup/g1/io.max
Запускаем run.sh и смотрим PID-ы процессов в PostgreSQL:
SELECT * FROM pg_stat_activity WHERE application_name = 'pg_repack';
>>> 50447, 50448
Помещаем их в группу g1:
# echo 50447 > /sys/fs/cgroup/g1/cgroup.procs
# echo 50448 > /sys/fs/cgroup/g1/cgroup.procss
Ожидаем завершения работы скрипта run.sh. Наблюдать за работой процесса можно командой iotop -p 50447. Завершивший работу процесс группы g1 удаляется из неё автоматически.
Аналогично проводим измерения для ограничений 40mb, 80mb, 160mb и без ограничения скорости.
Скорость обработки считается как размер файла (17gb), делённый на количество секунд, ушедших на его обработку.
|
Ограничение диска (mb/sec) |
Скорость обработки (mb/sec) |
Время работы (sec) |
Накопление WAL (шт.) |
|
20 |
7,02 |
2477 |
250 |
|
40 |
8,52 |
2041 |
350 |
|
60 |
23,78 |
732 |
300 |
|
80 |
28,39 |
613 |
550 |
|
160 |
40,86 |
426 |
700 |
|
без ограничения |
48,08 |
362 |
700 |
Можно, например, начинать замедление с 80mb/sec. Смотреть количество WAL в каталоге pg_wal. Если архиватор не успевает их переносить – уменьшить скорость IO группы cgroup. Оптимальное значение подбирать индивидуально, оно определяется загрузкой системы, пропускной способностью диска, свободным местом.
Удаление таблицы (если создавалась):
DROP TABLE t1;
Удаление группы cgroup:
# rmdir /sys/fs/cgroup/g1
Автор: utdm
Источник [1]
Сайт-источник PVSM.RU: https://www.pvsm.ru
Путь до страницы источника: https://www.pvsm.ru/postgresql/410135
Ссылки в тексте:
[1] Источник: https://habr.com/ru/articles/880646/?utm_source=habrahabr&utm_medium=rss&utm_campaign=880646
Нажмите здесь для печати.