Устранение перестроения индекса при увеличении размерности типа колонки в партиционированных таблицах
Описание
В СУБД Pangolin реализовано поведение, что при изменении размерности колонки партиционированной таблицы не происходит перестроение локального индекса, построенного по этой колонке.
В основе данного решения использована логика сохранения RelFileNode, которая реализована и используется для обычных таблиц в оригинальном PostgreSQL. Эта логика была воспроизведена для всех партиций таблицы, к которой применяется команда ALTER TABLE.
Описание решения
На этапе обработки операции ALTER TABLE формируется список RelFileNode входящих индексов с сохранением их имен и OID namespace. В данный список включаются только совместимые индексы. Проверка совместимости выполняется с использованием оригинальной функции, применяемой для непартиционированных таблиц.
Сформированный список используется на этапе создания субиндексов. Сопоставление выполняется по имени субиндекса и OID namespace таким образом, чтобы при пересоздании индекс фактически создавался пустым, без данных. На финальном этапе обработки для каждого сохраненного RelFileNode выполняется подстановка соответствующих объектов файловой системы в уже существующий пустой индекс.
В результате индексы и их субиндексы логически пересоздаются и получают новые OID, однако используемые RelFileNode сохраняют свои значения без изменений. Такой подход позволяет существенно сократить время выполнения операции ALTER TABLE для совместимых изменений.
Решение о применимости оптимизации принимается по следующим критериям, учитывается:
- бинарная совместимость типов;
- размер целевой колонки (>=);
- возможность изменения специфических параметров колонки (например,
collation,timezoneи других).
Назначение
Значительно ускорить перестроение индексов при выполнении операции ALTER TABLE для партиционированных таблиц аналогично механизму для ускорения этой операции для непартиционированных таблиц в ядре PostgreSQL.
Ограничения
Ограничения полностью соответствуют ограничениям оригинальной версии на перестроение индексов для непартиционированных таблиц и включают:
- бинарную совместимость старого и нового типа колонки;
- равный или больший размер нового типа колонки;
- специфичные для типа ограничения (например,
timezoneдля колонки даты); - отсутствие применимости для глобальных индексов (ГИ).
Настройка
Функциональность не требует отдельно настройки и доступна сразу после установки СУБД.
Отключение данной функциональность невозможно.
Сценарии использования
Уменьшение размера колонки
Предусловия
-
Создайте партиционированную таблицу:
CREATE TABLE test_expl_glob (
id bigserial,
start_date timestamp,
status1 varchar(1),
status2 varchar(1)
)
PARTITION BY RANGE (start_date); -
Создайте индексы:
CREATE index test_expl_glob_idx_1 ON test_expl_glob USING btree (status1);
CREATE index test_expl_glob_idx_2 ON test_expl_glob USING btree (status2); -
Создайте партиции:
CREATE TABLE test_expl_glob1 PARTITION OF test_expl_glob FOR VALUES FROM ('2024-07-02 00:00:00') TO ('2024-07-03 00:00:00');
CREATE TABLE test_expl_glob2 PARTITION OF test_expl_glob FOR VALUES FROM ('2024-07-03 00:00:00') TO ('2024-07-04 00:00:00');
CREATE TABLE test_expl_glob3 PARTITION OF test_expl_glob FOR VALUES FROM ('2024-07-04 00:00:00') TO ('2024-07-05 00:00:00'); -
Заполните таблицу данными:
INSERT INTO test_expl_glob SELECT g.id,'2024-07-02 15:34:40.472880','A','C' FROM generate_series(1,3000000) g(id);
INSERT INTO test_expl_glob SELECT g.id,'2024-07-03 15:34:40.472880','A','C' FROM generate_series(1,3000000) g(id);
INSERT INTO test_expl_glob SELECT g.id,'2024-07-04 15:34:40.472880','A','C' FROM generate_series(1,3000000) g(id);
Шаги
-
Выполните команду
ALTER TABLEбез перестроения индекса:ALTER TABLE test_expl_glob ALTER COLUMN status1 TYPE varchar(2);
ALTER TABLE test_expl_glob ALTER COLUMN status1 TYPE varchar(200);
ALTER TABLE test_expl_glob ALTER COLUMN status1 TYPE varchar(500); -
Выполните команду
ALTER TABLEс перестроением индекса (уменьшение ширины колонки):ALTER TABLE test_expl_glob ALTER COLUMN status1 TYPE varchar(1);При изменении размерности колонки
status1партиционированной таблицыtest_expl_globне происходит перестроение локального индекса, построенного по этой колонке.