Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

Транзакции и MVCC

AngaraBase обеспечивает конкурентный доступ к данным через MVCC (Multi-Version Concurrency Control). Транзакции гарантируют атомарность изменений, а MVCC позволяет читателям и писателям работать одновременно без взаимных блокировок.

Основы транзакций

Управление транзакциями

BEGIN; -- начать явную транзакцию
SAVEPOINT sp1; -- создать точку сохранения
ROLLBACK TO SAVEPOINT sp1; -- откатить до точки сохранения
COMMIT; -- зафиксировать транзакцию
ROLLBACK; -- откатить всю транзакцию

Autocommit

По умолчанию AngaraBase работает в режиме autocommit: каждый отдельный SQL-оператор выполняется как самостоятельная транзакция. Если оператор завершается успешно — результат фиксируется автоматически, при ошибке — откатывается.

Для операций, затрагивающих несколько строк или таблиц, используйте явные транзакции (BEGIN / COMMIT), чтобы объединить изменения в единую атомарную единицу.

MVCC: версионирование строк

Ключевая идея MVCC — читатели не блокируют писателей, писатели не блокируют читателей. Это достигается за счёт хранения нескольких версий каждой строки.

Метаданные версий

Каждая версия строки содержит два служебных поля:

ПолеНазначение
created_commitEpoch (commit timestamp), при котором версия была создана
deleted_commitEpoch, при котором версия была помечена как удалённая ( для активных версий)

Правило видимости

Версия строки видна транзакции со snapshot S, если выполняются оба условия:

  1. created_commit <= S — версия создана до или в момент snapshot
  2. Версия не удалена, или deleted_commit > S — удаление произошло после snapshot

Операции записи

  • INSERT — создаёт новую версию строки с created_commit = текущий epoch
  • UPDATE — не меняет строку на месте. Вместо этого: помечает текущую версию как удалённую (deleted_commit = текущий epoch) и создаёт новую версию с обновлёнными данными
  • DELETE — помечает версию как удалённую (deleted_commit = текущий epoch)

Уровни изоляции

Каждая транзакция получает snapshot — фиксированное представление данных на определённый момент времени.

READ COMMITTED (по умолчанию)

Snapshot обновляется перед каждым оператором. Транзакция видит все данные, зафиксированные до начала текущего оператора. Это рекомендуемый уровень изоляции для большинства задач.

SET TRANSACTION ISOLATION LEVEL READ COMMITTED;

REPEATABLE READ

Snapshot фиксируется в момент BEGIN и не меняется до конца транзакции. Все операторы внутри транзакции видят одно и то же состояние данных.

SET TRANSACTION ISOLATION LEVEL REPEATABLE READ;

SERIALIZABLE

С версии 0.6.4.4 AngaraBase реализует полноценный SERIALIZABLE (SSI) уровень изоляции. В режиме SERIALIZABLE аномалии write skew и phantoms предотвращаются через механизм SIREAD-блокировок и отслеживание rw-антизависимостей. Транзакции, нарушающие сериализуемость, прерываются с кодом 40001.

SET TRANSACTION ISOLATION LEVEL SERIALIZABLE;

Блокировки

Операции чтения

Чтение использует MVCC snapshot и не требует блокировок. Читатель никогда не ждёт писателя и наоборот.

Операции записи (Lock-Free DML)

Писатели используют атомарные операции (Compare-And-Swap) для установки версий на уровне строк, что обеспечивает lock-free бесконфликтные изменения. Блокировки в классическом виде больше не удерживаются.

DDL-операции

Операции изменения схемы (CREATE TABLE, ALTER TABLE, DROP TABLE) захватывают table-level locks на время выполнения.

Обнаружение deadlock

AngaraBase обнаруживает взаимные блокировки (deadlock) с помощью:

  • Timeout — если транзакция ожидает блокировку дольше заданного порога, она прерывается
  • Victim selection — при обнаружении цикла система выбирает транзакцию-жертву для отката
  • Deterministic lock ordering — внутренняя стратегия упорядочивания блокировок для снижения вероятности deadlock

Сборка мусора (AngaraGC)

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

Механизм работы

  1. GC watermark — вычисляется как минимальный snapshot среди всех активных транзакций: min(active_snapshots)
  2. Версии строк с deleted_commit < watermark безопасны для удаления — ни одна активная транзакция не может их увидеть
  3. Очистка выполняется фоновым процессом без остановки обработки запросов
  4. Bounded slices — GC обрабатывает данные порциями фиксированного размера, чтобы не вызывать всплески задержки
  5. Epoch Reaper — фоновый процесс (начиная с версии 0.6.5.24), который предотвращает зависание GC watermark из-за разорванных соединений или зависших сессий.

Отличие от PostgreSQL

В AngaraBase нет autovacuum в привычном понимании. Используется гибридный дизайн с epoch-based watermark (как в Oracle/InnoDB), что позволяет точнее контролировать момент очистки.

Рекомендации

  • Используйте READ COMMITTED (уровень по умолчанию) для большинства рабочих нагрузок
  • Избегайте долгоживущих транзакций — они удерживают GC watermark и не позволяют очистить старые версии строк, что увеличивает потребление дискового пространства
  • При использовании REPEATABLE READ помните о возможности write skew. Если нужна строгая сериализуемость, используйте явные блокировки (SELECT ... FOR UPDATE)

MVCC state при crash recovery

При перезапуске после аварийного завершения AngaraBase восстанавливает состояние MVCC из transaction log (WAL).

Что восстанавливается

  1. Committed transactions — транзакции, которые успели записать COMMIT в WAL
  2. Aborted transactions — незавершённые транзакции помечаются как aborted
  3. MVCC visibility — информация о том, какие версии строк видны для каждого commit epoch
  4. Transaction counters — текущий commit epoch и другие счётчики

Процесс восстановления

  1. WAL scan — сканирование файлов transaction log в хронологическом порядке
  2. MVCC replay — восстановление in-memory структур MVCC из записей в WAL
  3. Cleanup — пометка незавершённых транзакций как aborted

Ограничения

  • Backend requirement: восстановление MVCC работает только с transaction_log.backend = "file_bin"
  • Memory rebuild: MVCC state восстанавливается в памяти, что может занять время при большом объёме WAL
  • Read-your-writes: сразу после restart незавершённые транзакции не видны (помечены как aborted)

Мониторинг восстановления

-- Проверить режим восстановления
SELECT recovery_mode FROM sys.identity;

-- Проверить состояние системы после recovery
SELECT txn_commit_epoch_current FROM sys.health;

Возможные значения recovery_mode:

  • "normal" — обычный старт без восстановления
  • "crash_recovery" — восстановление после аварийного завершения
  • "forced_takeover" — принудительный захват instance lease

Связанные разделы