Увійти Реєстрація
Блог Серії
Кар'єра
Вакансії Компанії
Навчання
Документація Співбесіди Тестування Відео
Екосистема
Пакети Ресурси Проєкти Інструменти Події
Інше
Про нас Реклама

Як безпечно змінювати схему великої таблиці на продакшені?

Головна небезпека не в тривалості самої зміни, а в блокуваннях. ALTER TABLE у PostgreSQL бере ACCESS EXCLUSIVE-блокування. Якщо в цей момент іде довгий запит, ALTER стає в чергу - і всі нові запити до таблиці стають у чергу за ним. Сайт лягає, хоча сама операція займає мілісекунди.

Правила, що рятують:

SET lock_timeout = '3s';       -- краще впасти й повторити, ніж повісити таблицю
SET statement_timeout = '60s';
ALTER TABLE orders ADD COLUMN note text;

Що дешево, а що ні (PostgreSQL):

  • Додати колонку без значення за замовчуванням чи з незмінним default (PostgreSQL 11+) - миттєво, лише метадані.
  • Додати NOT NULL до наявної колонки - повна перевірка таблиці під блокуванням. Безпечніше: CHECK (col IS NOT NULL) NOT VALID, потім VALIDATE CONSTRAINT (без блокування запису), потім SET NOT NULL (PostgreSQL 12+ використає перевірене обмеження).
  • Зовнішній ключ - так само: NOT VALID, потім VALIDATE.
  • Змінити тип колонки - часто переписування всієї таблиці. Краще нова колонка, поступове заповнення, перемикання.
  • Індекс - лише CONCURRENTLY.

Перейменування й видалення - через «розширити, потім звузити» (expand/contract):

  1. Додати нову колонку, код пише в обидві.
  2. Перенести старі дані порціями.
  3. Код читає з нової.
  4. Окремим деплоєм прибрати стару колонку.

Так кожен крок сумісний і з попередньою, і з наступною версією коду, і деплой можна відкотити.

MySQL: багато змін виконуються online (ALGORITHM=INSTANT для додавання колонки з 8.0), для решти - gh-ost чи pt-online-schema-change.

Докладніше в документації: ALTER TABLE

Перевір себе

20 випадкових питань за спробу, після завершення - розбір кожної помилки

Схожі питання