Postgresql - большое удаление из 500Gb DB/auto-vacuum?

Мне нужно удалить около 80% моей базы данных Postgresql объемом 500 ГБ. На данный момент я успешно выполнил команду удаления примерно для 50 ГБ строк и приостановил выполнение, прежде чем продолжить. (Это заняло много времени, возможно, один час)

Я заметил, что после удаления около 50 ГБ данных дополнительное место на диске не освобождается, но при запуске «htop» можно наблюдать некоторые процессы postgres с интенсивным использованием памяти. Правильно ли я предполагаю, что это связано с мертвыми строками, которые необходимо очистить до освобождения места на диске?

Вторая часть этого вопроса: если я не ошибаюсь насчет первой части, лучше ли мне удалить все строки, а затем разрешить автоочистку? Похоже, автоочистка (или какой-то другой интенсивный фоновый процесс) запустилась сама по себе, прежде чем у меня появилась возможность продолжить список команд для удаления строк. Мне просто продолжить или я должен изящно сказать ему остановиться первым?


person JSStuball    schedule 06.04.2018    source источник
comment
autovacuum не выполняет vacuum full - поэтому он не обязательно освобождает место на диске для удаленных кортежей, но вместо этого помечает их как повторно используемые. да- это нормально. нет - не стоит об этом заботиться - продолжайте свою работу, предоставив автовакууму выполнять свою работу   -  person Vao Tsun    schedule 06.04.2018


Ответы (2)


После большого удаления обязательно запустится автоочистка. Это так, как задумано, и не должно мешать вам удалять еще больше строк.

Хотя автоочистка освобождает мертвое пространство в таблицах, оно не возвращает пространство операционной системе. Скорее, оно остается свободным пространством в таблице и может быть повторно использовано для будущих вставок.

Если вы хотите сжать таблицы, запустите для них VACUUM (FULL), но имейте в виду, что при этом таблица перезаписывается, поэтому временно используется дополнительное пространство для хранения и блокируются все одновременные действия с таблицей.

Если вам приходится регулярно выполнять такие массовые удаления, подумайте о разбиении таблицы на разделы. Это делает массовое удаление безболезненным.

person Laurenz Albe    schedule 06.04.2018

Лучшим решением было бы TRUNCATE таблицу.

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

В итоге я продублировал таблицу:

CREATE table dupe_table AS (SELECT * FROM table);

Усечение исходной таблицы:

TRUNCATE table

Наконец, перемещение данных обратно:

INSERT INTO table(column1, column2, column3)
SELECT column1, column2, column3
FROM dupe_table

ПРИМЕЧАНИЕ: вы можете потерять данные, если транзакция произойдет между созданием дубликата таблицы и усечением исходной таблицы.

person ricks    schedule 06.05.2020