Как изменить значение по умолчанию большой таблицы Postgres, не принимая навсегда? - PullRequest
2 голосов
/ 13 сентября 2011

В приложении Rails с поддержкой Postgres, запущенном на Heroku, я пытаюсь добавить логический столбец, для которого по умолчанию установлено значение false, а для нуля установлено значение false (NOT NULL).

Миграция занимает часы за часом (на самом деле около 15 или около того таких полей необходимо добавить). Использование памяти идет через крышу (5-6 ГБ или более). Я думаю, это потому, что Postgres упаковывает миграцию в транзакцию и пытается загрузить всю таблицу в память, чтобы она могла откатиться при сбое.

Без поля по умолчанию или NOT NULL столбец добавляется в мгновение ока.

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

Теперь миграция занимает около 3-4 часов и использует только около 100 МБ ОЗУ.

Есть ли лучшее решение?

Ответы [ 2 ]

2 голосов
/ 13 сентября 2011

Исходя из вашего времени, я ожидаю, что вы выполняете «обновление» через RoR, что, возможно, означает обработку «строка за раз».Я только что проверил таблицу 300K строк с первичным ключом и 3 внешними ключами, и добавление логического значения стоит около 5 секунд (для меня это слишком мало для точного сравнения) Запрос:

ALTER TABLE mine.trivally
    ADD COLUMN the_bool boolean NOT NULL DEFAULT 'True' ;

, который предлагаетчто ваш фреймворк производит неоптимальный код.По меньшей мере.

0 голосов
/ 13 сентября 2011

Извлечение large-hadron-migrator .Он претендует на реализацию схемы для крупномасштабной миграции за одной таблицей.Это намного сложнее, чем просто миграция, потому что она использует пару фоновых таблиц и набор триггеров, чтобы выполнить миграцию либо в режиме онлайн, либо с минимальным временем простоя.

...